相邻的svg:polygon边缘不相遇。

14

我正在使用相邻的多边形绘制条形图,如下所示:

如果仔细观察,您会发现每个多边形之间有白色空隙(缩放后):

我正试图防止这种情况发生。我找到了SVG shape-rendering 属性,并将其设置为geometricPrecision。这解决了问题,但给了我非常清晰的边缘:

我也不想要那样。我尝试了shape-rendering的其他可能值,但没有一个很好地工作。(我在WebKit上尝试过这些方法。)我正在寻找解决方案。

对于那些感兴趣的人,图表的 jsFiddle 在这里


谢谢你的shape-rendering技巧,太棒了!正是我在寻找的。链接文章没有提到的是,你也可以在SVG内部的组上使用它,这非常方便,特别是当你有几何形状和文本轮廓(你确实希望抗锯齿)结合在一起时。 - Rijk
2个回答

7

实际问题在于你应该将图形渲染为一个单独的多边形,而不是每个条形图都渲染为一个多边形,但我假设你这样做有原因。

一种可能的解决方案是设置描边属性,使多边形轮廓被绘制,导致它们略微重叠。您可以在组元素上设置这些属性,以将其应用于所有封闭的多边形。

<g stroke-width="0.5" stroke="black" stroke-linejoin="round">

更新的 jsFiddle 链接

请注意,这会使图形看起来比实际大一点,但我认为这不是一个重要的问题。

造成这种情况的原因是,多边形的偏移量并没有完全对齐像素边界(至少大部分时间如此)。如果你将 svg 宽度固定在 300px 的倍数上(从而将所有内容对齐到像素边界),缝隙就应该消失了。

考虑一个 4x4 像素的区域,你想要从 (0,0) 到 (2.5,2.5) 渲染一个正方形,如下所示:

enter image description here

你可以将从 (0,0) 到 (1,1) 的像素涂成纯黑色,但是如何处理边缘——它们既不完全黑也不完全白。抗锯齿解决方案是使用灰度色阶,其比例与覆盖像素的面积成比例。

enter image description here

但是当你尝试在第一个多边形旁边(即从偏移量 2.5 开始)渲染另一个多边形时,你将遇到同样的问题,即抗锯齿左侧边缘。只不过这一次它会稍微暗一些,因为背景是灰色而不是白色。

enter image description here

正如你发现的那样,你可以通过设置不同的 shape-rendering 选项来禁用此效果,但这样就失去了对斜线的抗锯齿优势,使得这些边缘看起来锯齿状。


是的,实际上我打算在多边形上添加一个悬停效果,这就是为什么我一开始将它们分开而不是一个大的多边形。我认为这样做会有用。但是为什么会发生这种情况,你能回答吗? - ahmet alp balkan
1
@ahmetalpbalkan 我已更新我的回答,并解释了为什么你会看到那些空白。 - James Holderness
但是如果灰色绝对成比例,那么它就应该是50%的灰色。两个50%的灰度应该组合在一起形成100%黑色。我觉得大多数渲染器实际上是根据SVG对象的背景进行抗锯齿处理,而不是SVG画布上当前的内容。或者说,抗锯齿技术并非完美无缺,不能为x+0.5像素处的边框产生50%的灰色。 - trlkly
嗯,也许这里的解决方案是以50%的不透明度绘制笔画? - Andrew

0
我找到了一个明确而优雅的解决方案来解决这个问题。将你的多边形转换成一个带有多个线段的路径:
<script src="http://d3js.org/d3.v3.min.js"></script>
<svg width="100%" height="30%" viewBox="0 0 100 100" preserveAspectRatio="none">
        <path d="M0,100 0,70 3.3333333333333335,66 3.3333333333333335,100 M3.3333333333333335,100 3.3333333333333335,66 6.666666666666667,66 6.666666666666667,100 M6.666666666666667,100 6.666666666666667,66 10,62 10,100 M10,100 10,62 13.333333333333334,57.99999999999999 13.333333333333334,100 M13.333333333333334,100 13.333333333333334,57.99999999999999 16.666666666666664,56 16.666666666666664,100 M16.666666666666664,100 16.666666666666664,56 20,54 20,100 M20,100 20,54 23.333333333333332,40 23.333333333333332,100 M23.333333333333332,100 23.333333333333332,40 26.666666666666668,24 26.666666666666668,100 M26.666666666666668,100 26.666666666666668,24 30,15.999999999999998 30,100 M30,100 30,15.999999999999998 33.33333333333333,13.999999999999996 33.33333333333333,100 M33.33333333333333,100 33.33333333333333,13.999999999999996 36.666666666666664,11.999999999999996 36.666666666666664,100 M36.666666666666664,100 36.666666666666664,11.999999999999996 40,10.000000000000004 40,100 M40,100 40,10.000000000000004 43.333333333333336,10.000000000000004 43.333333333333336,100 M43.333333333333336,100 43.333333333333336,10.000000000000004 46.666666666666664,8.000000000000004 46.666666666666664,100 M46.666666666666664,100 46.666666666666664,8.000000000000004 50,8.000000000000004 50,100 M50,100 50,8.000000000000004 53.333333333333336,6.000000000000002 53.333333333333336,100 M53.333333333333336,100 53.333333333333336,6.000000000000002 56.666666666666664,6.000000000000002 56.666666666666664,100 M56.666666666666664,100 56.666666666666664,6.000000000000002 60,8.000000000000004 60,100 M60,100 60,8.000000000000004 63.33333333333333,10.000000000000004 63.33333333333333,100 M63.33333333333333,100 63.33333333333333,10.000000000000004 66.66666666666666,8.000000000000004 66.66666666666666,100 M66.66666666666666,100 66.66666666666666,8.000000000000004 70,11.999999999999996 70,100 M70,100 70,11.999999999999996 73.33333333333333,13.999999999999996 73.33333333333333,100 M73.33333333333333,100 73.33333333333333,13.999999999999996 76.66666666666667,11.999999999999996 76.66666666666667,100 M76.66666666666667,100 76.66666666666667,11.999999999999996 80,10.000000000000004 80,100 M80,100 80,10.000000000000004 83.33333333333334,11.999999999999996 83.33333333333334,100 M83.33333333333334,100 83.33333333333334,11.999999999999996 86.66666666666667,13.999999999999996 86.66666666666667,100 M86.66666666666667,100 86.66666666666667,13.999999999999996 90,11.999999999999996 90,100 M90,100 90,11.999999999999996 93.33333333333333,4.000000000000002 93.33333333333333,100 M93.33333333333333,100 93.33333333333333,4.000000000000002 96.66666666666667,0 96.66666666666667,100 M96.66666666666667,100 96.66666666666667,0 100,0 100,100 M100,100 100,0 100,0 100,100"/>
</svg>

http://jsfiddle.net/313xc6bg/

然而,如果您想对每个段应用不同的效果,则无法使用此方法。在这种情况下,我认为解决方法是添加足够宽的描边以覆盖白色空间,同时保持AA。

此外,我仍然遇到了Safari(仅限)与不同多边形中点的顺序有关的问题。更改顺序(即顺时针到逆时针)可以解决问题。


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