/* BaseMesh.h Written by Matthew Fisher BaseMesh is an abstract mesh class that defines basic mesh functionality. It also includes source for most of the manipulation (shape generation, file loading, etc.) that is possible under this generic structure. Each mesh must be associated with a graphics device before most operations can be performed. */ // // a single face in the mesh // struct TriMeshFace { TriMeshFace() {} TriMeshFace(DWORD I0, DWORD I1, DWORD I2) { I[0] = I0; I[1] = I1; I[2] = I2; } DWORD I[3]; }; class BaseMesh { public: BaseMesh(); // // Memory // virtual void Allocate(UINT NewVertexCount, UINT NewFaceCount) = 0; virtual void FreeMemory() = 0; void CopyMesh(BaseMesh &Copy) const; BaseMesh& operator = (const BaseMesh &O); virtual void operator += (const BaseMesh &O); virtual void AppendVertices(const BaseMesh &O); virtual void LoadMeshList(const Vector &Meshes); virtual void LoadMeshList(const Vector< pair > &Meshes); // // Accessors // virtual UINT IndexCount() const = 0; virtual UINT VertexCount() const = 0; virtual UINT FaceCount() const = 0; virtual MeshVertex* Vertices() = 0; virtual DWORD* Indices() = 0; virtual const MeshVertex* Vertices() const = 0; virtual const DWORD* Indices() const = 0; GraphicsDevice& GetGD() const; void SetGD(GraphicsDevice &GD); Vec3f EvaluateBarycentricPos(UINT FaceIndex, float u, float v) const; // // Coloring functions // void SetColor(RGBColor C); //sets the color of each vertex in the mesh void SetAlpha(BYTE Alpha); //sets the alpha component of the color color of each vertex in the mesh void RandomizeColors(); //randomizes the color of each vertex in the mesh void ColorNormals(); //colors the vertices of the mesh based upon the normal vector at that point void ColorNormals(float fr, float fg, float fb); //colors the vertices of the mesh based upon the normal vector at that point, //weighted by the given values (1.0 = full intensity, 0.0 = RGBColor::Black.) void ColorNormals(RGBColor Color); void ColorNormalsGrayScale(RGBColor Color); //colors each vertex based upon the normals but to grayscale color //values. UseMaximumValue = true/false will give slightly different colorings. // // Texturing functions // void TextureSphericalMap(int variable); //sets texture coordinates of each vertex based upon the spherical coordinates of the position of that vertex void TextureMapToNormals(int variable); //sets texture coordinates of each vertex based upon the normal vector of that vertex // // Geometry functions // // Sphere void CreateSphere(float radius, int refinement); //creates a icosahedron with a given radius refined to a sphere refinement times. void CreateSphere(float radius, int slices, int stacks); //creates a sphere based upon a given number of angular slices/stacks in spherical coordinates. // Box void CreateBox(float w, float h, float d, int refinement = 0); //creates a box with the given width, height, and depth, refined a given number of times. void CreateBox(const Rectangle3f &Rect); // Triangle void CreateTriangle(const Vec3f &v0, const Vec3f &v1, const Vec3f &v2, RGBColor color); // Teapot void CreateTeapot(float radius); //creates a teapot (by default loads it from a file, which must be initalized.) // Cylinder void CreateCylinder(float radius, float height, UINT slices, UINT stacks); //creates a cylinder with the given paramaters void CreateCylinder(float radius, const Vec3f &pt1, const Vec3f &pt2, UINT slices, UINT stacks); //creates a cylinder between two points in 3-space void CreateClosedCylinder(float radius, const Vec3f &pt1, const Vec3f &pt2, UINT slices, UINT stacks); //creates a cylinder between two points in 3-space void ReCreateCylinder(float radius, const Vec3f &pt1, const Vec3f &pt2, UINT slices, UINT stacks); //if CreateCylinder has already been called with the same paramaters, recreates the //cylinder without reallocating memory space. void CreateCylinder(Vec3f (*PositionFunction) (float), float Start, //creates a cylinder such that the center of each slice follows a given function from float End, float radius, UINT slices, UINT stacks); //Start to End. void ReCreateCylinder(Vec3f (*PositionFunction) (float), float Start, //if CreateCylinder has already been called with the same paramaters, recreates the float End, float radius, UINT slices, UINT stacks); //cylinder without reallocating memory space. void CreateClosedCylinder(float radius, float height, UINT slices, UINT stacks); //creates a cylinder whose ends are closed off. void CreateLantern(float radius, float height, UINT slices, UINT stacks); //creates a lantern, which is just a cylinder that is poorly triangulated. // Planes void CreatePrettyPlane(float size, UINT slicesX, UINT slicesY); //creates an X-Y plane centered at the origin with the given paramaters void CreateCanonicalRenderPlane(); void CreatePlane(float size, UINT slicesX, UINT slicesY); //creates an X-Y plane centered at the origin with the given paramaters void CreatePlane(const Vec3f &start, const Vec3f &end, UINT slicesX, UINT SlicesY); //creates a plane between the given points void CreatePlane(const Plane &p, float length, UINT slices); //creates a plane that represents the given plane void CreatePlane(const Plane &p, float length, UINT slices, const Vec3f &Center); //creates a plane that represents the given plane void CreateViewPlane(float EyeDist, UINT slices, MatrixController &MC); //creates a plane that covers the whole screen a given distance //from the Matrix4 transform represented by MC // Torus void CreateTorus(float MainRadius, float SmallRadius,UINT slices, UINT stacks); //creates a torus with the given paramaters // Lozenge void CreateLozenge(float Radius, const Vec3f &Start, const Vec3f &End, UINT slices, UINT stacks); //creates a lozenge between the given points void ReCreateLozenge(float Radius, const Vec3f &Start, const Vec3f &End, UINT slices, UINT stacks); //recreates a lozenge between the given points without reallocating memory. void CreatePointCloudBoxes(const Vector &Points, float Radius); // // Rendering functions // virtual void Render() const = 0; //renders the mesh on the associated graphics device // // File functions // // ASCII void SaveASCII(const String &Filename) const; void LoadASCII(const String &Filename); void SaveStream(OutputDataStream &stream) const; void LoadStream(InputDataStream &stream); // Binary void SaveBinary(const String &Filename) const; void LoadBinary(const String &Filename); void SaveCompressed(const String &Filename) const; void LoadCompressed(const String &Filename); // Other void SaveObj(const String &Filename) const; //saves the mesh in *.obj format void SavePBRT(const String &Filename, const Vector &LocalCoordinateFrame); void SavePly(const String &Filename); //saves the mesh in *.ply format void LoadObj(const String &Filename, bool IgnoreSlashes = true); //loads the mesh in *.obj format void LoadPly(const String &Filename); //saves the mesh in *.ply format void LoadGridPly(const String &Filename); //saves the mesh in *.ply format, Cyberware grid style // // Normal manipulation // virtual void GenerateNormals(); //generates the normals at each vertex based upon the average of the incident faces void GCNormals(); //generates and colors the normals at each vertex void NormalizeNormals(); //normalizes all vertex normals in the mesh // // Position manipulation // void Stretch(float Factor); //stretches the mesh uniformly in all directions void Stretch(const Vec3f &V); //stretches the mesh non-uniformly in each dimension void Translate(const Vec3f &V); //translates every vertex in the mesh void SetRadius(float Size); //rescales the mesh such that the maximum distance from the origin to a vertex is Size void ApplyMatrix(const Matrix4 &M); //applys M to every vertex position and normal in the mesh // // Enhancement functions // void TwoPatch(); //enhances the mesh by replacing each face with 4 faces. Linear interpolation is used. void Subdivide(); void Subdivide(UINT Iterations); // // Bounding visibility // Rectangle3f BoundingBox() const; //calculates the bounding box for the set of all vertex in the mesh Rectangle3f BoundingBox(const Matrix4 &transform) const; float Radius(); //computes the maximum distance from the origin to a vertex of the mesh float Radius(const Vec3f &Center); Matrix4 UnitSphereTransform(); //translates the mesh such that the center of the bounding box for the mesh is the origin // // Simplification // #ifdef USE_POINT_SET virtual void WeldVertices(float epsilon); //takes every group of vertices within epsilon of each other and replaces them with a single vertex, //and alters incident faces to point to these new vertices. virtual void WeldVertices(float epsilon, Vector &OldToNewMapping); #endif void UnIndex(); //duplicates every vertex such that each triangle points to its own set of 3 vertices, rather than //incident triangles sharing vertices. void CleanVerticesAndTriangles(); void CleanVerticesAndTriangles(Vector &OldToNewMapping); // // Splitting // void Split(Plane &p, BaseMesh &M1, BaseMesh &M2); //given an arbitrary plane, returns in M1 the vertices and faces in this mesh that lie on one side //of the plane, and returns the vertices/faces that lie on the other side in M2. //triangles that lie on the boundary are grouped as if they were on the side with 2 vertices satisfying the condition. void Split(float (*PositionFunction) (Vec3f &), BaseMesh &M1, BaseMesh &M2); //same as split, except the decision function is whether PositionFunction is //negative or positive at the vertex position. void ClosedPlaneSplit(const Plane &P, BaseMesh &M1, BaseMesh &M2); void CullFaces(const BYTE FaceTest[]); // // Query // UINT32 Hash32() const; UINT64 Hash64() const; float SurfaceArea() const; float SidedSurfaceArea(const Plane &P); // // Helper functions // void RotateFaces(); protected: GraphicsDevice *_GD; };