tge/lib/maxsdk31/polyshp.h
2025-02-17 23:17:30 -06:00

268 lines
10 KiB
C++
Executable File

/**********************************************************************
*<
FILE: polyshp.h
DESCRIPTION: Polyline shape methods
CREATED BY: Tom Hudson
HISTORY: Created 3 October 1995
*> Copyright (c) 1995, All Rights Reserved.
**********************************************************************/
#ifndef __POLYSHP_H_
#define __POLYSHP_H_
#include "shphier.h"
#include "captypes.h"
#include "shpsels.h" // Shape selection classes
#include "templt.h"
// Display flags
#define DISP_VERTTICKS (1<<0)
//#define DISP_BEZHANDLES (1<<1)
#define DISP_SELVERTS (1<<10)
#define DISP_SELSEGMENTS (1<<11)
#define DISP_SELPOLYS (1<<13)
// Snap flags
#define PSHAPE_SNAP_IGNORELAST (1<<0)
#define PSHAPE_SNAP_NOEDGES (1<<1)
// Selection level bits.
#define SHAPE_OBJECT (1<<0)
#define SHAPE_SPLINE (1<<1)
#define SHAPE_SEGMENT (1<<2)
#define SHAPE_VERTEX (1<<3)
// Parameter types for shape interpolation (Must match interpolation types in object.h)
#define POLYSHP_INTERP_SIMPLE 0 // Parameter space based on segments
#define POLYSHP_INTERP_NORMALIZED 1 // Parameter space normalized to curve length
// Flags for sub object hit test
// NOTE: these are the same bits used for object level.
#define SUBHIT_SHAPE_SELONLY (1<<0)
#define SUBHIT_SHAPE_UNSELONLY (1<<2)
#define SUBHIT_SHAPE_ABORTONHIT (1<<3)
#define SUBHIT_SHAPE_SELSOLID (1<<4)
#define SUBHIT_SHAPE_VERTS (1<<24)
#define SUBHIT_SHAPE_SEGMENTS (1<<25)
#define SUBHIT_SHAPE_POLYS (1<<26)
#define SUBHIT_SHAPE_TYPEMASK (SUBHIT_SHAPE_VERTS|SUBHIT_SHAPE_SEGMENTS|SUBHIT_SHAPE_POLYS)
class Spline3D;
//--------------------------------------------------------------
// Capping classes, etc.
// CapVert flags
#define CAPVERT_VISEDGE (1<<0)
class CapVert {
public:
int vert;
DWORD flags;
float ang;
CapVert *prev,*next;
CapVert *smaller,*bigger;
CapVert() { vert=0; flags = 0; ang = 0.0f; prev=next=smaller=bigger = NULL; }
};
//--------------------------------------------------------------
// Predefined PolyPt flags
// Bits 0-7 are available to the user. Bits 8-31 are reserved for internal use
// Use these to make capping more efficient
// If your class converts to a PolyLine, use them!
#define POLYPT_KNOT (1<<8) // A control point
#define POLYPT_INTERPOLATED (1<<9) // An interpolated point
// If you convert to a PolyLine, use this bit to control smoothing of the resulting shape
// If this bit is set, it means that any mesh generated will share smoothing across the edge
#define POLYPT_SMOOTH (1<<10) // Point is part of a smooth transition
#define POLYPT_SEG_SELECTED (1<<11) // The segment that starts with this point is selected
// Used internally by capping code
#define POLYPT_BRIDGE (1<<16) // Span between two polygons
#define POLYPT_SPLICE (1<<17) // Point is endpoint of a bridge
#define POLYPT_VISEDGE (1<<18) // Segment should be visible on mesh
#define POLYPT_NO_SPLICE (1<<19) // Don't allow a bridge at this point
#define POLYPT_INVIS_EDGE (1<<20) // Force segment to be invisible on capping
// Flags2 field contains material IDs:
// The mat ID is stored in the HIWORD of the PolyPt flags2 field
#define POLYPT_MATID_SHIFT 16
#define POLYPT_MATID_MASK 0xFFFF
class PolyPt {
public:
Point3 p;
DWORD flags; // See above
DWORD flags2; // See above
int aux; // Auxiliary data attached to this point (usually mesh vertex number for capping)
PolyPt() { p = Point3(0,0,0); flags = 0; flags2 = 0; aux = 0; }
PolyPt(Point3 ip, DWORD f=0, int a=0, DWORD f2=0) { p = ip; flags = f; aux = a; flags2 = f2;}
inline MtlID GetMatID() {return (int)((flags2>>POLYPT_MATID_SHIFT)&POLYPT_MATID_MASK);}
inline void SetMatID(MtlID id) {flags2 &= 0xFFFF; flags2 |= (DWORD)(id<<POLYPT_MATID_SHIFT);}
};
// PolyLine::Cap3DS / PolyShape::Make3DSCap options
#define CAP3DS_OPT_CLOSEST_BRIDGE (1<<0) // Bridge polys at closest point
// PolyLine flags
#define POLYLINE_CLOSED (1<<0)
#define POLYLINE_NO_SELF_INT (1<<1) // Ignore self-intersections (special!)
class PolyLine {
public:
int numPts;
PolyPt *pts;
DWORD flags;
Box3 bdgBox;
float cachedLength;
float *lengths; // Cached lengths for each point
float *percents; // Cached percentages for each point
BOOL cacheValid;
CoreExport PolyLine();
CoreExport PolyLine(PolyLine& from);
CoreExport ~PolyLine();
CoreExport void Init();
void Close() { flags |= POLYLINE_CLOSED; }
CoreExport BOOL IsClosed();
void Open() { flags &= ~POLYLINE_CLOSED; }
CoreExport BOOL IsOpen();
void SetNoSelfInt() { flags |= POLYLINE_NO_SELF_INT; }
BOOL IsNoSelfInt() { return (flags & POLYLINE_NO_SELF_INT) ? TRUE : FALSE; }
int Verts() { return numPts; }
CoreExport int Segments();
CoreExport BOOL SetNumPts(int count, BOOL keep = TRUE);
CoreExport void Append(PolyPt& p);
CoreExport void Insert(int where, PolyPt& p);
CoreExport void Delete(int where);
CoreExport void Reverse(BOOL keepZero=FALSE);
CoreExport PolyLine& operator=(PolyLine& from);
CoreExport PolyLine& operator=(Spline3D& from);
CoreExport PolyPt& operator[](int index) { return pts[index]; }
CoreExport void BuildBoundingBox(void);
CoreExport void InvalidateGeomCache();
CoreExport Box3 GetBoundingBox(Matrix3 *tm=NULL); // RB: optional TM allows the box to be calculated in any space.
CoreExport void Render(GraphicsWindow *gw, Material *ma, RECT *rp, int compFlags, int numMat);
CoreExport void Render(GraphicsWindow *gw, Material *ma, int numMat, BOOL colorSegs, BitArray &segsel);
CoreExport BOOL Select(GraphicsWindow *gw, Material *ma, HitRegion *hr, int abortOnHit = FALSE);
CoreExport void Snap(GraphicsWindow *gw, SnapInfo *snap, IPoint2 *p, Matrix3 &tm, DWORD flags);
CoreExport void Transform(Matrix3 &tm);
CoreExport void Dump(TCHAR *title = NULL);
CoreExport void SpliceLine(int where, PolyLine &source, int splicePoint);
CoreExport BOOL HitsSegment(Point2 p1, Point2 p2, BOOL findAll = FALSE, IntersectionCallback3D *cb = NULL);
CoreExport int Cap3DS(CapVert *capverts, MeshCapInfo &capInfo, DWORD options = 0);
CoreExport BOOL HitsPolyLine(PolyLine &line, BOOL findAll = FALSE, IntersectionCallback3D *cb = NULL);
CoreExport BOOL SurroundsPoint(Point2 &point);
CoreExport Point3 InterpPiece3D(int segment, float t);
CoreExport Point3 InterpCurve3D(float u, int ptype=POLYSHP_INTERP_SIMPLE);
CoreExport Point3 TangentPiece3D(int segment, float t);
CoreExport Point3 TangentCurve3D(float u, int ptype=POLYSHP_INTERP_SIMPLE);
CoreExport MtlID GetMatID(int segment);
CoreExport float CurveLength();
CoreExport BOOL IsClockWise(); // 2D!
CoreExport BOOL SelfIntersects(BOOL findAll = FALSE, IntersectionCallback3D *cb = NULL); // 2D!
CoreExport void GetSmoothingMap(IntTab &map);
// IO
CoreExport IOResult Save(ISave *isave);
CoreExport IOResult Load(ILoad *iload);
};
#define CAPFACE_AB (1<<0)
#define CAPFACE_BC (1<<1)
#define CAPFACE_CA (1<<2)
class ShapeObject;
// Options for steps in MakePolyShape (>=0: Use fixed steps)
// NOTE: DO NOT change these defines -- They're also used by ShapeObject (object.h)
#define PSHAPE_BUILTIN_STEPS -2 // Use the shape's built-in steps/adaptive settings (default)
#define PSHAPE_ADAPTIVE_STEPS -1 // Force adaptive steps
class PolyShape {
public:
int numLines;
PolyLine *lines;
DWORD flags;
Box3 bdgBox;
// Selection
ShapeVSel vertSel; // selected vertices
ShapeSSel segSel; // selected segments
ShapePSel polySel; // selected polygons
// Selection level
DWORD selLevel;
// Display attribute flags
DWORD dispFlags;
// Capping caches
MeshCapInfo morphCap;
BOOL morphCapCacheValid;
MeshCapInfo gridCap;
BOOL gridCapCacheValid;
PatchCapInfo patchCap;
BOOL patchCapCacheValid;
// Hierarchy cache
ShapeHierarchy cachedHier;
BOOL hierCacheValid;
CoreExport PolyShape();
CoreExport PolyShape(PolyShape& from);
CoreExport ~PolyShape();
CoreExport void Init(); // Used by constructors
CoreExport void NewShape(); // Deletes all lines
CoreExport BOOL SetNumLines(int count, BOOL keep = TRUE);
CoreExport PolyLine* NewLine();
CoreExport void Append(PolyLine &l);
CoreExport void Insert(int where, PolyLine& l);
CoreExport void Delete(int where);
CoreExport PolyShape& operator=(PolyShape& from);
CoreExport PolyShape& operator=(BezierShape& from);
CoreExport void BuildBoundingBox(void);
CoreExport void InvalidateGeomCache(BOOL unused); // Also invalidates capping caches
CoreExport void InvalidateCapCache();
CoreExport Box3 GetBoundingBox(Matrix3 *tm=NULL); // RB: optional TM allows the box to be calculated in any space.
CoreExport void GetDeformBBox(TimeValue t, Box3& box, Matrix3 *tm, BOOL useSel );
CoreExport void Render(GraphicsWindow *gw, Material *ma, RECT *rp, int compFlags, int numMat);
CoreExport BOOL Select(GraphicsWindow *gw, Material *ma, HitRegion *hr, int abortOnHit = FALSE);
CoreExport void Snap(GraphicsWindow *gw, SnapInfo *snap, IPoint2 *p, Matrix3 &tm);
CoreExport void Snap(GraphicsWindow *gw, SnapInfo *snap, IPoint2 *p, Matrix3 &tm, DWORD flags);
CoreExport void Transform(Matrix3 &tm);
CoreExport int MakeCap(TimeValue t, MeshCapInfo &capInfo, int capType);
CoreExport int MakeCap(TimeValue t, PatchCapInfo &capInfo);
CoreExport int Make3DSCap(MeshCapInfo &capInfo, DWORD options = 0);
CoreExport int MakeGridCap(MeshCapInfo &capInfo);
CoreExport void Dump(TCHAR *title = NULL);
CoreExport void UpdateCachedHierarchy();
CoreExport ShapeHierarchy &OrganizeCurves(TimeValue t, ShapeHierarchy *hier = NULL);
CoreExport void UpdateSels();
CoreExport void Reverse(int poly, BOOL keepZero=FALSE);
CoreExport void Reverse(BitArray &reverse, BOOL keepZero=FALSE);
CoreExport MtlID GetMatID(int poly, int piece);
// Constructs a vertex selection list based on the current selection level.
CoreExport BitArray VertexTempSel(int poly);
// functions for use in data flow evaluation
CoreExport void ShallowCopy(PolyShape *ashape, unsigned long channels);
CoreExport void DeepCopy(PolyShape *ashape, unsigned long channels);
CoreExport void NewAndCopyChannels(unsigned long channels);
CoreExport void FreeChannels( unsigned long channels, int zeroOthers=1);
// IO
CoreExport IOResult Save(ISave *isave);
CoreExport IOResult Load(ILoad *iload);
};
#endif // __POLYSHP_H_