Wpf MVVM 3D Model Viewer – IMeshData Cube
Posted by triroot on February 16, 2010
In my last post I implemented a 3D Model Viewer that renders geometry from IMeshData. In the post I just rendered a simple triangle mesh. Here I’m going to implement a simple cube mesh. This implementation is designed to be easy to follow, and has not been optimized for saving memory.
For reference, here is what the IMeshData looks like:
public interface IMeshData
{
IEnumerable<Point3D> Vertices { get; }
IEnumerable<int> TriangleIndices { get; }
}
I implemented a static Utility class that will describe the data needed for each cube face. The Contributions are the four corner points in 3D space for a face, and the TriangleIndices describes how to use those points to construct two triangles for the face
public enum CubeFaceType
{
None,
Left,
Right,
Top,
Bottom,
Front,
Back,
}
class CubeFaceUtil
{
internal static CubeFaceType[] GetCubeFaces()
{
return new CubeFaceType[]
{
CubeFaceType.Left,
CubeFaceType.Right,
CubeFaceType.Top,
CubeFaceType.Bottom,
CubeFaceType.Front,
CubeFaceType.Back
};
}
internal static Point3D[] GetContributions(CubeFaceType type)
{
switch (type)
{
case CubeFaceType.Left:
return new Point3D[]
{
new Point3D(-1, 1, -1),
new Point3D(-1, 1, 1),
new Point3D(-1, -1, 1),
new Point3D(-1, -1, -1)
};
case CubeFaceType.Right:
return new Point3D[]
{
new Point3D(1, 1, 1),
new Point3D(1, 1, -1),
new Point3D(1, -1, -1),
new Point3D(1, -1, 1)
};
case CubeFaceType.Top:
return new Point3D[]
{
new Point3D(-1, 1, -1),
new Point3D(1, 1, -1),
new Point3D(1, 1, 1),
new Point3D(-1, 1, 1)
};
case CubeFaceType.Bottom:
return new Point3D[]
{
new Point3D(1, -1, -1),
new Point3D(-1, -1, -1),
new Point3D(-1, -1, 1),
new Point3D(1, -1, 1)
};
case CubeFaceType.Front:
return new Point3D[]
{
new Point3D(-1, 1, 1),
new Point3D(1, 1, 1),
new Point3D(1, -1, 1),
new Point3D(-1, -1, 1)
};
case CubeFaceType.Back:
return new Point3D[]
{
new Point3D(1, 1, -1),
new Point3D(-1, 1, -1),
new Point3D(-1, -1, -1),
new Point3D(1, -1, -1)
};
default:
throw new ArgumentException(
"Unsupported CubeFaceType",
"type");
}
}
internal static int[] GetTriangleIndices()
{
return new int[]
{
0, 3, 1,
1, 3, 2
};
}
}
Now all that needs to be done is to iterate through the faces and add them to the MeshDataCube.
public class MeshDataCube : IMeshData
{
public MeshDataCube(double cubeSize)
{
double halfFaceSize = cubeSize / 2;
List<int> allIndices = new List<int>();
List<Point3D> allVertices = new List<Point3D>();
foreach (CubeFaceType faceType in CubeFaceUtil.GetCubeFaces())
{
int[] indices = CubeFaceUtil.GetTriangleIndices();
Point3D[] contributions = CubeFaceUtil.GetContributions(faceType);
Point3D[] positions = contributions.Select(p => p.Scale(halfFaceSize)).ToArray();
// shift the indicies by the number of vertices already added.
allIndices.AddRange(indices.Select(i => i + allVertices.Count()));
allVertices.AddRange(positions);
}
Vertices = allVertices;
TriangleIndices = allIndices;
}
public IEnumerable<int> TriangleIndices { get; protected set; }
public IEnumerable<Point3D> Vertices { get; protected set; }
}
BAM!
Wpf MVVM 3D Model Viewer – More View Panels « Tristan Root's Blog said
[...] Comments (RSS) « Wpf MVVM 3D Model Viewer – IMeshData Cube [...]