diff --git a/src/db/db/gsiDeclDbTrans.cc b/src/db/db/gsiDeclDbTrans.cc index 794e787b5..eea902139 100644 --- a/src/db/db/gsiDeclDbTrans.cc +++ b/src/db/db/gsiDeclDbTrans.cc @@ -33,6 +33,43 @@ namespace gsi { +// --------------------------------------------------------------- +// A helper for the single-coordinate/distance transformation + +namespace +{ + +template struct long_coord; + +template<> struct long_coord +{ + typedef int64_t type; + static type rounded (double v) + { + return type (v > 0 ? v + 0.5 : v - 0.5); + } +}; + +template<> struct long_coord +{ + typedef int64_t type; + static type rounded (double v) + { + return type (v > 0 ? v + 0.5 : v - 0.5); + } +}; + +template<> struct long_coord +{ + typedef double type; + static type rounded (double v) + { + return v; + } +}; + +} + // --------------------------------------------------------------- // simple_trans binding @@ -111,6 +148,11 @@ struct trans_defs *trans = C (trans->angle (), mirror, trans->disp ()); } + static typename long_coord::type trans_coord (const C * /*t*/, typename long_coord::type c) + { + return long_coord::rounded (double (c)); + } + static db::edge trans_edge (const C *t, const db::edge &edge) { return edge.transformed (*t); @@ -219,18 +261,18 @@ struct trans_defs "\n" "@return The inverted transformation\n" ) + - method ("ctrans|*", &C::ctrans, arg ("d"), - "@brief Transforms a distance\n" + method_ext ("ctrans|*", &trans_coord, arg ("d"), + "@brief Transforms a single distance\n" "\n" "The \"ctrans\" method transforms the given distance.\n" - "e = t(d). For the simple transformations, there\n" - "is no magnification and no modification of the distance\n" - "therefore.\n" + "This is equivalent to multiplying with the magnification. For the simple transformations, there\n" + "is no magnification and no modification of the distance.\n" "\n" "@param d The distance to transform\n" "@return The transformed distance\n" "\n" - "The product '*' has been added as a synonym in version 0.28." + "The product '*' has been added as a synonym in version 0.28. " + "The distance can be signed since version 0.29.3." ) + method ("trans|*", (point_type (C::*) (const point_type &) const) &C::trans, arg ("p"), "@brief Transforms a point\n" @@ -604,6 +646,11 @@ struct cplx_trans_defs return new C (mag, r, mirrx, displacement_type (x, y)); } + static typename long_coord::type trans_coord (const C *t, typename long_coord::type c) + { + return long_coord::rounded (t->mag () * double (c)); + } + static simple_trans_type s_trans (const C *cplx_trans) { return simple_trans_type (db::complex_trans (*cplx_trans)); @@ -729,18 +776,18 @@ struct cplx_trans_defs "\n" "@return The inverted transformation\n" ) + - method ("ctrans|*", &C::ctrans, arg ("d"), - "@brief Transforms a distance\n" + method_ext ("ctrans|*", &trans_coord, arg ("d"), + "@brief Transforms a single distance\n" "\n" "The \"ctrans\" method transforms the given distance.\n" - "e = t(d). For the simple transformations, there\n" - "is no magnification and no modification of the distance\n" - "therefore.\n" + "This is equivalent to multiplying with the magnification. For the simple transformations, there\n" + "is no magnification and no modification of the distance.\n" "\n" "@param d The distance to transform\n" "@return The transformed distance\n" "\n" - "The product '*' has been added as a synonym in version 0.28." + "The product '*' has been added as a synonym in version 0.28. " + "The distance can be signed since version 0.29.3." ) + method ("trans|*", (target_point_type (C::*) (const point_type &) const) &C::trans, arg ("p"), "@brief Transforms a point\n" diff --git a/testdata/ruby/dbTransTest.rb b/testdata/ruby/dbTransTest.rb index b5d6f3444..9d669e4b0 100644 --- a/testdata/ruby/dbTransTest.rb +++ b/testdata/ruby/dbTransTest.rb @@ -81,7 +81,9 @@ class DBTrans_TestClass < TestBase assert_equal( RBA::Trans::new(RBA::Trans::R180).to_s, "r180 0,0" ) assert_equal( e.ctrans( 2.0 ), 2.0 ) + assert_equal( e.ctrans( -2.0 ), -2.0 ) assert_equal( e * 2.0, 2.0 ) + assert_equal( e * -2.0, -2.0 ) assert_equal( e.trans( RBA::Edge::new(0, 1, 2, 3) ).to_s, "(-3,-2;-1,0)" ) assert_equal( ( e * RBA::Edge::new(0, 1, 2, 3) ).to_s, "(-3,-2;-1,0)" ) assert_equal( e.trans( RBA::Box::new(0, 1, 2, 3) ).to_s, "(-3,-2;-1,0)" ) @@ -142,9 +144,13 @@ class DBTrans_TestClass < TestBase assert_equal( mb.trans( RBA::DPoint::new( 1, 0 )).to_s, "17,3" ) assert_equal( mb.ctrans(2).to_s, "4.0" ) + assert_equal( mb.ctrans(-2).to_s, "-4.0" ) assert_equal( (mb * 2).to_s, "4.0" ) + assert_equal( (mb * -2).to_s, "-4.0" ) assert_equal( i.ctrans(2).to_s, "1.0" ) + assert_equal( i.ctrans(-2).to_s, "-1.0" ) assert_equal( (i * 2).to_s, "1.0" ) + assert_equal( (i * -2).to_s, "-1.0" ) end @@ -203,7 +209,9 @@ class DBTrans_TestClass < TestBase assert_equal( (c.angle - 45).abs < 1e-10, true ) assert_equal( c.ctrans( 5 ).to_s, "3.75" ) + assert_equal( c.ctrans( -5 ).to_s, "-3.75" ) assert_equal( (c * 5).to_s, "3.75" ) + assert_equal( (c * -5).to_s, "-3.75" ) assert_equal( c.trans( RBA::DPoint::new( 12, 16 ) ).to_s, "17.3492424049,-14.6213203436" ) assert_equal( RBA::DCplxTrans::new.to_s, "r0 *1 0,0" ) @@ -270,6 +278,11 @@ class DBTrans_TestClass < TestBase c.mirror = true assert_equal( c.to_s, "m135 1,7" ) + assert_equal( e.ctrans( 2 ), 2 ) + assert_equal( e.ctrans( -2 ), -2 ) + assert_equal( e * 2, 2 ) + assert_equal( e * -2, -2 ) + assert_equal( e.trans( RBA::Edge::new(0, 1, 2, 3) ).to_s, "(-3,-2;-1,0)" ) assert_equal( ( e * RBA::Edge::new(0, 1, 2, 3) ).to_s, "(-3,-2;-1,0)" ) assert_equal( e.trans( RBA::Box::new(0, 1, 2, 3) ).to_s, "(-3,-2;-1,0)" ) @@ -311,9 +324,13 @@ class DBTrans_TestClass < TestBase assert_equal( mb.trans( RBA::Point::new( 1, 0 )).to_s, "17,3" ) assert_equal( mb.ctrans(2).to_s, "4.0" ) + assert_equal( mb.ctrans(-2).to_s, "-4.0" ) assert_equal( (mb * 2).to_s, "4.0" ) + assert_equal( (mb * -2).to_s, "-4.0" ) assert_equal( i.ctrans(2).to_s, "1.0" ) + assert_equal( i.ctrans(-2).to_s, "-1.0" ) assert_equal( (i * 2).to_s, "1.0" ) + assert_equal( (i * -2).to_s, "-1.0" ) end @@ -360,7 +377,9 @@ class DBTrans_TestClass < TestBase assert_equal( (c.angle - 45).abs < 1e-10, true ) assert_equal( c.ctrans( 5 ).to_s, "3.75" ) + assert_equal( c.ctrans( -5 ).to_s, "-3.75" ) assert_equal( (c * 5).to_s, "3.75" ) + assert_equal( (c * -5).to_s, "-3.75" ) assert_equal( c.trans( RBA::Point::new( 12, 16 ) ).to_s, "17.3492424049,-14.6213203436" ) assert_equal( RBA::CplxTrans::new.to_s, "r0 *1 0,0" )