diff options
Diffstat (limited to 'public/disp_powerinfo.h')
| -rw-r--r-- | public/disp_powerinfo.h | 213 |
1 files changed, 213 insertions, 0 deletions
diff --git a/public/disp_powerinfo.h b/public/disp_powerinfo.h new file mode 100644 index 0000000..0abd035 --- /dev/null +++ b/public/disp_powerinfo.h @@ -0,0 +1,213 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: This module defines the CPowerInfo class, which contains a +// whole bunch of precalculated data for each displacement power. +// It holds data that indicates how to tesselate, how to access +// neighbor displacements, etc. +// +// $NoKeywords: $ +//=============================================================================// + +#ifndef DISP_POWERINFO_H +#define DISP_POWERINFO_H +#ifdef _WIN32 +#pragma once +#endif + + +#include "disp_vertindex.h" +#include "bspfile.h" + + +#define NUM_POWERINFOS (MAX_MAP_DISP_POWER+1) + + +struct DispNodeInfo_t +{ + enum + { + // Indicates if any children at all have triangles + CHILDREN_HAVE_TRIANGLES = 0x1 + }; + + + // Indicates which tesselation indices are associated with a node + unsigned short m_FirstTesselationIndex; + unsigned char m_Count; + unsigned char m_Flags; +}; + + +// ------------------------------------------------------------------------ // +// CTesselateWindings are used to tell what order a node needs to visit +// vertices while tesselating. +// ------------------------------------------------------------------------ // +class CTesselateVert +{ +public: + CTesselateVert( CVertIndex const &index, int iNode ); + + CVertIndex m_Index; + short m_iNode; // Which node this vert is a part of (-1 on left, right, up, and down). +}; + + +class CTesselateWinding +{ +public: + CTesselateVert *m_Verts; + short m_nVerts; // (includes the last vert) +}; + + +class CVertDependency +{ +public: + + // Returns false if there is no dependency stored here. + bool IsValid() { return m_iVert.x != -1; } + + +public: + + // The vert index is in the same power as the source displacement. + // It is also wrapped, so for example, on the middle of the right edge + // of a 3x3, it will have a dependency on the 3x3's root node (1,1), and it + // will have another (1,1) entry that references a neighbor. + CVertIndex m_iVert; + + // This is -1 if the vert exists inside the source displacement. + // It is one of the NEIGHBOREDGE_ codes above if it reaches into a neighbor. + short m_iNeighbor; +}; + + +// Precalculated data about displacement vertices. +class CVertInfo +{ +public: + CVertInfo(); + + // These are the vertices that this vertex depends on (vertices that must be + // active for this vert to exist). + CVertDependency m_Dependencies[2]; + + // These are the vertices that have this vert in their m_Dependencies. + enum { NUM_REVERSE_DEPENDENCIES=4 }; + CVertDependency m_ReverseDependencies[NUM_REVERSE_DEPENDENCIES]; + + short m_iNodeLevel; // -1 if this is not a node. Otherwise, the recursion level + // of this node (root node = 1). + CVertIndex m_iParent; // x=-1 if this is a not a node or if it's the root node. +}; + + +class CTwoUShorts +{ +public: + unsigned short m_Values[2]; +}; + + +class CFourVerts +{ +public: + CVertIndex m_Verts[4]; +}; + + +// Used for referencing triangles in the fully-tesselated displacement by index. +class CTriInfo +{ +public: + unsigned short m_Indices[3]; +}; + + +// Precalculated data for displacements of a certain power. +class CPowerInfo +{ +public: + CPowerInfo( + CVertInfo *pVertInfo, + CFourVerts *pSideVerts, + CFourVerts *pChildVerts, + CFourVerts *pSideVertCorners, + CTwoUShorts *pErrorEdges, + CTriInfo *pTriInfos ); + + int GetPower() const { return m_Power; } + int GetSideLength() const { return m_SideLength; } + const CVertIndex& GetRootNode() const { return m_RootNode; } + int GetMidPoint() const { return m_MidPoint; } // Half the edge length. + + // Get at the tri list. + int GetNumTriInfos() const { return m_nTriInfos; } + const CTriInfo* GetTriInfo( int i ) const { return &m_pTriInfos[i]; } + + // Get the number of vertices in a displacement of this power. + int GetNumVerts() const { return m_MaxVerts; } + + // Return a corner point index. Indexed by the CORNER_ defines. + const CVertIndex& GetCornerPointIndex( int iCorner ) const; + + +public: + + CVertInfo *m_pVertInfo; + CFourVerts *m_pSideVerts; // The 4 side verts for each node. + CFourVerts *m_pChildVerts; // The 4 children for each node. + CFourVerts *m_pSideVertCorners; + CTwoUShorts *m_pErrorEdges; // These are the edges + // that are used to measure the screenspace + // error with respect to each vert. + + CTriInfo *m_pTriInfos; + int m_nTriInfos; + + int m_Power; + + CVertIndex m_RootNode; + int m_SideLength; + int m_SideLengthM1; // Side length minus 1. + int m_MidPoint; // Side length / 2. + int m_MaxVerts; // m_SideLength * m_SideLength + int m_NodeCount; // total # of nodes, including children + + // Precalculated increments if you're using a bit vector to represent nodes. + // Starting at level 0 of the tree, this stores the increment between the nodes at this + // level. Vectors holding node data are stored in preorder traversal, and these + // increments tell the number of elements between nodes at each level. + int m_NodeIndexIncrements[MAX_MAP_DISP_POWER]; + + CVertIndex m_EdgeStartVerts[4]; + CVertIndex m_EdgeIncrements[4]; + + CVertIndex m_NeighborStartVerts[4][4]; // [side][orientation] + CVertIndex m_NeighborIncrements[4][4]; // [side][orientation] + + +private: + friend void InitPowerInfo( CPowerInfo *pInfo, int iMaxPower ); + + CVertIndex m_CornerPointIndices[4]; +}; + + +// ----------------------------------------------------------------------------- // +// Globals. +// ----------------------------------------------------------------------------- // + +// Indexed by the TWINDING_ enums. +extern CTesselateWinding g_TWinding; + + +// ----------------------------------------------------------------------------- // +// Functions. +// ----------------------------------------------------------------------------- // + +// Valid indices are MIN_MAP_DISP_POWER through (and including) MAX_MAP_DISP_POWER. +const CPowerInfo* GetPowerInfo( int iPower ); + + +#endif // DISP_POWERINFO_H |