我有一堆使用相同svg路径的对象,基本上是一个箭头。我想将对象放在另一个圆圈的svg路径上,这样箭头看起来就像向外“向外”。
我读了一些文章,说使用<object>
为svg提供了更多控制但我无法找到如何将<object>
定位到另一个svg <object>
路径(圆圈)。< / p>
而不是仅仅手动旋转每个<object>
我想将它们放在一条路径上,以便将来动画它们会更容易。我希望它们在翻转时从中心向外移动一点,我想通过路径而不是手动设置每个箭头的动画,动画会更容易。
我可以像这里一样沿着路径制作动画 http://demo.hongkiat.com/scalable-vector-graphics-animation/ 并通过将“跟随路径”上的路径更改为圆形,但我不想动画,只需定位....
更新:我似乎能够在网上找到一个元素到路径上的唯一东西是animationTransform或沿着路径动画的东西,但我只想沿着另一个元素(路径)定位元素,如下所示: 额外的箭头是我计划将来在翻滚时制作动画的方法......但是现在我很好奇如何定位箭头。我也没有多少,但它是一个开始,我终于工作了。任何帮助表示赞赏!
我只是想,将箭头旋转成带有css3或svg的圆圈会更好吗?
答案 0 :(得分:1)
您的应用程序演示了SVG的动态方面。我希望我的回答不是太冗长:)
创建你的'箭头',使它们的中心/底点位于(0,0) - 这是在将它们放在一个圆圈时使用的,以及用于onmouseover的'hilite / extend'功能。
我建议为每个黑色和灰色箭头使用多边形而不是路径。
然后放在<defs>
中以创建所需的使用元素。
e.g
<defs>
<polygon id="myBlackArrow" points="10,0 -10,0 -10,-80 -15,-80 0,-100 15,-80 10,-80" fill="black" />
<polygon id="myGrayArrow" points="10,0 -10,0 -10,-80 -15,-80 0,-100 15,-80 10,-80" fill="silver" />
</defs>
然后,通过一些Javascript,您可以围绕中心点构建箭头:
var NS="http://www.w3.org/2000/svg"
var xref="http://www.w3.org/1999/xlink"
var centerX=200
var centerY=200
//---every 40 degrees around a center point--
function placeArrowsAroundCircle()
{
for(var k=0;k<9;k++)
{
var rotateAngle=k*40
var grayArrow=document.createElementNS(NS,"use")
grayArrow.setAttributeNS(xref,"href", "#myGrayArrow")
grayArrow.setAttribute("onmouseover", "hilite(evt)")
grayArrow.setAttribute("onmouseout", "unhilite(evt)")
grayArrow.setAttribute("rotateAngle", rotateAngle)
grayArrow.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
mySVG.appendChild(grayArrow)
}
for(var k=0;k<9;k++)
{
var rotateAngle=k*40+20
var blackArrow=document.createElementNS(NS,"use")
blackArrow.setAttributeNS(xref,"href", "#myBlackArrow")
blackArrow.setAttribute("onmouseover", "hilite(evt)")
blackArrow.setAttribute("onmouseout", "unhilite(evt)")
blackArrow.setAttribute("rotateAngle", rotateAngle)
blackArrow.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
mySVG.appendChild(blackArrow)
}
}
鼠标悬停/退出的每个箭头附加的两个功能将延伸/收缩目标箭头(箭头在y方向上缩放为1.3)。
//--onmouseover---
function hilite(evt)
{
//---IE and Chrome---
if(evt.target.correspondingUseElement)
var target=evt.target.correspondingUseElement
else //---FF---
var target=evt.target
var rotateAngle=target.getAttribute("rotateAngle")
target.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")scale(1,1.3)")
}
//---onmouseout--
function unhilite(evt)
{
//---IE and Chrome---
if(evt.target.correspondingUseElement)
var target=evt.target.correspondingUseElement
else //---FF---
var target=evt.target
var rotateAngle=target.getAttribute("rotateAngle")
target.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
}
下面是一个示例,您可以将其放在.htm文档中以查看其是否有效。对IE / CH / FF
进行了测试<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<body>
<center>
<div id="svgDiv" style='background-color:lightblue;width:400px;height:400px;'>
<svg id="mySVG" width="400" height="400">
<defs>
<polygon id="myBlackArrow" points="10,0 -10,0 -10,-80 -15,-80 0,-100 15,-80 10,-80" fill="black" />
<polygon id="myGrayArrow" points="10,0 -10,0 -10,-80 -15,-80 0,-100 15,-80 10,-80" fill="silver" />
</defs>
</svg>
</div>
<button onClick=placeArrowsAroundCircle()>Place Arrows Around Circle</button>
</center>
<script id=myScript>
var NS="http://www.w3.org/2000/svg"
var xref="http://www.w3.org/1999/xlink"
var centerX=200
var centerY=200
//---every 40 degrees around a center point--
//---button---
function placeArrowsAroundCircle()
{
for(var k=0;k<9;k++)
{
var rotateAngle=k*40
var grayArrow=document.createElementNS(NS,"use")
grayArrow.setAttributeNS(xref,"href", "#myGrayArrow")
grayArrow.setAttribute("onmouseover", "hilite(evt)")
grayArrow.setAttribute("onmouseout", "unhilite(evt)")
grayArrow.setAttribute("rotateAngle", rotateAngle)
grayArrow.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
mySVG.appendChild(grayArrow)
}
for(var k=0;k<9;k++)
{
var rotateAngle=k*40+20
var blackArrow=document.createElementNS(NS,"use")
blackArrow.setAttributeNS(xref,"href", "#myBlackArrow")
blackArrow.setAttribute("onmouseover", "hilite(evt)")
blackArrow.setAttribute("onmouseout", "unhilite(evt)")
blackArrow.setAttribute("rotateAngle", rotateAngle)
blackArrow.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
mySVG.appendChild(blackArrow)
}
}
//--onmouseover---
function hilite(evt)
{
//---IE and Chrome---
if(evt.target.correspondingUseElement)
var target=evt.target.correspondingUseElement
else //---FF---
var target=evt.target
var rotateAngle=target.getAttribute("rotateAngle")
target.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")scale(1,1.3)")
}
//---onmouseout--
function unhilite(evt)
{
//---IE and Chrome---
if(evt.target.correspondingUseElement)
var target=evt.target.correspondingUseElement
else //---FF---
var target=evt.target
var rotateAngle=target.getAttribute("rotateAngle")
target.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
}
</script>
</body>
</html>
答案 1 :(得分:1)
这与前一个答案类似,不同之处在于它使用导入的路径作为箭头而不是多边形。
首先,您导入的路径是 humongus ,因此它们对于我的400x400 svg来说太大了。
因此,我必须将它们缩小到适合我的svg的尺寸。我选择80px作为箭头的高度。要做到这一点,我必须得到导入路径的实际大小,我已将其放在一个元素中。我使用getBBox()
执行此操作,如下所示。
//--get actual size---
var bb=importedPaths.getBBox()
var bbx=bb.x
var bby=bb.y
var bbw=bb.width
var bbh=bb.height
//---find the center point of this <g>---
var cx=bbx+.5*bbw
var cy=bby+.5*bbh
//---set desired size, i.e. scale the import--
var heightSize=80
var scale=heightSize/bbh
//---translate so it's bottom is centered is at (0,0)
var transX=(-cx)*scale
var transY=(-cy-.5*bbh)*scale
importedPaths.setAttribute("transform","translate("+transX+" "+transY+")scale("+scale+" "+scale+")")
现在我有这个大小并且位于箭头底部以(0,0)为中心,所以我可以用它来制作符号元素。
我将重新调整大小的导入的副本作为黑色箭头和灰色箭头,并将它们放在<defs>
元素中。 <defs>
用于存储/隐藏用于符号的元素。
//---create your symbol objects from transformed import, by placing <g> in defs--
var blackArrow=importedPaths.cloneNode(true)
blackArrow.id="myBlackArrow"
myDefs.appendChild(blackArrow)
var grayArrow=importedPaths.cloneNode(true)
grayArrow.id="myGrayArrow"
grayArrow.setAttribute("fill","silver")
myDefs.appendChild(grayArrow)
以下是一个html文件,您可以在其中查看此操作。我已经包含了一个textarea,显示了如何创建svg。 (我在左上方留下原始箭头)。注意:在IE和Chrome中正常工作,FF不能完全呈现箭头组。
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<body>
<div style='padding:5px;background-color:gainsboro;'>OK in:IE11/CH32, but FF23 does not fully render arrow in in circle<br /></div>
<br />
<br />
<br />
<center>
<div id=svgDiv style='width:400px;height:400px;background-color:lightgreen'>
<svg id="mySVG" width="400" y="400" overflow="visible" >
<defs id="myDefs">
</defs>
<g id="importedPaths" fill="black"><path d="M2553.826,1137.28l-2.772-1.719l29.799,1445.434l195.02,1.004l9.765-1448.729 c0,0-63.94,42.007-113.36,42.007S2553.826,1137.28,2553.826,1137.28z" /><path d="M2451.84,1058.265c0,0,171.983,75.005,216.505,75.005s188.535-75.005,188.535-75.005l-190.691-366.037 L2451.84,1058.265z" /></g>
</svg>
</div>
<button onClick=placeArrowsAroundCircle()>Place Arrows Around Circle</button><br />
<br />SVG Source:<br />
<textarea id=svgSourceValue style='font-size:110%;font-family:lucida console;width:90%;height:200px'></textarea>
</center>
<script id=myScript>
var NS="http://www.w3.org/2000/svg"
var xref="http://www.w3.org/1999/xlink"
//--place this at the center of this svg---
var centerX=200
var centerY=200
//---every 30 degrees around a center point--
//---button---
function placeArrowsAroundCircle()
{
for(var k=0;k<12;k++)
{
var rotateAngle=k*30
var grayArrow=document.createElementNS(NS,"use")
grayArrow.setAttributeNS(xref,"href", "#myGrayArrow")
grayArrow.setAttribute("onmouseover", "hilite(evt)")
grayArrow.setAttribute("onmouseout", "unhilite(evt)")
grayArrow.setAttribute("rotateAngle", rotateAngle)
grayArrow.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
mySVG.appendChild(grayArrow)
}
for(var k=0;k<12;k++)
{
var rotateAngle=k*30+15 //--offset 15 degrees---
var blackArrow=document.createElementNS(NS,"use")
blackArrow.setAttributeNS(xref,"href", "#myBlackArrow")
blackArrow.setAttribute("onmouseover", "hilite(evt)")
blackArrow.setAttribute("onmouseout", "unhilite(evt)")
blackArrow.setAttribute("rotateAngle", rotateAngle)
blackArrow.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
mySVG.appendChild(blackArrow)
}
svgSourceValue.value=svgDiv.innerHTML
}
//--onmouseover---
function hilite(evt)
{
//---IE and Chrome---
if(evt.target.correspondingUseElement)
var target=evt.target.correspondingUseElement
else //---FF---
var target=evt.target
var rotateAngle=target.getAttribute("rotateAngle")
target.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")scale(1,1.3)")
}
//---onmouseout--
function unhilite(evt)
{
//---IE and Chrome---
if(evt.target.correspondingUseElement)
var target=evt.target.correspondingUseElement
else //---FF---
var target=evt.target
var rotateAngle=target.getAttribute("rotateAngle")
target.setAttribute("transform","translate("+centerX+" "+centerY+")rotate("+rotateAngle+")")
}
document.addEventListener("onload",init(),false)
//---adjust(transform) the imported paths so they fit this svg viewPort---
function init()
{
//--get actual size---
var bb=importedPaths.getBBox()
var bbx=bb.x
var bby=bb.y
var bbw=bb.width
var bbh=bb.height
//---find the center point of this <g>---
var cx=bbx+.5*bbw
var cy=bby+.5*bbh
//---set desired size, i.e. scale the import--
var heightSize=80
var scale=heightSize/bbh
//---translate so it's bottom is centered is at (0,0)
var transX=(-cx)*scale
var transY=(-cy-.5*bbh)*scale
importedPaths.setAttribute("transform","translate("+transX+" "+transY+")scale("+scale+" "+scale+")")
//---create your symbol objects from transformed import, by placing <g> in defs--
var blackArrow=importedPaths.cloneNode(true)
blackArrow.id="myBlackArrow"
myDefs.appendChild(blackArrow)
var grayArrow=importedPaths.cloneNode(true)
grayArrow.id="myGrayArrow"
grayArrow.setAttribute("fill","silver")
myDefs.appendChild(grayArrow)
//---see textarea---
svgSourceValue.value=svgDiv.innerHTML
}
</script>
</body>
</html>