1

I am implementing a marching cubes algorithm generally based on the implementation of Paul Bourke with some major adjustments:

  • precalculation of the scalarfield (floating point values)
  • avoiding duplicated vertices in the final list using a std::map
  • vertex storing to visualize the final mesh in Ogre3D

Basically I changed nearly 80% of his code. My resulting mesh has some ugly terrasses and I am not sure how to avoid them. I assumed that using floating points for the scalar field would do the job. Is this a common effect? How can you avoid it?

Terassing Marching Cubes

calculating the vertex positions on the edges. (cell.val[p1] contains the scalar value for the given vertex):

//if there is an intersection on this edge
        if (cell.iEdgeFlags & (1 << iEdge))
        {
            const int* edge = a2iEdgeConnection[iEdge];

            int p1 = edge[0];
            int p2 = edge[1];

            //find the approx intersection point by linear interpolation between the two edges and the density value
            float length = cell.val[p1] / (cell.val[p2] + cell.val[p1]);
            asEdgeVertex[iEdge] = cell.p[p1] + length  * (cell.p[p2] - cell.p[p1]);
        }

You can find the complete sourcecode here: https://github.com/DieOptimistin/MarchingCubes I use Ogre3D as library for this example.

Anthea
  • 3,741
  • 5
  • 40
  • 64
  • It certainly can be made to be smooth, but can you narrow this down to a few lines of code which are giving you a pixel location you disagree with, instead of a screenshot? It's really hard to help you debug a screenshot... – Andy Newman Jun 16 '15 at 10:03
  • I edited the question. Since it's possible to make it smooth without any extra smoothing algorithm, I assume I have a bug in the calculation of the position of a vertex. – Anthea Jun 16 '15 at 10:29
  • Do you have the original comparison in context to render the same scene for comparision? If so, please post a screenshot. I would guess that somehow cached vertex positions are wrongly selected or the interpolation along the cube edges is based on the wrong values. – Codor Jun 16 '15 at 10:36
  • You're approach looks sane. Check that your linear interpolation is actually working correctly, and check that the values it is interpolating between are what you would expect. What is that really? I assume it is an isosurface of a field strength but what is equation of the field? – Andy Newman Jun 16 '15 at 10:57
  • Should length = v[p1] / (v[p2] - v[p1]) ? not +? – Andy Newman Jun 16 '15 at 11:12

1 Answers1

0

As Andy Newmann said, the devil was in the linear interpolation. Correct is:

float offset;
float delta = cell.val[p2] - cell.val[p1];

if (delta == 0) offset = 0.5;
else offset = (mTargetValue - cell.val[p1]) / delta;

asEdgeVertex[iEdge] = cell.p[p1] + offset* (cell.p[p2] - cell.p[p1]);
Anthea
  • 3,741
  • 5
  • 40
  • 64