我可以获得svg对象的翻译/缩放吗?

时间:2015-05-23 19:25:58

标签: javascript svg

我正在编写一个符号识别服务,我想扩展它以完成公式识别。这允许人们编写公式然后让LaTeX回来。一旦用户完成写作,我就将所写的内容存储为带有模板的SVG

<?xml version="1.0" encoding="UTF-8" standalone="no"?>

<svg
   xmlns:dc="http://purl.org/dc/elements/1.1/"
   xmlns:cc="http://creativecommons.org/ns#"
   xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
   xmlns:svg="http://www.w3.org/2000/svg"
   xmlns="http://www.w3.org/2000/svg"
   version="1.1"
   width="400"
   height="400"
   xml:space="preserve"
   viewBox="0 0 {{ width }} {{ height }}"
   preserveAspectRatio="xMidYMid meet">

{{ path }}
{{ dots }}
</svg>

这包含在

<object data="123456.svg"
        type="image/svg+xml"
        id="canvas"
        style="width:400px;height:400px;border:1px solid black;"></object>

(参见example with old template without centering

现在我有一些JavaScript代码允许用户细分公式。但是当SVG将自身与viewBox / preserveAspectRatio集中在一起时,此代码需要进行调整。

如何获得调整代码的必要值(转换和缩放因子)?

(我发现MDN SVG Svg DOM interface,但是当我将svg包含在对象标记中时,这似乎不起作用。我不能将svg包含在图像标记中,因为我需要处理SVG的内容。)< / p>

1 个答案:

答案 0 :(得分:1)

SVG元素有一个名为getScreenCTM()的函数,它返回用于将SVG空间中的坐标转换为屏幕空间中的坐标的矩阵。

你想做相反的方向。幸运的是,所有SVGMatrix对象都有一个名为inverse()的函数,它会反转矩阵。

您需要做的就是从鼠标事件中取出clientXclientY坐标,然后通过倒置矩阵运行它们。然后,您将获得该点的相应SVG坐标。

<html>

<object data="324196.svg"
        type="image/svg+xml"
        id="canvas"
        style="width:400px;height:400px;border:1px solid black;" onclick="calc()"></object>

</body>

<script>

canvas.addEventListener("load",function(){
   document.getElementById("canvas").contentDocument.addEventListener("click", calc);
});

function calc(evt)
{
    var svg = document.getElementById("canvas").contentDocument.firstChild;

    var  point = svg.createSVGPoint();
    point.x = evt.clientX;
    point.y = evt.clientY;
    point = point.matrixTransform(svg.getScreenCTM().inverse());

    var circle = document.createElementNS("http://www.w3.org/2000/svg", "circle");
    circle.setAttribute("cx", point.x);
    circle.setAttribute("cy", point.y);
    circle.setAttribute("r", "5");
    circle.setAttribute("fill", "red");
    circle.setAttribute("fill-opacity", "0.5");
    svg.appendChild(circle);
}

</script>

</html>