如何在SVG/raphael中在贝塞尔曲线末端绘制箭头?

5

我有一个由以下代码生成的曲线:

    var path = ["M", x1.toFixed(3), y1.toFixed(3), "L", arrow_left_x, arrow_left_y, "L", arrow_right_x, arrow_right_y, "L", x1.toFixed(3), y1.toFixed(3), "C", x2, y2, x3, y3, x4.toFixed(3), y4.toFixed(3)].join(",");

这里输入图片描述

但是我的箭头没有正确完成。
- 它只指向右边,而且不指向贝塞尔曲线端点处的斜率方向。 - 它没有被填充。

现在,我知道我在这里的数学计算不正确,但主要是想知道如何填充线段末端的三角形。谢谢!

仅供演示目的:

        arrow_left_x = (x1 - 8);
        arrow_left_y = (y1 - 8);
        arrow_right_x = (x1 - 8);
        arrow_right_y = (y1 + 8);

那是我使用的获取坐标的代码。

现在Raphael 2.1版本拥有一对路径属性arrow-startarrow-end,详情请见https://dev59.com/KIXca4cB1Zd3GeqPO-Mf。 - user56reinstatemonica8
1个回答

20

我猜你应该使用标记符号来达到你的目的。在这里可以看到一个示例

编辑:

你需要在defs部分创建一个标记符号:

var defs = document.createElementNS('http://www.w3.org/2000/svg', 'defs');
var marker = document.createElementNS('http://www.w3.org/2000/svg', 'marker');
marker.setAttribute('id', 'Triangle');
marker.setAttribute('viewBox', '0 0 16 16');
marker.setAttribute('refX', '0');
marker.setAttribute('refY', '6');
marker.setAttribute('markerUnits', 'strokeWidth');
marker.setAttribute('markerWidth', '16');
marker.setAttribute('markerHeight', '12');
marker.setAttribute('orient', 'auto');
var path = document.createElementNS('http://www.w3.org/2000/svg', 'path');
marker.appendChild(path); 
path.setAttribute('d', 'M 0 0 L 16 8 L 0 16 z');   
path.setAttribute('stroke', '#000');   
path.setAttribute('stroke-width', '1'); 
path.setAttribute('style', '  marker-start :none;   marker-end :none; ');      

document.getElementById( id_of_svg_placeholder ).getElementsByTagName('svg')[0].appendChild(defs);
defs.appendChild(marker);

并在CSS中引用它:

path {marker-start:url("#Triangle")}
或者作为属性:
<path d="..." marker-start="url(#Triangle)" />

这里是生成的 jsfiddle


好的,我现在明白它是如何工作的了。然而,它与Raphael不兼容,因为它使用标签而不是属性。如果您以某种方式编辑您的答案,我会将负投票改为正投票。或者,如果您能够弄清楚如何在这里放置标记:http://jsfiddle.net/G5mTx/10/,那就太棒了。 - NullVoxPopuli
9
我希望这是你所需要的:http://jsfiddle.net/G5mTx/29/。不要害怕使用本地DOM方法。也许是Raphael与创建SVG标记不兼容,而不是反过来。另外,我猜对于一个提供帮助并给出问题关键字的人进行投票反对可能不太友好。 - Spadar Shut
除非您编辑您的答案,否则我无法点赞。=\ 不过那正是我需要的!您太棒了!<3 - NullVoxPopuli
谢谢!这很容易实现到我的新代码中:http://jsfiddle.net/G5mTx/30/ - NullVoxPopuli
10
"对于那些提供帮助的人而言,给他们的回答投下反对票并不是太友善了。" #真实故事 - Necronet
代码行的顺序不正确,应该像这样:var path = document.createElementNS('http://www.w3.org/2000/svg', 'path'); 然后是多行的 path.setAttribute(...); 接着是 marker.appendChild(path); 然后是 defs.appendChild(marker); 最后是 ....getElementsByTagName('svg')[0].appendChild(defs); - TomoMiha

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接