1

我正在尝试使用http://meatfighter.com/fluiddynamics/GPU_Gems_Chapter_38.pdf作为资源使用 WebGL 进行流体模拟。我已经实现了一切,但我觉得有很多事情不能正常工作。我添加了边界,但似乎它们没有任何效果,这让我怀疑有多少压力和平流正在起作用。我展示了散度,我在移动物体的位置以及速度到达边缘(边界)时几乎没有得到什么,但我得到的压力是完全空的。我使用链接资源中描述的扩散着色器计算压力。

我知道我发布的代码由于其性质而有点令人困惑。如果有帮助,我可以提供任何图片/模拟链接。

- 编辑 -

经过更多调查,我认为问题与我的平流功能有关。或者至少是一个问题。我不确定如何解决它。

我遵循的一般过程不是发布我的所有代码,而是:平流速度扩散速度加速度计算散度计算压力减梯度

对于扩散速度和计算压力,我只进行 10 次迭代,因为我的计算机可以处理我的实现(一旦我开始工作,我会优化),但我觉得计算压力和减去梯度没有任何效果。

这是我正在使用的着色器:

//advection
uniform vec2 res;//The width and height of our screen
uniform sampler2D velocity;//input velocity
uniform sampler2D quantity;//quantity to advect


void main() {
        vec2 pixel = gl_FragCoord.xy / res.xy;

        float i0, j0, i1, j1;
        float x, y, s0, s1, t0, t1, dxt0, dyt0;
        float dt = 1.0/60.0;
        float Nx = res.x -1.0;
        float Ny = res.y -1.0;
        float i = pixel.x;
        float j = pixel.y;

        dxt0 = dt  ;
        dyt0 = dt  ;
        x = gl_FragCoord.x - dxt0 * (texture2D(velocity, pixel).x );
        y = gl_FragCoord.y - dyt0 * (texture2D(velocity, pixel).y );

        i0=x-0.5; 
        i1=x+0.5;

        j0=y-0.5; 
        j1=y+0.5;


        s1 = x-i0; 
        s0 = 1.0-s1; 
        t1 = y-j0; 
        t0 = 1.0-t1;


        float p1 =  (t0 * texture2D(quantity, vec2(i0,j0)/res.xy).r);
        float p2 =  (t1 * texture2D(quantity, vec2(i0,j1)/res.xy).r);
        float p3 =  (t0 * texture2D(quantity, vec2(i1,j0)/res.xy).r);
        float p4 =  (t1 * texture2D(quantity, vec2(i1,j1)/res.xy).r);
        float total1 = s0 * (p1 + p2);
        float total2 = s1 * (p3 + p4);
        gl_FragColor.r = total1 + total2;

        p1 =  (t0 * texture2D(quantity, vec2(i0,j0)/res.xy).g);
        p2 =  (t1 * texture2D(quantity, vec2(i0,j1)/res.xy).g);
        p3 =  (t0 * texture2D(quantity, vec2(i1,j0)/res.xy).g);
        p4 =  (t1 * texture2D(quantity, vec2(i1,j1)/res.xy).g);
        total1 = s0 * (p1 + p2);
        total2 = s1 * (p3 + p4);
        gl_FragColor.g = total1 + total2;

}

//diffusion shader starts here

uniform vec2 res;//The width and height of our screen
uniform sampler2D x;//Our input texture
uniform sampler2D b;
uniform float alpha;
uniform float rBeta;


void main() {
    float xPixel = 1.0/res.x;
    float yPixel = 1.0/res.y;
    vec2 pixel = gl_FragCoord.xy / res.xy;
    gl_FragColor = texture2D( b, pixel );

    vec4 leftColor = texture2D(x,vec2(pixel.x-xPixel,pixel.y));
    vec4 rightColor = texture2D(x,vec2(pixel.x+xPixel,pixel.y));
    vec4 upColor = texture2D(x,vec2(pixel.x,pixel.y-yPixel));

    vec4 downColor = texture2D(x,vec2(pixel.x,pixel.y+yPixel));




    gl_FragColor.r = (gl_FragColor.r * alpha +leftColor.r   + rightColor.r + upColor.r + downColor.r) * rBeta;

    gl_FragColor.g = (gl_FragColor.g * alpha +leftColor.g   + rightColor.g + upColor.g + downColor.g)* rBeta;


    gl_FragColor.b = (gl_FragColor.b * alpha +leftColor.b   + rightColor.b + upColor.b + downColor.b)* rBeta;


}



//gradient
uniform vec2 res;//The width and height of our screen
uniform sampler2D velocity;//Our input velocity
uniform sampler2D pressure;//Our input pressure

void main() {
    float xPixel = 1.0/res.x;
    float yPixel = 1.0/res.y;
    vec2 pixel = gl_FragCoord.xy / res.xy;

    vec4 leftColor  = texture2D(pressure, vec2(pixel.x-xPixel,pixel.y));
    vec4 rightColor = texture2D(pressure, vec2(pixel.x+xPixel,pixel.y));
    vec4 upColor    = texture2D(pressure, vec2(pixel.x,pixel.y-yPixel));
    vec4 downColor  = texture2D(pressure, vec2(pixel.x,pixel.y+yPixel));




    vec2 gradient = xPixel/2.0 * vec2((rightColor.x - leftColor.x), (upColor.y - downColor.y));
    //Diffuse equation
    gl_FragColor = texture2D(velocity, pixel) ;
    gl_FragColor.xy -= gradient;



}



uniform vec2 res;//The width and height of our screen
uniform sampler2D velocity;//Our input texture


void main() {
    float xPixel = 1.0/res.x;
    float yPixel = 1.0/res.y;
    vec2 pixel = gl_FragCoord.xy / res.xy;

    vec4 leftColor  = texture2D(velocity, vec2(pixel.x-xPixel,pixel.y));
    vec4 rightColor = texture2D(velocity, vec2(pixel.x+xPixel,pixel.y));
    vec4 upColor    = texture2D(velocity, vec2(pixel.x,pixel.y-yPixel));
    vec4 downColor  = texture2D(velocity, vec2(pixel.x,pixel.y+yPixel));




    float div = xPixel/2.0 * ((rightColor.x - leftColor.x) + (upColor.y - downColor.y));
    //Diffuse equation
    gl_FragColor = vec4(div);



}
4

0 回答 0