SVG在鼠标拖动时缩放旋转的元素

时间:2019-06-25 12:16:14

标签: javascript svg matrix rotation scale

我正在为我要处理的项目使用svg和矩阵,并且尝试使用香草javascript实现免费转换。到目前为止,我已经可以使用javascript和此库https://www.npmjs.com/package/transformation-matrix#transform进行所有转换,以帮助我处理矩阵。 目前,我的代码仅适用于rect元素,但我认为大部分代码确实会用于具有某些更改的其他元素。

当我尝试缩放旋转的矩形时出现问题。 在我的代码中,当我单击某个元素时,为它提供了围绕该元素的路径,其中一些圆圈代表可以缩放矩形的方向,其中1代表中心,1代表旋转。

正如我所说的,我对任何转换都没有问题,无论是转换旋转/缩放的形状还是其他任何东西,我唯一不知道怎么做的是如何缩放旋转的保持旋转的形状。

如果rect的旋转角度为0,则根据我决定缩放的方向,我只需根据鼠标指针获得新的宽度/高度,然后进行平移和缩放的混合即可。这很好并且按预期工作。 如果rect旋转了,这会折断,我可能会使用我缩放的点与鼠标指针之间有效的欧几里得距离,但实际上不会。所以我有点迷失了。

        const elem = document.getElementById('rect2');
        const x = elem.x.baseVal.value;
        const y = elem.y.baseVal.value;
        const width = elem.width.baseVal.value;
        const height = elem.height.baseVal.value;

        // this is a function that return the mouse coords on the canvas- 
        // svg
        const m = this.getCanvasMousePos(e);

        if(type === 'bottom-center'){
            const newH = (m.y - y) / height;
            const s = scale(1,newH);
            const form = toSVG(s);
            elem.setAttribute('transform', form);
        }else if (type === 'top-center'){
            const newH = (y+height - m.y) / height;
            const s = scale(1,newH);
            const t = translate(0,m.y-y)
            const comp = compose(t,s);
            const form = toSVG(comp);
            elem.setAttribute('transform', form);
        }else if (type === 'middle-left') {
            const newW = (x+width - m.x) / width;
            const s = scale(newW,1);
            const t = translate(m.x-x, 0);
            const comp = compose(t,s)
            const form = toSVG(comp);
            elem.setAttribute('transform', form);
        }else if (type === 'middle-right') {
            const newW = (m.x - x) / width;
            const s = scale(newW,1);
            const form = toSVG(s);
            elem.setAttribute('transform', form);
        }else if (type === 'bottom-right') {
            const newW = (m.x - x) / width;
            const newH = (m.y - y) / height;
            const s = scale(newW,newH);
            const form = toSVG(s);
            elem.setAttribute('transform', form);
        }else if (type === 'bottom-left'){
            const newW = ((x + width) - m.x) / width;
            const newH = (m.y - y) / height;
            const t = translate(m.x - x,0);
            const s = scale(newW,newH);
            const comp = compose(t,s)
            const form = toSVG(comp);
            elem.setAttribute('transform', form);
        }else if (type === 'top-left') {
            const newW = ((x + width) - m.x) / width;
            const newH = ((y + height) - m.y) / height;
            const t = translate(m.x-x,m.y-y);
            const s = scale(newW,newH);
            const comp = compose(t,s)
            const form = toSVG(comp);
            elem.setAttribute('transform', form);
        }else if (type === 'top-right') {
            const newW = (m.x - x) / width;
            const newH = ((y + height) - m.y) / height;
            const t = translate(0,m.y-y);
            const s = scale(newW,newH);
            const comp = compose(t,s)
            const form = toSVG(comp);
            elem.setAttribute('transform', form);
        };

这是非旋转svgs的代码。

希望有人能提供帮助,非常感谢

1 个答案:

答案 0 :(得分:0)

我找到了解决方法。

无论何时旋转形状,都应平移鼠标指针和形状,就好像它们没有旋转一样,请正常进行缩放,然后再平移并最后旋转。我的问题是我在尝试平移之前要旋转!

如果使用此方法,则顺序应为transform(旋转平移比例),因为您输入的最后一个是第一个发生的!