matrix - 在球体上从一点移动到另一点

标签 matrix glsl vector-graphics cinder

我正在使用基于 GPU 的粒子系统。 通过将 x、y、z 位置作为 1024*1024 纹理上的 RGB 值传递来计算出 100 万个粒子。他们的速度也是如此。

我试图让它们从任意一点移动到球体上的一点。

我当前用于计算的着色器正在从一个点直接移动到另一个点。

我目前没有使用质量或速度纹理

// float mass   = texture2D( posArray, texCoord.st).a;
vec3 p      = texture2D( posArray, texCoord.st).rgb;
// vec3 v       = texture2D( velArray, texCoord.st).rgb;

// map into 'cinder space'
p = (p * - 1.0) + 0.5;

// vec3 acc = -0.0002*p; // Centripetal force
// vec3 ayAcc  = 0.00001*normalize(cross(vec3(0, 1 ,0),p)); // Angular force
// vec3 new_v  = v + mass*(acc+ayAcc);

vec3 new_p = p + ((moveToPos - p) / duration);

// map out of 'cinder space'
new_p = (new_p - 0.5) * -1.0;

gl_FragData[0] = vec4(new_p.x, new_p.y, new_p.z, mass);
//gl_FragData[1] = vec4(new_v.x, new_v.y, new_v.z, 1.0);

moveToPos 是 float 形式的鼠标指针 (0.0f > 1.0f) 坐标系从 (0.5,0.5 > -0.5,-0.5) 转换为 (0.0,0.0 > 1.0,1.0)

我对向量数学和令我困惑的计算完全陌生。我知道我需要使用公式:

x=Rsinψcosθ

y=Rsinψsinθ

z=Rcosψ

但是从 moveToPos(xyz) > p(xyz) 计算角度仍然是一个问题

最佳答案

几年前我编写了这个 GPU 粒子着色器的原始版本(现在 @: https://github.com/num3ric/Cinder-Particles )。这是解决您的问题的一种可能的方法

我将从片段着色器开始,对粒子施加 Spring 力,以便它们或多或少地被限制在球体的表面。像这样的事情:

uniform sampler2D posArray;
uniform sampler2D velArray;
varying vec4 texCoord;

void main(void)
{   
    float mass  = texture2D( posArray, texCoord.st).a;
    vec3 p      = texture2D( posArray, texCoord.st).rgb;
    vec3 v      = texture2D( velArray, texCoord.st).rgb;

    float x0    = 0.5; //distance from center of sphere to be maintaned
    float x     = distance(p, vec3(0,0,0)); // current distance
    vec3 acc    = -0.0002*(x - x0)*p; //apply spring force (hooke's law)

    vec3 new_v  = v + mass*(acc);
    new_v = 0.999*new_v; // friction to slow down velocities over time
    vec3 new_p  = p + new_v;

    //Render to positions texture
    gl_FragData[0] = vec4(new_p.x, new_p.y, new_p.z, mass);
    //Render to velocities texture
    gl_FragData[1] = vec4(new_v.x, new_v.y, new_v.z, 1.0);
}

然后,我将为与相同半径的球体相交的鼠标位置传递一个新的 vec3 uniform(在 Cinder 中的着色器外部完成)。

现在,将其与之前的软 Spring 约束结合起来。您可以向该吸引点添加切向力。从简单的 (mousePos - p) 加速开始,然后找到一种方法,使用叉积使该力完全切向。

我不确定球坐标方法在这里如何工作。

x=Rsinϕcosθ

y=Rsinϕsinθ

z=Rcosϕ

哪里可以得到 phi 和 θ?纹理以笛卡尔坐标存储位置和速度。另外,来回转换并不是真正的选择。

如果您对向量不熟悉,我的解释可能太高级了。不幸的是,着色器和粒子动画本质上是非常数学化的。

关于matrix - 在球体上从一点移动到另一点,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12934908/

相关文章:

c - 索引 0 处的 for 循环中的数组访问冲突异常

r - 从MODISSummaries函数返回错误(R包MODISTools)

c++ - GLSL 每像素点光着色

javascript - Raphaël.js 中的剪辑路径

圆角为圆弧的 SVG 路径

c# - 适用于带有 C# 绑定(bind)的 Windows 的矢量图形库

opencv - 如何通过 CV_MAT_ELEM 在多 channel 矩阵中设置元素?

c++ - 节点之间的存储成本

opengl-es - OpenGL半透明四边形神器

c++ - GLSL 停止渲染