]> source.dussan.org Git - svg.js.git/commitdiff
Identified transformation code to retire
authorSaivan <savian@me.com>
Sun, 25 Feb 2018 10:36:16 +0000 (21:36 +1100)
committerSaivan <savian@me.com>
Sun, 25 Feb 2018 10:36:16 +0000 (21:36 +1100)
This commit simply identifies some of the code that we will be
retiring in 3.0.0 related to transformations. I have commented
and in some cases removed code that will not be required.

Changes
=======
- Added the new affine composition and decomposition functions
- Commented out code that will be removed in coming commits

src/fx.js
src/helpers.js
src/matrix.js
src/transform.js
src/utilities.js

index 46276ed30162cbe3442a61e14475f6885179b4fc..ed81cc74a28e5eb19ac445823efc724653a3d5c6 100644 (file)
--- a/src/fx.js
+++ b/src/fx.js
@@ -640,35 +640,37 @@ SVG.FX = SVG.invent({
       // animate initialTransformation which has to be chained
       if(s.transforms.length){
 
-        // get initial initialTransformation
-        at = s.initialTransformation
-        for(i = 0, len = s.transforms.length; i < len; i++){
-
-          // get next transformation in chain
-          var a = s.transforms[i]
-
-          // multiply matrix directly
-          if(a instanceof SVG.Matrix){
-
-            if(a.relative){
-              at = at.multiply(new SVG.Matrix().morph(a).at(s.ease(this.pos)))
-            }else{
-              at = at.morph(a).at(s.ease(this.pos))
-            }
-            continue
-          }
-
-          // when transformation is absolute we have to reset the needed transformation first
-          if(!a.relative)
-            a.undo(at.extract())
-
-          // and reapply it after
-          at = at.multiply(a.at(s.ease(this.pos)))
-
-        }
-
-        // set new matrix on element
-        target.matrix(at)
+        // TODO: ANIMATE THE TRANSFORMS
+
+        // // get initial initialTransformation
+        // at = s.initialTransformation
+        // for(i = 0, len = s.transforms.length; i < len; i++){
+        //
+        //   // get next transformation in chain
+        //   var a = s.transforms[i]
+        //
+        //   // multiply matrix directly
+        //   if(a instanceof SVG.Matrix){
+        //
+        //     if(a.relative){
+        //       at = at.multiply(new SVG.Matrix().morph(a).at(s.ease(this.pos)))
+        //     }else{
+        //       at = at.morph(a).at(s.ease(this.pos))
+        //     }
+        //     continue
+        //   }
+        //
+        //   // when transformation is absolute we have to reset the needed transformation first
+        //   if(!a.relative)
+        //     a.undo(at.decompose())
+        //
+        //   // and reapply it after
+        //   at = at.multiply(a.at(s.ease(this.pos)))
+        //
+        // }
+        //
+        // // set new matrix on element
+        // target.matrix(at)
       }
 
       return this
index 9f52431e9adeef6444030225c1e7066cb64d2804..b6c2fe6b6cb2c6b5ba2583676c46108deec9da2e 100644 (file)
@@ -105,14 +105,6 @@ function proportionalSize(element, width, height) {
   }
 }
 
-// Delta transform point
-function deltaTransformPoint(matrix, x, y) {
-  return {
-    x: x * matrix.a + y * matrix.c + 0
-  , y: x * matrix.b + y * matrix.d + 0
-  }
-}
-
 // Map matrix array to object
 function arrayToMatrix(a) {
   return { a: a[0], b: a[1], c: a[2], d: a[3], e: a[4], f: a[5] }
@@ -209,3 +201,18 @@ function idFromReference(url) {
 
 // Create matrix array for looping
 var abcdef = 'abcdef'.split('')
+
+// Gets the distance of a point (a, b) from the origin
+function mag (a, b) {
+  return Math.sqrt(a * a + b * b)
+}
+
+// Given a coordinate (a, b), this will calculate the sin, cosine and angle
+// of this point projected onto the unit circle directly
+function unitCircle (a, b) {
+  var len = Math.sqrt(a * a + b * b)
+    , cos = a / len
+    , sin = b / len
+    , theta = Math.atan2(b, a) * 180 / Math.PI
+  return {theta: theta, cos: cos, sin: sin}
+}
index 4f358bace15c4dab4ceca3bb312edeaaf731f98b..e83fce6be137e7dddc3711c8cbb292a005fb6887 100644 (file)
@@ -23,33 +23,85 @@ SVG.Matrix = SVG.invent({
 
   // Add methods
 , extend: {
-    // Extract individual transformations
-    extract: function() {
-      // find delta transform points
-      var px    = deltaTransformPoint(this, 0, 1)
-        , py    = deltaTransformPoint(this, 1, 0)
-        , skewX = 180 / Math.PI * Math.atan2(px.y, px.x) - 90
-
+    // Convert an array of affine parameters into a matrix
+    compose: function (o, cx, cy) {
+
+      // Set the defaults
+      var tx = o.translateX || 0
+        , ty = o.translateY || 0
+        , theta = o.theta || 0
+        , sx = o.scaleX || 1
+        , sy = o.scaleY || 1
+        , lam = o.shear || 0
+        , cx = cx || 0
+        , cy = cy || 0
+
+      // Calculate the trigonometric values
+      var ct = Math.cos(theta * Math.PI / 180)
+        , st Math.sin(theta * Math.PI / 180)
+
+      // Calculate the matrix components directly
+      var a = sx * ct
+        , b = sx * st
+        , c = lam * sx * ct - sy * st
+        , d = lam * sx * st + sy * ct
+        , e = - sx * ct * (cx + cy * lam) + sy * st * cy + tx + cx
+        , f = - sx * st * (cx + cy * lam) - sy * ct * cy + ty + cy
+
+      // Construct a new matrix and return it
+      var matrix = new SVG.Matrix([a, b, c, d, e, f])
+      return matrix
+    }
+    // Decompose a matrix into the affine parameters needed to form it
+  ,  decompose: function (matrix, cx, cy) {
+
+      // Get the paramaters of the current matrix
+      var a = matrix.a
+        , b = matrix.b
+        , c = matrix.c
+        , d = matrix.d
+        , e = matrix.e
+        , f = matrix.f
+
+      // Project the first basis vector onto the unit circle
+      var circle = unitCircle (a, b)
+        , theta = circle.theta
+        , ct = circle.cos
+        , st = circle.sin
+
+      // Work out the transformation parameters
+      var signX = Math.sign(a * ct + b * st)
+        , sx = signX * mag (a, b)
+        , lam = (st * d + ct * c) / (ct * a + st * b)
+        , signY = Math.sign(- c * st + d * ct)
+        , sy = mag (lam * a - c, d - lam * b)
+        , tx = e - cx + cx * ct * sx + cy * (lam * ct * sx - st * sy)
+        , ty = f - cy + cx * st * sx + cy * (lam * st * sx + ct * sy)
+
+      // Package and return the parameters
       return {
-        // translation
-        x:        this.e
-      , y:        this.f
-      , transformedX:(this.e * Math.cos(skewX * Math.PI / 180) + this.f * Math.sin(skewX * Math.PI / 180)) / Math.sqrt(this.a * this.a + this.b * this.b)
-      , transformedY:(this.f * Math.cos(skewX * Math.PI / 180) + this.e * Math.sin(-skewX * Math.PI / 180)) / Math.sqrt(this.c * this.c + this.d * this.d)
-        // skew
-      , skewX:    -skewX
-      , skewY:    180 / Math.PI * Math.atan2(py.y, py.x)
-        // scale
-      , scaleX:   Math.sqrt(this.a * this.a + this.b * this.b)
-      , scaleY:   Math.sqrt(this.c * this.c + this.d * this.d)
-        // rotation
-      , rotation: skewX
+
+        // Bundle the affine parameters
+        translateX: tx
+      , translateY: ty
+      , theta: theta
+      , scaleX: sx
+      , scaleY: sy
+      , shear: lam
+
+      // Bundle the matrix parameters
       , a: this.a
       , b: this.b
       , c: this.c
       , d: this.d
       , e: this.e
       , f: this.f
+
+      // Return the new origin point
+      , x: this.e
+      , y: this.f
+
+      // Store the matrix
       , matrix: new SVG.Matrix(this)
       }
     }
index b7386030e6b98624359b9dd6b57a21a0db4debb0..548ac61f8560eda101f660c52945fcbb52eff0d2 100644 (file)
 SVG.extend(SVG.Element, {
   // Add transformations
   transform: function(o, relative) {
-    // get target in case of the fx module, otherwise reference this
+
+    // Get target in case of the fx module, otherwise reference this
     var target = this
       , matrix, bbox
 
-    // act as a getter
+    // Act as a getter if no object was passed
     if (typeof o !== 'object') {
-      // get current matrix
-      matrix = new SVG.Matrix(target).extract()
 
+      matrix = new SVG.Matrix(target).extract()
       return typeof o === 'string' ? matrix[o] : matrix
-    }
 
-    // get current matrix
-    matrix = new SVG.Matrix(target)
-
-    // ensure relative flag
-    relative = !!relative || !!o.relative
-
-    // act on matrix
-    if (o.a != null) {
-      matrix = relative ?
-        // relative
-        matrix.multiply(new SVG.Matrix(o)) :
-        // absolute
-        new SVG.Matrix(o)
-
-    // act on rotation
-    } else if (o.rotation != null) {
-      // ensure centre point
-      ensureCentre(o, target)
-
-      // apply transformation
-      matrix = relative ?
-        // relative
-        matrix.rotate(o.rotation, o.cx, o.cy) :
-        // absolute
-        matrix.rotate(o.rotation - matrix.extract().rotation, o.cx, o.cy)
-
-    // act on scale
-    } else if (o.scale != null || o.scaleX != null || o.scaleY != null) {
-      // ensure centre point
-      ensureCentre(o, target)
-
-      // ensure scale values on both axes
-      o.scaleX = o.scale != null ? o.scale : o.scaleX != null ? o.scaleX : 1
-      o.scaleY = o.scale != null ? o.scale : o.scaleY != null ? o.scaleY : 1
-
-      if (!relative) {
-        // absolute; multiply inversed values
-        var e = matrix.extract()
-        o.scaleX = o.scaleX * 1 / e.scaleX
-        o.scaleY = o.scaleY * 1 / e.scaleY
-      }
-
-      matrix = matrix.scale(o.scaleX, o.scaleY, o.cx, o.cy)
-
-    // act on skew
-    } else if (o.skew != null || o.skewX != null || o.skewY != null) {
-      // ensure centre point
-      ensureCentre(o, target)
-
-      // ensure skew values on both axes
-      o.skewX = o.skew != null ? o.skew : o.skewX != null ? o.skewX : 0
-      o.skewY = o.skew != null ? o.skew : o.skewY != null ? o.skewY : 0
-
-      if (!relative) {
-        // absolute; reset skew values
-        var e = matrix.extract()
-        matrix = matrix.multiply(new SVG.Matrix().skew(e.skewX, e.skewY, o.cx, o.cy).inverse())
-      }
-
-      matrix = matrix.skew(o.skewX, o.skewY, o.cx, o.cy)
-
-    // act on flip
-    } else if (o.flip) {
-      if(o.flip == 'x' || o.flip == 'y') {
-        o.offset = o.offset == null ? target.bbox()['c' + o.flip] : o.offset
-      } else {
-        if(o.offset == null) {
-          bbox = target.bbox()
-          o.flip = bbox.cx
-          o.offset = bbox.cy
-        } else {
-          o.flip = o.offset
-        }
-      }
-
-      matrix = new SVG.Matrix().flip(o.flip, o.offset)
-
-    // act on translate
-    } else if (o.x != null || o.y != null) {
-      if (relative) {
-        // relative
-        matrix = matrix.translate(o.x, o.y)
-      } else {
-        // absolute
-        if (o.x != null) matrix.e = o.x
-        if (o.y != null) matrix.f = o.y
-      }
-    }
+    // If an object was passed, then we should apply the transformations
+    } else {
 
-    return this.attr('transform', matrix)
-  }
-})
+      // Get the bounding box to use in our calculations
+      var bbox = target.bbox()
+
+      // Extract the parameters for the affine transform
+      var cx = (o.origin && o.origin.length) ?
 
-SVG.extend(SVG.FX, {
-  transform: function(o, relative) {
-    // get target in case of the fx module, otherwise reference this
-    var target = this.target()
-      , matrix, bbox
 
-    // act as a getter
-    if (typeof o !== 'object') {
-      // get current matrix
-      matrix = new SVG.Matrix(target).extract()
 
-      return typeof o === 'string' ? matrix[o] : matrix
-    }
 
-    // ensure relative flag
-    relative = !!relative || !!o.relative
-
-    // act on matrix
-    if (o.a != null) {
-      matrix = new SVG.Matrix(o)
-
-    // act on rotation
-    } else if (o.rotation != null) {
-      // ensure centre point
-      ensureCentre(o, target)
-
-      // apply transformation
-      matrix = new SVG.Rotate(o.rotation, o.cx, o.cy)
-
-    // act on scale
-    } else if (o.scale != null || o.scaleX != null || o.scaleY != null) {
-      // ensure centre point
-      ensureCentre(o, target)
-
-      // ensure scale values on both axes
-      o.scaleX = o.scale != null ? o.scale : o.scaleX != null ? o.scaleX : 1
-      o.scaleY = o.scale != null ? o.scale : o.scaleY != null ? o.scaleY : 1
-
-      matrix = new SVG.Scale(o.scaleX, o.scaleY, o.cx, o.cy)
-
-    // act on skew
-    } else if (o.skewX != null || o.skewY != null) {
-      // ensure centre point
-      ensureCentre(o, target)
-
-      // ensure skew values on both axes
-      o.skewX = o.skewX != null ? o.skewX : 0
-      o.skewY = o.skewY != null ? o.skewY : 0
-
-      matrix = new SVG.Skew(o.skewX, o.skewY, o.cx, o.cy)
-
-    // act on flip
-    } else if (o.flip) {
-      if(o.flip == 'x' || o.flip == 'y') {
-        o.offset = o.offset == null ? target.bbox()['c' + o.flip] : o.offset
-      } else {
-        if(o.offset == null) {
-          bbox = target.bbox()
-          o.flip = bbox.cx
-          o.offset = bbox.cy
-        } else {
-          o.flip = o.offset
-        }
-      }
-
-      matrix = new SVG.Matrix().flip(o.flip, o.offset)
-
-    // act on translate
-    } else if (o.x != null || o.y != null) {
-      matrix = new SVG.Translate(o.x, o.y)
     }
 
-    if(!matrix) return this
 
-    matrix.relative = relative
 
-    this.last().transforms.push(matrix)
 
-    return this._callStart()
+
+
+
+
+
+
+
+
+
+    //
+    // // get current matrix
+    // matrix = new SVG.Matrix(target)
+    //
+    // // ensure relative flag
+    // relative = !!relative || !!o.relative
+    //
+    // // act on matrix
+    // if (o.a != null) {
+    //   matrix = relative ?
+    //     // relative
+    //     matrix.multiply(new SVG.Matrix(o)) :
+    //     // absolute
+    //     new SVG.Matrix(o)
+    //
+    // // act on rotation
+    // } else if (o.rotation != null) {
+    //   // ensure centre point
+    //   ensureCentre(o, target)
+    //
+    //   // apply transformation
+    //   matrix = relative ?
+    //     // relative
+    //     matrix.rotate(o.rotation, o.cx, o.cy) :
+    //     // absolute
+    //     matrix.rotate(o.rotation - matrix.extract().rotation, o.cx, o.cy)
+    //
+    // // act on scale
+    // } else if (o.scale != null || o.scaleX != null || o.scaleY != null) {
+    //   // ensure centre point
+    //   ensureCentre(o, target)
+    //
+    //   // ensure scale values on both axes
+    //   o.scaleX = o.scale != null ? o.scale : o.scaleX != null ? o.scaleX : 1
+    //   o.scaleY = o.scale != null ? o.scale : o.scaleY != null ? o.scaleY : 1
+    //
+    //   if (!relative) {
+    //     // absolute; multiply inversed values
+    //     var e = matrix.extract()
+    //     o.scaleX = o.scaleX * 1 / e.scaleX
+    //     o.scaleY = o.scaleY * 1 / e.scaleY
+    //   }
+    //
+    //   matrix = matrix.scale(o.scaleX, o.scaleY, o.cx, o.cy)
+    //
+    // // act on skew
+    // } else if (o.skew != null || o.skewX != null || o.skewY != null) {
+    //   // ensure centre point
+    //   ensureCentre(o, target)
+    //
+    //   // ensure skew values on both axes
+    //   o.skewX = o.skew != null ? o.skew : o.skewX != null ? o.skewX : 0
+    //   o.skewY = o.skew != null ? o.skew : o.skewY != null ? o.skewY : 0
+    //
+    //   if (!relative) {
+    //     // absolute; reset skew values
+    //     var e = matrix.extract()
+    //     matrix = matrix.multiply(new SVG.Matrix().skew(e.skewX, e.skewY, o.cx, o.cy).inverse())
+    //   }
+    //
+    //   matrix = matrix.skew(o.skewX, o.skewY, o.cx, o.cy)
+    //
+    // // act on flip
+    // } else if (o.flip) {
+    //   if(o.flip == 'x' || o.flip == 'y') {
+    //     o.offset = o.offset == null ? target.bbox()['c' + o.flip] : o.offset
+    //   } else {
+    //     if(o.offset == null) {
+    //       bbox = target.bbox()
+    //       o.flip = bbox.cx
+    //       o.offset = bbox.cy
+    //     } else {
+    //       o.flip = o.offset
+    //     }
+    //   }
+    //
+    //   matrix = new SVG.Matrix().flip(o.flip, o.offset)
+    //
+    // // act on translate
+    // } else if (o.x != null || o.y != null) {
+    //   if (relative) {
+    //     // relative
+    //     matrix = matrix.translate(o.x, o.y)
+    //   } else {
+    //     // absolute
+    //     if (o.x != null) matrix.e = o.x
+    //     if (o.y != null) matrix.f = o.y
+    //   }
+    // }
+    //
+    // return this.attr('transform', matrix)
   }
 })
 
+SVG.extend(SVG.FX, {
+  transform: function(o, relative) {
+
+
+
+
+  //   // get target in case of the fx module, otherwise reference this
+  //   var target = this.target()
+  //     , matrix, bbox
+  //
+  //   // act as a getter
+  //   if (typeof o !== 'object') {
+  //     // get current matrix
+  //     matrix = new SVG.Matrix(target).extract()
+  //
+  //     return typeof o === 'string' ? matrix[o] : matrix
+  //   }
+  //
+  //   // ensure relative flag
+  //   relative = !!relative || !!o.relative
+  //
+  //   // act on matrix
+  //   if (o.a != null) {
+  //     matrix = new SVG.Matrix(o)
+  //
+  //   // act on rotation
+  //   } else if (o.rotation != null) {
+  //     // ensure centre point
+  //     ensureCentre(o, target)
+  //
+  //     // apply transformation
+  //     matrix = new SVG.Rotate(o.rotation, o.cx, o.cy)
+  //
+  //   // act on scale
+  //   } else if (o.scale != null || o.scaleX != null || o.scaleY != null) {
+  //     // ensure centre point
+  //     ensureCentre(o, target)
+  //
+  //     // ensure scale values on both axes
+  //     o.scaleX = o.scale != null ? o.scale : o.scaleX != null ? o.scaleX : 1
+  //     o.scaleY = o.scale != null ? o.scale : o.scaleY != null ? o.scaleY : 1
+  //
+  //     matrix = new SVG.Scale(o.scaleX, o.scaleY, o.cx, o.cy)
+  //
+  //   // act on skew
+  //   } else if (o.skewX != null || o.skewY != null) {
+  //     // ensure centre point
+  //     ensureCentre(o, target)
+  //
+  //     // ensure skew values on both axes
+  //     o.skewX = o.skewX != null ? o.skewX : 0
+  //     o.skewY = o.skewY != null ? o.skewY : 0
+  //
+  //     matrix = new SVG.Skew(o.skewX, o.skewY, o.cx, o.cy)
+  //
+  //   // act on flip
+  //   } else if (o.flip) {
+  //     if(o.flip == 'x' || o.flip == 'y') {
+  //       o.offset = o.offset == null ? target.bbox()['c' + o.flip] : o.offset
+  //     } else {
+  //       if(o.offset == null) {
+  //         bbox = target.bbox()
+  //         o.flip = bbox.cx
+  //         o.offset = bbox.cy
+  //       } else {
+  //         o.flip = o.offset
+  //       }
+  //     }
+  //
+  //     matrix = new SVG.Matrix().flip(o.flip, o.offset)
+  //
+  //   // act on translate
+  //   } else if (o.x != null || o.y != null) {
+  //     matrix = new SVG.Translate(o.x, o.y)
+  //   }
+  //
+  //   if(!matrix) return this
+  //
+  //   matrix.relative = relative
+  //
+  //   this.last().transforms.push(matrix)
+  //
+  //   return this._callStart()
+  // }
+})
+
 SVG.extend(SVG.Element, {
   // Reset all transformations
   untransform: function() {
@@ -230,141 +260,145 @@ SVG.extend(SVG.Element, {
 
 })
 
-SVG.Transformation = SVG.invent({
-
-  create: function(source, inversed){
-
-    if(arguments.length > 1 && typeof inversed != 'boolean'){
-      return this.constructor.call(this, [].slice.call(arguments))
-    }
-
-    if(Array.isArray(source)){
-      for(var i = 0, len = this.arguments.length; i < len; ++i){
-        this[this.arguments[i]] = source[i]
-      }
-    } else if(typeof source == 'object'){
-      for(var i = 0, len = this.arguments.length; i < len; ++i){
-        this[this.arguments[i]] = source[this.arguments[i]]
-      }
-    }
-
-    this.inversed = false
-
-    if(inversed === true){
-      this.inversed = true
-    }
-
-  }
-
-, extend: {
-
-    arguments: []
-  , method: ''
-
-  , at: function(pos){
-
-      var params = []
-
-      for(var i = 0, len = this.arguments.length; i < len; ++i){
-        params.push(this[this.arguments[i]])
-      }
-
-      var m = this._undo || new SVG.Matrix()
-
-      m = new SVG.Matrix().morph(SVG.Matrix.prototype[this.method].apply(m, params)).at(pos)
-
-      return this.inversed ? m.inverse() : m
-
-    }
-
-  , undo: function(o){
-      for(var i = 0, len = this.arguments.length; i < len; ++i){
-        o[this.arguments[i]] = typeof this[this.arguments[i]] == 'undefined' ? 0 : o[this.arguments[i]]
-      }
-
-      // The method SVG.Matrix.extract which was used before calling this
-      // method to obtain a value for the parameter o doesn't return a cx and
-      // a cy so we use the ones that were provided to this object at its creation
-      o.cx = this.cx
-      o.cy = this.cy
-
-      this._undo = new SVG[capitalize(this.method)](o, true).at(1)
-
-      return this
-    }
-
-  }
-
-})
-
-SVG.Translate = SVG.invent({
-
-  parent: SVG.Matrix
-, inherit: SVG.Transformation
-
-, create: function(source, inversed){
-    this.constructor.apply(this, [].slice.call(arguments))
-  }
-
-, extend: {
-    arguments: ['transformedX', 'transformedY']
-  , method: 'translate'
-  }
-
-})
-
-SVG.Rotate = SVG.invent({
-
-  parent: SVG.Matrix
-, inherit: SVG.Transformation
-
-, create: function(source, inversed){
-    this.constructor.apply(this, [].slice.call(arguments))
-  }
-
-, extend: {
-    arguments: ['rotation', 'cx', 'cy']
-  , method: 'rotate'
-  , at: function(pos){
-      var m = new SVG.Matrix().rotate(new SVG.Number().morph(this.rotation - (this._undo ? this._undo.rotation : 0)).at(pos), this.cx, this.cy)
-      return this.inversed ? m.inverse() : m
-    }
-  , undo: function(o){
-      this._undo = o
-      return this
-    }
-  }
-
-})
-
-SVG.Scale = SVG.invent({
-
-  parent: SVG.Matrix
-, inherit: SVG.Transformation
-
-, create: function(source, inversed){
-    this.constructor.apply(this, [].slice.call(arguments))
-  }
-
-, extend: {
-    arguments: ['scaleX', 'scaleY', 'cx', 'cy']
-  , method: 'scale'
-  }
-
-})
-
-SVG.Skew = SVG.invent({
-
-  parent: SVG.Matrix
-, inherit: SVG.Transformation
-
-, create: function(source, inversed){
-    this.constructor.apply(this, [].slice.call(arguments))
-  }
-
-, extend: {
-    arguments: ['skewX', 'skewY', 'cx', 'cy']
-  , method: 'skew'
-  }
-
-})
+// TODO: DESTROY
+//       =======
+//
+//
+// SVG.Transformation = SVG.invent({
+//
+//   create: function(source, inversed){
+//
+//     if(arguments.length > 1 && typeof inversed != 'boolean'){
+//       return this.constructor.call(this, [].slice.call(arguments))
+//     }
+//
+//     if(Array.isArray(source)){
+//       for(var i = 0, len = this.arguments.length; i < len; ++i){
+//         this[this.arguments[i]] = source[i]
+//       }
+//     } else if(typeof source == 'object'){
+//       for(var i = 0, len = this.arguments.length; i < len; ++i){
+//         this[this.arguments[i]] = source[this.arguments[i]]
+//       }
+//     }
+//
+//     this.inversed = false
+//
+//     if(inversed === true){
+//       this.inversed = true
+//     }
+//
+//   }
+//
+// , extend: {
+//
+//     arguments: []
+//   , method: ''
+//
+//   , at: function(pos){
+//
+//       var params = []
+//
+//       for(var i = 0, len = this.arguments.length; i < len; ++i){
+//         params.push(this[this.arguments[i]])
+//       }
+//
+//       var m = this._undo || new SVG.Matrix()
+//
+//       m = new SVG.Matrix().morph(SVG.Matrix.prototype[this.method].apply(m, params)).at(pos)
+//
+//       return this.inversed ? m.inverse() : m
+//
+//     }
+//
+//   , undo: function(o){
+//       for(var i = 0, len = this.arguments.length; i < len; ++i){
+//         o[this.arguments[i]] = typeof this[this.arguments[i]] == 'undefined' ? 0 : o[this.arguments[i]]
+//       }
+//
+//       // The method SVG.Matrix.extract which was used before calling this
+//       // method to obtain a value for the parameter o doesn't return a cx and
+//       // a cy so we use the ones that were provided to this object at its creation
+//       o.cx = this.cx
+//       o.cy = this.cy
+//
+//       this._undo = new SVG[capitalize(this.method)](o, true).at(1)
+//
+//       return this
+//     }
+//
+//   }
+//
+// })
+//
+// SVG.Translate = SVG.invent({
+//
+//   parent: SVG.Matrix
+// , inherit: SVG.Transformation
+//
+// , create: function(source, inversed){
+//     this.constructor.apply(this, [].slice.call(arguments))
+//   }
+//
+// , extend: {
+//     arguments: ['transformedX', 'transformedY']
+//   , method: 'translate'
+//   }
+//
+// })
+//
+// SVG.Rotate = SVG.invent({
+//
+//   parent: SVG.Matrix
+// , inherit: SVG.Transformation
+//
+// , create: function(source, inversed){
+//     this.constructor.apply(this, [].slice.call(arguments))
+//   }
+//
+// , extend: {
+//     arguments: ['rotation', 'cx', 'cy']
+//   , method: 'rotate'
+//   , at: function(pos){
+//       var m = new SVG.Matrix().rotate(new SVG.Number().morph(this.rotation - (this._undo ? this._undo.rotation : 0)).at(pos), this.cx, this.cy)
+//       return this.inversed ? m.inverse() : m
+//     }
+//   , undo: function(o){
+//       this._undo = o
+//       return this
+//     }
+//   }
+//
+// })
+//
+// SVG.Scale = SVG.invent({
+//
+//   parent: SVG.Matrix
+// , inherit: SVG.Transformation
+//
+// , create: function(source, inversed){
+//     this.constructor.apply(this, [].slice.call(arguments))
+//   }
+//
+// , extend: {
+//     arguments: ['scaleX', 'scaleY', 'cx', 'cy']
+//   , method: 'scale'
+//   }
+//
+// })
+//
+// SVG.Skew = SVG.invent({
+//
+//   parent: SVG.Matrix
+// , inherit: SVG.Transformation
+//
+// , create: function(source, inversed){
+//     this.constructor.apply(this, [].slice.call(arguments))
+//   }
+//
+// , extend: {
+//     arguments: ['skewX', 'skewY', 'cx', 'cy']
+//   , method: 'skew'
+//   }
+//
+// })
index c41e8e41a31d25330240f36712ee5689437fbf2f..e44beac40ef2f58fdc557c12bf54118804cdac93 100644 (file)
@@ -4,10 +4,10 @@ SVG.utils = {
     var i
       , il = array.length
       , result = []
-    
+
     for (i = 0; i < il; i++)
       result.push(block(array[i]))
-    
+
     return result
   }
 
@@ -16,11 +16,11 @@ SVG.utils = {
     var i
       , il = array.length
       , result = []
-    
+
     for (i = 0; i < il; i++)
       if (block(array[i]))
         result.push(array[i])
-    
+
     return result
   }
 
@@ -38,4 +38,4 @@ SVG.utils = {
     return this.filter( nodes, function(el) { return el instanceof window.SVGElement })
   }
 
-}
\ No newline at end of file
+}