D3.js 如何将svg形状放置在圆中?

D3.js 如何将svg形状放置在圆中?,d3.js,D3.js,我正在玩一点D3.js,我的大部分工作都正常。但是我想把我的svg形状放在一个圆圈里。因此,我将用颜色和文本显示数据的差异。我知道如何画圆和饼图,但我想基本上有一个大小相同的圆。不要让它们重叠,顺序是不相关的。我不知道从哪里开始,找出每个圆的x&y。如果我理解正确,这是一个相当标准的数学问题: 只需以适当的步长循环某些角度变量,并使用sin()和cos()计算x和y值 例如: 假设您正在尝试放置3个对象。一个圆有360度。因此,每个对象都与下一个对象成120度角。如果对象的大小为20x20像素,

我正在玩一点D3.js,我的大部分工作都正常。但是我想把我的svg形状放在一个圆圈里。因此,我将用颜色和文本显示数据的差异。我知道如何画圆和饼图,但我想基本上有一个大小相同的圆。不要让它们重叠,顺序是不相关的。我不知道从哪里开始,找出每个圆的x&y。

如果我理解正确,这是一个相当标准的数学问题:

只需以适当的步长循环某些角度变量,并使用
sin()
cos()
计算x和y值

例如:

假设您正在尝试放置3个对象。一个圆有360度。因此,每个对象都与下一个对象成120度角。如果对象的大小为20x20像素,请将其放置在以下位置:

 x1 = sin(  0 * pi()/180) * r + xc - 10;  y1 = cos(  0 * pi()/180) * r + yc - 10
 x2 = sin(120 * pi()/180) * r + xc - 10;  y2 = cos(120 * pi()/180) * r + yc - 10
 x3 = sin(240 * pi()/180) * r + xc - 10;  y3 = cos(240 * pi()/180) * r + yc - 10
这里,
r
是圆的半径,
(xc,yc)
是圆中心点的坐标。
-10的
确保对象的中心(而不是左上角)位于圆上。
*pi()/180
将度转换为弧度,这是大多数
sin()
cos()
实现所需的单位


注意:这将使形状均匀分布在圆周围。为了确保它们不会重叠,您必须选择足够大的
r
。如果对象具有简单且相同的边界,只需布置10个边界并计算出所需的半径,然后,如果需要放置20个边界,则使半径增大两倍,30个边界增大三倍,以此类推。如果对象的形状不规则,并且您希望将它们按最佳顺序放置在圆周围,以找到可能的最小圆,那么这个问题将变得非常混乱。也许有这样一个库,但我脑子里没有,因为我没有使用D3.js,我也不确定它是否能为您提供此功能。

这里有另一种方法,对于任意大小的形状,使用D3的
布局:

布局(,)将根据给定半径和返回任意两个项目中心间距的函数为您计算每个项目的x、y位置。在本例中,我使用了大小不同的圆,因此它们之间的间距是半径的函数:

var tree = d3.layout.tree()
    .size([360, radius])
    .separation(function(a, b) {
        return radiusScale(a.size) + radiusScale(b.size);
    });
使用D3
布局解决了第一个问题,即在一个圆圈中布局项目。正如@Markus所指出的,第二个问题是如何计算圆的右半径。为了方便起见,我在这里采用了一种略为粗略的方法:我将圆的周长估计为各种项目的直径之和,中间有一个给定的填充,然后根据周长计算半径:

var roughCircumference = d3.sum(data.map(radiusScale)) * 2 +
        padding * (data.length - 1),
    radius = roughCircumference / (Math.PI * 2);

这里的周长并不精确,而且随着圆圈中的项目越来越少,它的精确度也越来越低,但对于这个目的来说,它已经足够接近了。

感谢背景匹配信息,我正在寻找一个特定的D3js解决方案,但这有助于理解。我正在寻找一种解决方案,它将允许点放置在其他路径形状中,如新月形和圆形。答案是:)@MarkusA,很好的答案。你也知道如何找到最小半径量吗?还是我应该问一个全新的问题?在您的示例中,3个对象是20x20。通过反复试验,我可以看到半径约为22.5的物体刚好接触。如何自动计算此最小半径?我的对象大小不规则。@Jared一个圆的周长是由2*pi()*r给出的,因此如果您的对象是球形的,您可以通过获取对象的直径,乘以对象的数量,然后将结果除以2pi(),大致了解所需的半径。问题是,只有当对象接触到圆的周长时,这才起作用。通常,他们会在圆圈内的某个地方碰触。虽然计算所需半径是完全可能的,但它需要更多的几何图形,公式将取决于对象的形状和数量。