如何制作带有边框的SVG“线条”?

17

我有一个小的SVG小部件,其目的是显示一系列角度(请参见图像)。

现在,这些角度是线元素,只有描边而没有填充。但现在我想要一个“内部填充”颜色和一个“描边/边框”周围。我猜线元素无法处理这个问题,那么我应该使用什么替代品呢?

请注意,线的描边末端是圆形的。我希望在解决方案中保持这种效果。

角度线

<svg height="160" version="1.1" viewBox="-0.6 -0.6 1.2 1.2" width="160" xmlns="http://www.w3.org/2000/svg">
  <g>
    <g>
      <circle class="sensorShape" cx="0" cy="0" fill="#FFF" r="0.4" stroke="black" stroke-width="0.015"/>
      <line stroke="black" stroke-width="0.015" x1="0" x2="0" y1="-0.4" y2="0.4"/>
      <line stroke="black" stroke-width="0.015" x1="-0.4" x2="0.4" y1="0" y2="0"/>
    </g>
    <g class="lsNorthAngleHandsContainer">
      <line data-angle="348" stroke="red" stroke-linecap="round" stroke-width="0.04" transform="rotate(348)" x1="0" x2="0" y1="0" y2="-0.4"/>
      <text font-size="0.08" transform="translate(-0.02316467632710395,-0.45125904029352226)">
        348
      </text>
    </g>
  </g>
</svg>
5个回答

23

新增第二条线,坐标相同但线宽更细:

<g class="lsNorthAngleHandsContainer">
  <line data-angle="348" stroke="red" stroke-linecap="round" stroke-width="0.04" transform="rotate(348)" x1="0" x2="0" y1="0" y2="-0.4"/>
  <line data-angle="348" stroke="yellow" stroke-linecap="round" stroke-width="0.025" transform="rotate(348)" x1="0" x2="0" y1="0" y2="-0.4"/>

5

我发现了一种优雅的解决方案,受到这个示例的启发,可以应用于W3C关于填充和描边的文章。基本上,你需要将路径移动到定义中,并使用该定义来绘制两个元素:

<svg width="200" height="200" viewBox="0 0 100 100">
    <defs>
        <line id="line1" x1="25" x2="75" y1="25" y2="75"/>
    </defs>
    <use xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#line1" class="stroke"></use>
    <use xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#line1" class="line"></use>
</svg>

通过使用<defs><use>,您可以仅更改路径元素以更新两条线。JSFiddle演示

4

看起来你的线条是不透明的,所以你可以在“外部”颜色的较粗线上方,用“内部”颜色绘制一条细线。


谢谢,这是个好主意。但是我怎样才能确保“顶部”行正好居中于“底部”行的中心位置? - Tony R
1
只需使用相同的坐标和较细的线宽即可。使用圆形端点会看起来更加正确。 - Janne
啊,现在我想起来了,我相信你是正确的!谢谢 Janne。 - Tony R

3

您可以使用带有圆角的矩形,但是数学计算会有所改变:

  <rect data-angle="348" stroke="red" stroke-linecap="round" stroke-width="0.02" fill="#FF0" transform="rotate(348, 0, 0)" x="-0.02"  y="-0.4" width=".06" height=".4" rx=".03" ry=".03"/>

http://jsfiddle.net/RNAuP/


这就是我最初认为的解决方案。然而,你的解决方案看起来不如Janne的好。矩形的起点和终点没有完美地对齐在圆心和圆周上。 - Tony R
如果您能够正确对齐它,这个解决方案似乎更容易操作(比如说,如果我想要动态添加/删除轮廓,我就可以这样做)。因此,由于不同的原因,这变得笨拙了...您必须使用矩形的每个“短边”的中点。 - Tony R
这是一个算术问题,您必须从旋转中心减去边框宽度 http://jsfiddle.net/F5e74/,我坦率地认为两条线是更简单的解决方案。 - methodofaction
哎呀!这好一点了,但还不完美...最初我是将半圆端点的中心与大圆和其轮廓的中心对齐。为你的努力加1分 =) - Tony R

0

你也可以使用路径来完成它,尽管在圆形部分可能有些棘手:

<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" [
  <!-- I often use entities to be able to change lot of numbers at once in static SVG, also kind of makes the paths more readable.
       Obvisouly, if you're generating the path you can use the same variables in code to append to d -->
  <!ENTITY handFill "0.01">
  <!ENTITY handFill2 "0.02"><!-- Should be 2 * handFill to be centered -->
  <!ENTITY handStroke "0.005"><!-- Should be less than handFill2 to not hide fill -->
]>
<svg height="160" version="1.1" viewBox="-0.6 -0.6 1.2 1.2" width="160" xmlns="http://www.w3.org/2000/svg">
  <g>
    <g>
      <circle class="sensorShape" cx="0" cy="0" fill="#FFF" r="0.4" stroke="black" stroke-width="0.015"/>
      <line stroke="black" stroke-width="0.015" x1="0" x2="0" y1="-0.4" y2="0.4"/>
      <line stroke="black" stroke-width="0.015" x1="-0.4" x2="0.4" y1="0" y2="0"/>
    </g>
    <g class="lsNorthAngleHandsContainer">
      <path d="
        M -&handFill;,0 l0,-0.4
        a &handFill;,&handFill; 0 0,1 &handFill2;,0
        l 0,0.4
        a &handFill;,&handFill; 0 0,1 -&handFill2;,0
      " stroke="red" stroke-linecap="round" stroke-width="&handStroke;" fill="yellow" transform="rotate(348)" />
      <text font-size="0.08" transform="translate(-0.02316467632710395,-0.45125904029352226)">
        348
      </text>
    </g>
  </g>
</svg>

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