x 和 y 在设置 Transform() 后获得附加值
x and y get added additional value after setting Transform()
我正在研究 svg 自由变换。一切正常,除非对象在页面初始化后有自己的带有缩放值的转换属性。
像这样:
<g transform="matrix(1.5,0,0,1.5,70,70)"></g>
下面是我对这个对象进行拖动和调整大小的操作
var newTransform = 't' + (this.data('xy').x) + ',' + (this.data('xy').y);
newTransform += 'r' + (this.data('r'))
newTransform += 's' + (this.data('s'))
this.transform(newTransform);
如果对象没有初始比例值,这可以正常工作,除非。可以完美地拖动和缩放对象。
但是,如果对象一开始就有缩放属性(不等于1),当我设置第一个transform()时,对象会再次缩放。将添加额外的 x、y 和大小。如果我改用矩阵,问题就可以解决。但是对象不会从中心缩放。
用矩阵变换:
var t = new Snap.Matrix()
t.add(this.data('s'),0,0,this.data('s'),this.data('xy').x,this.data('xy').y);
this.transform(t);
我在使用 snap svg 字符串进行转换时做错了什么吗?如何防止第一次转换 (str) 缩放两次?
这可能会变得相当复杂。如果可以合并,最简单的方法是将要拖动的元素放在 g/group 元素内。然后将拖动放在那个外部 g/group 元素上。
这会保留内部元素上的现有转换,并且不会变得混乱。所以如果你可以在 svg 中包含一个额外的组元素,我会走这条路。
如果您出于任何原因不能。我认为从长远来看(特别是如果您将进行包括动态旋转等在内的自由变换),那么我认为您需要变得更加复杂。我包括了一条我可能会使用的起始路线,它也将能够应对缩放的 viewbox/screen,因为这会带来额外的复杂性。
所以我可能会介绍一些新方法...
getCursorPoint 获取鼠标的实际点,说明屏幕上的任何变换(与元素相对)。我不确定您在具体示例中是否需要这个,但是您稍后可能会发现使用放大的纸张或其他东西遇到了这个问题。
getTransformedDrag,考虑拖动时的任何屏幕转换。
Element.prototype.getCursorPoint = function( x, y ) {
var pt = this.paper.node.createSVGPoint();
pt.x = x; pt.y = y;
return pt.matrixTransform( this.paper.node.getScreenCTM().inverse() );
}
Element.prototype.getTransformedDrag = function( otx, oty, x, y ) {
var xy = this.getCursorPoint( x, y );
var tdx = {};
var snapInvMatrix = this.data('origTransform').invert();
snapInvMatrix.e = snapInvMatrix.f = 0;
tdx.x = snapInvMatrix.x( xy.x - otx, xy.y - oty );
tdx.y = snapInvMatrix.y( xy.x - otx, xy.y - oty );
return tdx;
}
现在我们有一些关于拖动的背景绒毛,我们可以将它们插入到一些元素拖动中....
存储可能的屏幕变换光标位置和元素上的初始矩阵。
var dragStart = function(x, y, ev) {
this.data('origTransform', this.transform().localMatrix)
var txy = this.getCursorPoint(x,y)
this.data('oxy', {x: txy.x, y: txy.y });
}
var dragMove = function(dx, dy, x, y, ev) {
var tdr = this.getTransformedDrag( this.data('oxy').x, this.data('oxy').y, x, y)
this.data('xy', {
x: tdr.x,
y: tdr.y
})
.updateTransform();
}
Element.prototype.updateTransform = function() {
var newTransform = 't' + (this.data('xy').x) + ',' + (this.data('xy').y);
//newTransform += 'r' + (this.data('r'))
//newTransform += 's' + (this.data('s'))
this.transform(this.data('origTransform').toTransformString() + newTransform )
return this;
}
如前所述,这似乎过于复杂,但我只是想包含一些您以后可能会发现有用的额外代码,因为这是一个相当复杂的领域。所以当你需要的时候就把这个作为参考吧。
我正在研究 svg 自由变换。一切正常,除非对象在页面初始化后有自己的带有缩放值的转换属性。
像这样:
<g transform="matrix(1.5,0,0,1.5,70,70)"></g>
下面是我对这个对象进行拖动和调整大小的操作
var newTransform = 't' + (this.data('xy').x) + ',' + (this.data('xy').y);
newTransform += 'r' + (this.data('r'))
newTransform += 's' + (this.data('s'))
this.transform(newTransform);
如果对象没有初始比例值,这可以正常工作,除非。可以完美地拖动和缩放对象。
但是,如果对象一开始就有缩放属性(不等于1),当我设置第一个transform()时,对象会再次缩放。将添加额外的 x、y 和大小。如果我改用矩阵,问题就可以解决。但是对象不会从中心缩放。
用矩阵变换:
var t = new Snap.Matrix()
t.add(this.data('s'),0,0,this.data('s'),this.data('xy').x,this.data('xy').y);
this.transform(t);
我在使用 snap svg 字符串进行转换时做错了什么吗?如何防止第一次转换 (str) 缩放两次?
这可能会变得相当复杂。如果可以合并,最简单的方法是将要拖动的元素放在 g/group 元素内。然后将拖动放在那个外部 g/group 元素上。
这会保留内部元素上的现有转换,并且不会变得混乱。所以如果你可以在 svg 中包含一个额外的组元素,我会走这条路。
如果您出于任何原因不能。我认为从长远来看(特别是如果您将进行包括动态旋转等在内的自由变换),那么我认为您需要变得更加复杂。我包括了一条我可能会使用的起始路线,它也将能够应对缩放的 viewbox/screen,因为这会带来额外的复杂性。
所以我可能会介绍一些新方法...
getCursorPoint 获取鼠标的实际点,说明屏幕上的任何变换(与元素相对)。我不确定您在具体示例中是否需要这个,但是您稍后可能会发现使用放大的纸张或其他东西遇到了这个问题。
getTransformedDrag,考虑拖动时的任何屏幕转换。
Element.prototype.getCursorPoint = function( x, y ) {
var pt = this.paper.node.createSVGPoint();
pt.x = x; pt.y = y;
return pt.matrixTransform( this.paper.node.getScreenCTM().inverse() );
}
Element.prototype.getTransformedDrag = function( otx, oty, x, y ) {
var xy = this.getCursorPoint( x, y );
var tdx = {};
var snapInvMatrix = this.data('origTransform').invert();
snapInvMatrix.e = snapInvMatrix.f = 0;
tdx.x = snapInvMatrix.x( xy.x - otx, xy.y - oty );
tdx.y = snapInvMatrix.y( xy.x - otx, xy.y - oty );
return tdx;
}
现在我们有一些关于拖动的背景绒毛,我们可以将它们插入到一些元素拖动中....
存储可能的屏幕变换光标位置和元素上的初始矩阵。
var dragStart = function(x, y, ev) {
this.data('origTransform', this.transform().localMatrix)
var txy = this.getCursorPoint(x,y)
this.data('oxy', {x: txy.x, y: txy.y });
}
var dragMove = function(dx, dy, x, y, ev) {
var tdr = this.getTransformedDrag( this.data('oxy').x, this.data('oxy').y, x, y)
this.data('xy', {
x: tdr.x,
y: tdr.y
})
.updateTransform();
}
Element.prototype.updateTransform = function() {
var newTransform = 't' + (this.data('xy').x) + ',' + (this.data('xy').y);
//newTransform += 'r' + (this.data('r'))
//newTransform += 's' + (this.data('s'))
this.transform(this.data('origTransform').toTransformString() + newTransform )
return this;
}
如前所述,这似乎过于复杂,但我只是想包含一些您以后可能会发现有用的额外代码,因为这是一个相当复杂的领域。所以当你需要的时候就把这个作为参考吧。