marching cubes, very small triangles

So I'm trying to generate terrain using marching cubes algorithm. At this point I'm implementing the diffuse lighting (fragment shader). I calculated normals for each vertex and got this: result

The left side of the picture displays the normals (for each vertex and triangle) and wireframe, to the right is the lighted landscape from the same camera angle.

so, i'm curious, what am I doing wrong?

I calculate normals this way:

for (int t = 0; t < all_triangles.size(); t++) {

        Vertex v0 = all_vertices[triangle.get_vertex(0)];
        Vertex v1 = all_vertices[triangle.get_vertex(1)];
        Vertex v2 = all_vertices[triangle.get_vertex(2)];

        QVector3D edge1 = v1 - v0;
        QVector3D edge2 = v2 - v0;

        QVector3D normal = QVector3D::crossProduct(edge1, edge2);
//        triangle.set_normal(normal.normalized());

        for (int v = 0; v < 3; v++) {
            all_vertices[triangle.get_vertex(v)].add_normal(normal.normalized());
        }
    }

    for (int v = 0; v < all_vertices.size(); v++) {
        auto normal = all_vertices[v].get_normal();
        normal.normalize();
        all_vertices[v].set_normal(normal);

    }

upd: vcs

bitbucket source


Your math is correct. You normals are looks like fine, but it's very hard to 100% understand your picture.

common approach for debuging such problems is: - flat shading (no normal smoothing) - use triangle/vertex normal as color to visualize normals

Also please share your shading code.


That's normal for marching cubes. It's a know problem of the algorythm with some technical name like redundant triangles. There is a very simple adjustment for that if you need less triangles and dont mind adding a compare equals line for every vertex, the fix is to snap iso values onto the corners of the cubes if they are more than 95% closer to them. MC optimizations are very cool the best would be octree sensing of used cubes and resizing the cubes relative to the complexity or flatness of the surface at that zone. there are awesome papers on the topic.

Here is a demonstration of a fast fix just by snapping values to corners if edge intersection proximity to corner is under 5% or over 95%, tunable, can try 90% if you want.

Generic MC: 在这里输入图像描述

Simplest possible optimization: 在这里输入图像描述

SnapMC is similar:

在这里输入图像描述


Some things to try:

(1) Weight your normals. add_normal(normal.normalized()*weight), where weight can be a lot of things, like the area of the triangle, or the inner angle

(2) Compute a normal from your field. You are getting a surface where f(x,y,z)=0. Evaluate to f(x-eps,y,z)-f(x+eps,y,z) to get your normal x, same for y,z.

(3) Just blur it. For every vertex add in all adjacent normals by edge, and average.

I think you want (2). Especially for terrain.

链接地址: http://www.djcxy.com/p/37248.html

上一篇: 可视化用行军立方体生成的等值面

下一篇: 行军的立方体,非常小的三角形