从平面方程生成点网格的算法[关闭]
Posted
技术标签:
【中文标题】从平面方程生成点网格的算法[关闭]【英文标题】:Algorithm to generate a point grid out of a plane equation [closed] 【发布时间】:2013-08-28 11:39:15 【问题描述】:我在 3D 空间中有一个平面方程:ax + by + cz + d = 0我想用规则分布的点从平面上的特定点在给定半径内填充这个平面。在我看来,应该有一个数学上的优雅答案,但我看不到它。用 C++ 或伪代码回答会更好。
【问题讨论】:
请提供一个例子,你已经尝试过什么,以及你具体遇到的问题。这不是“为我的规范提供代码”网站 一个给定的半径是什么?飞机上的特定点?没有这些信息,这个问题就没有多大意义。 @Save:对。平面上特定点的给定半径。 提示:在你的平面中选择两个正交向量。您现在可以将这些用作转换矩阵,将 x-y 平面中的点带入您的平面。 @nyarlathotep:我不知道该怎么做...我现在看到的唯一解决方案是在平面上选择两个极值点,在它们之间迭代并从其中切出一个半径... 【参考方案1】:我假设您有一个相当不错的 3d 矢量类,并在答案中将其称为 vec3。您需要的第一件事是平面中的矢量。在给定法线平面方程的情况下,有几种方法可以生成一个,但我更喜欢这个:
vec3 getPerpendicular(vec3 n)
// find smallest component
int min=0;
for (int i=1; i<3; ++i)
if (abs(n[min])>abs(n[i]))
min=i;
// get the other two indices
int a=(i+1)%3;
int b=(i+2)%3;
vec3 result;
result[i]=0.f;
result[a]=n[b];
result[b]=-n[a];
return result;
这种构造保证 dot(n, getPerpendicular(n)) 为零,这是正交性条件,同时还保持向量的大小尽可能高。请注意,将具有最小幅度的分量设置为 0 还可以保证您不会得到 0,0,0 向量,除非这已经是您的输入。在这种情况下,你的飞机会退化。
现在让你的基向量在平面上:
vec3 n(a,b,c); // a,b,c from your equation
vec3 u=normalize(getPerpendicular(n));
vec3 v=cross(u, n);
现在您可以通过缩放 u 和 v 并将其添加到您在飞机上获得的向量来生成您的点。
float delta = radius/N; // N is how many points you want max in one direction
float epsilon=delta*0.5f;
for (float y=-radius; y<radius+epsilon; radius+=delta)
for (float x=-radius; x<radius+epsilon; radius+=delta)
if (x*x+y*y < radius*radius) // only in the circle
addPoint(P+x*u+y*v); // P is the point on the plane
epsilon 确保您的点数是对称的,并且您不会错过极端情况下的最后一点。
【讨论】:
你能解释更多getPerpendicular()
吗?我不明白你在做什么......(我什至认为最后有什么问题......)
正交向量的条件是dot(a,b)==0。您始终可以通过将一个分量设置为零、交换其他两个分量并反转其中一个分量的符号来构造这样的向量。这样一来,在点积方程中,一个乘积为零,而另外两个乘积相互抵消。请注意,您交换的两个组件之一应该是非零的,否则您的结果将是 0,0,0(这在技术上垂直于一切,但在这里没用)
例如,如果你有一个向量 x,y,z - 向量 0,z,-y 总是垂直的,因为 0*x+yz-yz 是总是 0。
那么不应该是result[a] = n[b]; result[b] = -n[a];
吗?
是的,我搞砸了,抱歉 - 会修复以上是关于从平面方程生成点网格的算法[关闭]的主要内容,如果未能解决你的问题,请参考以下文章