如何跟踪移动的svg元素相对于固定的svg元素的位置? [英] How do I track the position of a moving svg element in relationship to a fixed svg element?

查看:116
本文介绍了如何跟踪移动的svg元素相对于固定的svg元素的位置?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在一个项目中,该项目使svg文件的元素在水平线上上下移动.我想跟踪移动元素相对于固定线的位置.这两个元素都在同一个svg中.我尝试使用

I am working on a project that moves elements of an svg file up and down across a horizontal line. I want to track the position of the moving element in relation to the fixed line. Both elements are within the same svg. I tried using

getBoundingClientRect().top

但是,由于getBoundingClientRect()函数产生的坐标根据视口的大小,位置和缩放而变化,因此,这并不是一个好的解决方案.在每种情况下,每种设备的情况都不相同.我需要能够知道一条特定路径何时在固定线以上或以下.我在包含组上使用setAttribute('transform','translate())在我的项目中移动一组对象.我需要知道单个对象在组中相对于不在组中的固定线的位置.

However, this does not provide a good solution as the coordinates produced by the getBoundingClientRect() function change based on the size, position, and zoom, of the viewport. It is not the same for every device in every situation. I need to be able to know when a specific path is a certain distance above or below a fixed line. I'm using setAttribute('transform','translate()) on the containing group to move a group of objects in my project. I need to know the position of an individual object within my group in relation to a fixed line not in my group.

<svg version="1.1" id="ex1-3rds-quarter-s" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px"
 y="0px" width="323.333px" height="55.333px" viewBox="0 0 323.333 55.333" enable-background="new 0 0 323.333 55.333"
 xml:space="preserve">
  <g id="ledgerlines">
    <line id="MidCLine1" fill="none" stroke="#000000" stroke-width="0.75" stroke-miterlimit="10" x1="48.09" y1="41.694" x2="57.924" y2="41.694"/>
  </g>
  <g id="note1">
    <path class="root" d="M54.113,38.945c1.116,0,2.172,0.578,2.172,1.813c0,1.435-1.116,2.411-2.052,2.969c-0.717,0.418-1.514,0.717-2.331,0.717
            c-1.116,0-2.172-0.578-2.172-1.813c0-1.435,1.116-2.411,2.052-2.969C52.499,39.244,53.296,38.945,54.113,38.945z"/>
    <path d="M54.113,33.963c1.116,0,2.172,0.578,2.172,1.813c0,1.435-1.116,2.411-2.052,2.969c-0.717,0.418-1.514,0.717-2.331,0.717
            c-1.116,0-2.172-0.578-2.172-1.813c0-1.435,1.116-2.411,2.052-2.969C52.499,34.262,53.296,33.963,54.113,33.963z"/>
  </g>
</svg>

有没有一种方法可以在不使用getBoundingClientRect()函数的情况下跟踪路径的位置?

Is there a way to track the position of the path without using the getBoundingClientRect() function?

谢谢, --christopher

Thanks, --christopher

推荐答案

尝试将路径放置在svg包装器/空"元素中.然后使用getBBox()作为包装器.这将提供用于设置/读取路径转换的x,y值.

Try placing your path in an svg 'wrapper/empty' element. Then use getBBox() for the wrapper. This will provide x,y values used to set/read the path's translations.

我在下面提供了一个示例,该示例可以在参考线之间移动矩形.即使rect已预先转换,这也可以工作.这使用单个SVG包装器.注意:如果只打算一次变换元素,则不必在bbx,bby值上使用矩阵变换.它们可以直接使用.

I have included an example below that can move rects between reference lines. This works even when the rect has been previously transformed. This uses a single SVG Wrapper. Note: If you are only going to transform your element a single time, then you do not have to use the matrix transform on the bbx, bby values. they can be used directly.

<!DOCTYPE html>
    <html xmlns="http://www.w3.org/1999/xhtml">
        <head>
        <title>SVG Wrapper</title>
        <meta http-equiv="content-type" content="text/html; charset=UTF-8">
        </head>
        <body style='font-family:arial'>
            <center>
            <h4>SVG Wrapper</h4>
            <div style='width:90%;background-color:gainsboro;text-align:justify;padding:10px;border-radius:6px;'>
           Translate rects to line via SVG Wrapper. Can translate between lines
            </div>
            <div id="svgDiv" style='background-color:gainsboro;width:400px;height:400px;'>
<svg id="mySVG" width="400" height="400">
<line id=refLine1 stroke='blue' stroke-width='2' x1=20 y1=40 x2=380 y2=40 />
<line id=refLine2 stroke='maroon' stroke-width='2' x1=20 y1=100 x2=380 y2=100 />
<g id=rectG>
<rect id=redRect fill=red x=60 y=200 width=100 height=50 />
<rect id=greenRect fill=lime x=260 y=320 width=100 height=50 />
</g>
<svg id=Wrapper />
</svg>
            </div>
<center>
<button onClick=moveToLine(refLine1,redRect)>Move Red Rect to <span style=color:blue>Line 1</span></button>
<button onClick=moveToLine(refLine1,greenRect)>Move Green Rect to <span style=color:blue>Line 1</span></button>
<br />
<button onClick=moveToLine(refLine2,redRect)>Move Red Rect to <span style=color:maroon>Line 2</span></button>
<button onClick=moveToLine(refLine2,greenRect)>Move Green Rect to <span style=color:maroon>Line 2</span></button>
</center>
            <br />SVG Source:<br />
            <textarea id=svgSourceValue style='font-size:110%;font-family:lucida console;width:90%;height:200px'></textarea>
            <br />Javascript:<br />
            <textarea id=jsValue style='border-radius:26px;font-size:110%;font-weight:bold;color:midnightblue;padding:16px;background-color:beige;border-width:0px;font-size:100%;font-family:lucida console;width:90%;height:400px'></textarea>
            </center>
            <div id='browserDiv' style='padding:5px;position:absolute;top:5px;left:5px;background-color:gainsboro;'>OK in:IE11/CH32/FF28<br /></div>
<script id=myScript>
function moveToLine(refLine,rect)
{
    //---move rect to this location at line---
    var targetY=refLine.y1.baseVal.value
    var targetX=rect.x.baseVal.value
    Wrapper.appendChild(rect)
    var bb=Wrapper.getBBox()
    //---return rect to its <g>---
    rectG.appendChild(rect)
    var bbx=bb.x
    var bby=bb.y

    //---bind wrapper x,y to rect's current transform--
    var pnt = mySVG.createSVGPoint();
    pnt.x = bbx;
    pnt.y = bby;
    var sCTM = rect.getCTM();
    PNT = pnt.matrixTransform(sCTM.inverse());
    //---translate rect's x,y to target---
    var transX=targetX-PNT.x
    var transY=targetY-PNT.y

    rect.setAttribute("transform","translate("+transX+" "+transY+")")

    svgSourceValue.value=svgDiv.innerHTML
}

</script>
            <script>
            document.addEventListener("onload",init(),false)
            function init()
            {
                svgSourceValue.value=svgDiv.innerHTML
                jsValue.value=myScript.text
            }
            </script>
        </body>
    </html>

这篇关于如何跟踪移动的svg元素相对于固定的svg元素的位置?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆