diff options
| author | robojumper <robojumper@gmail.com> | 2025-05-25 21:53:39 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2025-05-25 21:53:39 +0200 |
| commit | ae4573a236e59f966ea1197bebd8976ccb09e596 (patch) | |
| tree | 4dcb8e55213ac7c1755a4bbcadf517ccf2d480c6 /include | |
| parent | fd7d30d32283d03a412e8c401d04418351cf686a (diff) | |
| parent | 133ac12fcf28a8b475796169e7e7beb0de99bda5 (diff) | |
Merge pull request #175 from robojumper/d_path
d_path 33%
Diffstat (limited to 'include')
| -rw-r--r-- | include/d/a/obj/d_a_obj_dungeon_ship.h | 2 | ||||
| -rw-r--r-- | include/d/a/obj/d_a_obj_ivy_rope.h | 2 | ||||
| -rw-r--r-- | include/d/d_bzs_types.h | 33 | ||||
| -rw-r--r-- | include/d/d_room.h | 36 | ||||
| -rw-r--r-- | include/d/t/d_t_sound_area.h | 4 | ||||
| -rw-r--r-- | include/egg/math/eggRotation.h | 2 | ||||
| -rw-r--r-- | include/m/m_vec.h | 4 | ||||
| -rw-r--r-- | include/rvl/MTX/vec.h | 1 | ||||
| -rw-r--r-- | include/toBeSorted/actor_on_rail.h | 85 | ||||
| -rw-r--r-- | include/toBeSorted/d_path.h | 182 |
10 files changed, 246 insertions, 105 deletions
diff --git a/include/d/a/obj/d_a_obj_dungeon_ship.h b/include/d/a/obj/d_a_obj_dungeon_ship.h index d8106eb8..259b33d1 100644 --- a/include/d/a/obj/d_a_obj_dungeon_ship.h +++ b/include/d/a/obj/d_a_obj_dungeon_ship.h @@ -11,7 +11,7 @@ #include "nw4r/g3d/res/g3d_resfile.h" #include "s/s_State.hpp" #include "toBeSorted/actor_event.h" -#include "toBeSorted/actor_on_rail.h" +#include "toBeSorted/d_path.h" #include "toBeSorted/dowsing_target.h" #include "toBeSorted/d_emitter.h" #include "toBeSorted/time_proc.h" diff --git a/include/d/a/obj/d_a_obj_ivy_rope.h b/include/d/a/obj/d_a_obj_ivy_rope.h index 1f342416..c85d3ff4 100644 --- a/include/d/a/obj/d_a_obj_ivy_rope.h +++ b/include/d/a/obj/d_a_obj_ivy_rope.h @@ -12,7 +12,7 @@ #include "m/m_vec.h" #include "s/s_State.hpp" #include "toBeSorted/actor_event.h" -#include "toBeSorted/actor_on_rail.h" +#include "toBeSorted/d_path.h" #include "toBeSorted/attention.h" class dAcOivyRope_c : public dAcObjBase_c { diff --git a/include/d/d_bzs_types.h b/include/d/d_bzs_types.h index cf5264b4..638d98e0 100644 --- a/include/d/d_bzs_types.h +++ b/include/d/d_bzs_types.h @@ -24,10 +24,10 @@ struct AREA { // TODO: double check, copied from ss-tools // Size 0x28 struct BPNT { - /* 0x00 */ mVec3_c position1; - /* 0x0C */ mVec3_c position2; - /* 0x18 */ mVec3_c position3; - /* 0x24 */ u8 _0x24[4]; + /* 0x00 */ Vec position; + /* 0x0C */ Vec control1; + /* 0x18 */ Vec control2; + /* 0x24 */ u8 params[4]; }; // TODO: double check, copied from ss-tools @@ -99,15 +99,24 @@ struct OBJN { /* 0x00 */ u16 offset; }; +#define PATH_FLAG_WRAP_AROUND 1 +// 0 = spnt, pnt. 1 = bpnt, sbpt +#define PATH_FLAG_SPLINE 2 + // Size 0xC struct PATH { /* 0x00 */ u8 field_0x00; - /* 0x01 */ u8 field_0x01; + /* 0x01 */ u8 pathId; /* 0x02 */ u16 pointStartIndex; /* 0x04 */ u16 pointCount; - /* 0x06 */ u8 _0x06[4]; - /* 0x0A */ u8 firstBitIsWrapAround; + /* 0x06 */ u16 nextPath; + /* 0x08 */ u8 _0x08[2]; + /* 0x0A */ u8 flags; /* 0x0B */ u8 _0x0B[1]; + + u8 getNextId() const { + return nextPath; + } }; // Size 0x24 @@ -135,8 +144,8 @@ struct PLY { // Size 0x10 struct PNT { - /* 0x00 */ mVec3_c position; - /* 0x0C */ u8 _0x0C[4]; + /* 0x00 */ Vec position; + /* 0x0C */ u8 params[4]; }; // Size 0x4 @@ -170,14 +179,12 @@ struct SOBJ { /* 0x28 */ char name[8]; }; -// Size 0x??? -struct SBPT { - // ??? -}; // Parsed the same way in ss-tools typedef PNT SPNT; typedef PATH SPTH; +// Similarly accessed +typedef BPNT SBPT; // Size 0x14 struct STIF { diff --git a/include/d/d_room.h b/include/d/d_room.h index 30696fc2..287ae7c1 100644 --- a/include/d/d_room.h +++ b/include/d/d_room.h @@ -149,16 +149,40 @@ public: mpPath = path; } + const PATH *getPath(s32 off) const { + return mpPath + off; + } + + const u16 getPathCount() const { + return mPathCount; + } + + const SPTH *getSpth(s32 off) const { + return mpSpth + off; + } + + const u16 getSpthCount() const { + return mSpthCount; + } + void setPnt(const PNT *pnt, u16 count) { mPntCount = count; mpPnt = pnt; } + const PNT *getPnt(s32 off) const { + return mpPnt + off; + } + void setBpnt(const BPNT *bpnt, u16 count) { mBpntCount = count; mpBpnt = bpnt; } + const BPNT *getBpnt(s32 off) const { + return mpBpnt + off; + } + void setSpth(const SPTH *spth, u16 count) { mSpthCount = count; mpSpth = spth; @@ -169,14 +193,22 @@ public: mpSpnt = spnt; } + const SPNT *getSpnt(s32 off) const { + return mpSpnt + off; + } + void setSbpt(const SBPT *sbpt, u16 count) { mSbptCount = count; mpSbpt = sbpt; } - void setArea(const AREA *path, u16 count) { + const SBPT *getSbpt(s32 off) const { + return mpSbpt + off; + } + + void setArea(const AREA *area, u16 count) { mAreaCount = count; - mpArea = path; + mpArea = area; } void setPly(const PLY *ply, u16 count) { diff --git a/include/d/t/d_t_sound_area.h b/include/d/t/d_t_sound_area.h index 377adee4..0258f846 100644 --- a/include/d/t/d_t_sound_area.h +++ b/include/d/t/d_t_sound_area.h @@ -4,7 +4,7 @@ #include "d/t/d_tg.h" #include "m/m_mtx.h" #include "m/m_vec.h" -#include "toBeSorted/actor_on_rail.h" +#include "toBeSorted/d_path.h" class dTgSndAr_c : public dTg_c { public: @@ -27,7 +27,7 @@ private: bool checkAlg3(const mVec3_c &pos); mMtx_c mtx; - ActorOnRail mRail; + dPath_c mRail; }; #endif diff --git a/include/egg/math/eggRotation.h b/include/egg/math/eggRotation.h index 97910e97..b1e1e075 100644 --- a/include/egg/math/eggRotation.h +++ b/include/egg/math/eggRotation.h @@ -13,7 +13,7 @@ struct Rotation { mRot = other.mRot; } Rotation &operator=(const Rotation &other) { - mRot = val; + mRot = other.mRot; return *this; } Rotation &operator=(T val) { diff --git a/include/m/m_vec.h b/include/m/m_vec.h index 877da205..0fb52aea 100644 --- a/include/m/m_vec.h +++ b/include/m/m_vec.h @@ -196,6 +196,10 @@ public: return mVec3_c(x * f, y * f, z * f); } + friend mVec3_c operator*(f32 f, const mVec3_c &v) { + return mVec3_c(v.x * f, v.y * f, v.z * f); + } + /// @brief Scalar division operator. mVec3_c operator/(f32 f) const { f32 r = 1.0f / f; diff --git a/include/rvl/MTX/vec.h b/include/rvl/MTX/vec.h index a5b330dc..e220fa40 100644 --- a/include/rvl/MTX/vec.h +++ b/include/rvl/MTX/vec.h @@ -15,6 +15,7 @@ f32 PSVECMag(const Vec *); f32 PSVECDotProduct(const Vec *, const Vec *); void PSVECCrossProduct(const Vec *, const Vec *, Vec *); f32 PSVECSquareDistance(const Vec *, const Vec *); +f32 PSVECDistance(const Vec *, const Vec *); #define VECAdd PSVECAdd #define VECSubtract PSVECSubtract diff --git a/include/toBeSorted/actor_on_rail.h b/include/toBeSorted/actor_on_rail.h deleted file mode 100644 index b4e1924e..00000000 --- a/include/toBeSorted/actor_on_rail.h +++ /dev/null @@ -1,85 +0,0 @@ -#ifndef ACTOR_ON_RAIL_H -#define ACTOR_ON_RAIL_H - -#include "common.h" -#include "m/m_vec.h" - -class ActorOnRail { -private: - void *mpPathPtr; - int mRoomIndex; - u8 mPathSubtype; - -public: - /* 800A6690 */ - ActorOnRail(); - /* 800A66D0 */ - virtual ~ActorOnRail(); - - /* 800A6D90 */ - bool init(int pathIndex, int roomId, int pathSubtype); - /* 800A68B0 */ - mVec3_c *getPntPosForIndex(int index); - - void fn_800A7C80(int segmentIndex, mVec3_c &vec, f32 segmentFraction); -}; - -class ActorOnRail_Ext : public ActorOnRail { -public: - ActorOnRail_Ext(); - virtual ~ActorOnRail_Ext(); - - void setSegment(u16 segmentIndex, f32 segmentFraction); - bool initExt(int pathIndex, int roomId, int, int pathSegment, int pathSubtype, f32, f32, f32); - void fn_800A9650(); - - s32 getSegmentIndex() const { - return mSegmentIndex; - } - - f32 getSegmentFraction() const { - return mSegmentFraction; - } - - bool CheckFlag(u32 flag) const { - return (field_0x1C & flag) != 0; - } - - void ClearFlag(u32 flag) { - field_0x1C &= ~flag; - } - - void SetFlag(u32 flag) { - field_0x1C |= flag; - } - - const mVec3_c &getPosition() const { - return mPosition; - } - - void setSpeed(f32 speed) { - mSpeed = speed; - } - - - -private: - s32 mSegmentIndex; - f32 mSegmentFraction; - f32 mSpeed; - u32 field_0x1C; - f32 field_0x20; - UNKWORD field_0x24; - mVec3_c mPosition; -}; - -class ActorOnRail3 { - ActorOnRail mPath; - u16 mSomePntIdx; - u32 mFlags; - -public: - ActorOnRail3() : mSomePntIdx(0), mFlags(0) {} -}; - -#endif diff --git a/include/toBeSorted/d_path.h b/include/toBeSorted/d_path.h new file mode 100644 index 00000000..38891596 --- /dev/null +++ b/include/toBeSorted/d_path.h @@ -0,0 +1,182 @@ +#ifndef D_PATH_H +#define D_PATH_H + +#include "common.h" +#include "d/d_bzs_types.h" +#include "m/m_vec.h" + +/** + * A dPath_c describes a parametric 3D curve in a stage. + * This base path class provides read-only evaluation of the curve. + * + * A path consists of a number of points that this curve passes through. + * Paths can have two ends, or wrap around, connecting the end point with the start point again. + * The curve can either linearly connect the points, or it can be implemented as a spline + * (splines are used for certain actors where smooth movement is necessary, e.g. Sandship). + * + * A curve point (or the segment between that point and the next) is identified by an integer point index [0; n-1], and + * each segment itself is parametrized by a float parameter in [0.0; 1.0]. We call this parameter "time", though since + * no requirements are imposed on the distance between points, there is no guarantee of constant speed across the curve. + * ActorOnRail_Ext (todo rename) provides calculations that allow actors to move along the curve with constant speed. + */ +class dPath_c { +private: + const PATH *mpPathPtr; + s32 mRoomIndex; + bool mPathSubtype; + + /** Must only be called for spline paths. Extracts the relevant path points and control points for the given segment. */ + bool extractControlPoints( + s32 pointIndex, mVec3_c &currPos, mVec3_c &currControl2, mVec3_c &nextControl1, mVec3_c &nextPos + ) const; + + /** + * Check if the given path segment is a linear segment - even splines can have linear segments! + * This can speed up some calculations. + */ + bool isLinearSegment(s32 pointIndex) const; + + void set(const PATH *path, s32 roomIndex, bool subtype); + + const PNT *getPathPoint(s32 pointIndex) const; + const BPNT *getPathBpoint(s32 pointIndex) const; + +public: + /* 800A6690 */ + dPath_c(); + /* 800A66D0 */ + virtual ~dPath_c(); + + bool isWrapping() const { + return mpPathPtr->flags & PATH_FLAG_WRAP_AROUND; + } + + bool isLinear() const { + return (mpPathPtr->flags & PATH_FLAG_SPLINE) == 0; + } + + s32 getNumPoints() const { + return mpPathPtr->pointCount; + } + + /* 800A6D90 */ + bool initWithPathId(s32 pathId, s32 roomId, bool pathSubtype); + bool initWithPathIndex(s32 pathIndex, s32 roomId, bool pathSubtype); + + void clear(); + + + /** Get a given point that the curve passes through. */ + const Vec *getPoint(s32 pointIndex) const; + /** Evaluates the curve position for the given segment and time. */ + void getPoint(s32 pointIndex, f64 time, mVec3_c &out) const; + /** Extract point param - TODO what is this used for? */ + u8 getPointParam(s32 pointIndex, s32 param) const; + + /** Return the index of this PATH in the current room. */ + u16 getMyPathIndex(s32 roomId) const; + /** Apparently paths can be linked somehow. */ + bool getNextPath(dPath_c *next) const; + + /** + * Approximate the time for the given distance along the segment. + * The return value is clamped to [0.0, 1.0]. If the distance exceeds + * the length of this segment, write the excess to the provided pointer. + */ + f32 getSegmentTime(s32 pointIndex, f32 segmentDistance, f32 stepSize, f32 *excess); + + /** + * Approximates the distance already traveled on the given segment for the given time. + * Calling this with time == 1.0f returns the segment length. + * Higher resolution -> higher accuracy. + */ + f32 getDistanceMovedOnSegment(s32 pointIndex, s32 resolution, f32 time) const; + /** Calculates the normalized direction of an actor moving along the segment for the given time. */ + bool getDirection(s32 segmentIndex, f32 time, mVec3_c &result) const; + /** Calculates the speed (scalar) of an actor moving along the segment at the given time. */ + bool getSpeed(s32 segmentIndex, f32 time, f32 *result) const; + /** Calculates the velocity (vector) of an actor moving along the segment at the given time. */ + bool getVelocity(s32 segmentIndex, f32 time, mVec3_c &result) const; + +}; + +/** A stateful "path driver" that moves along a given path with a given speed. */ +class ActorOnRail_Ext { +public: + ActorOnRail_Ext(); + ~ActorOnRail_Ext(); + + f32 getRemainingDistanceOnSegment() const; + s32 getClosestXZPoint(const mVec3_c &) const; + void setSegment(s32 segmentIndex, f32 segmentTime); + bool init(s32 pathIndex, s32 roomId, u32 flags, s32 segmentIndex, bool pathSubtype, f32 segmentTime, f32 speed, f32 unk); + s32 execute(); + + s32 getSegmentIndex() const { + return mSegmentIndex; + } + + f32 getSegmentTime() const { + return mSegmentTime; + } + + bool CheckFlag(u32 flag) const { + return (mFlags & flag) != 0; + } + + void ClearFlag(u32 flag) { + mFlags &= ~flag; + } + + void SetFlag(u32 flag) { + mFlags |= flag; + } + + const mVec3_c &getPosition() const { + return mPosition; + } + + void setSpeed(f32 speed) { + mSpeed = speed; + } + + void getDirection(mVec3_c &result) { + mPath.getDirection(mSegmentIndex, mSegmentTime, result); + } + + bool checkFlag(u32 flags) const { + return (mFlags & flags) != 0; + } + + void offFlag(u32 flags) { + mFlags &= ~flags; + } + + void onFlag(u32 flags) { + mFlags |= flags; + } + +private: + s32 getNextPointIndex(s32 point) const; + s32 getNextPointIndex() const; + + /* 0x00 */ dPath_c mPath; + /* 0x10 */ s32 mSegmentIndex; + /* 0x14 */ f32 mSegmentTime; + /* 0x18 */ f32 mSpeed; + /* 0x1C */ u32 mFlags; + /* 0x20 */ f32 field_0x20; + /* 0x24 */ f32 mSegmentDistance; + /* 0x28 */ mVec3_c mPosition; +}; + +class ActorOnRail3 { + /* 0x00 */ dPath_c mPath; + /* 0x10 */ u16 mSomePntIdx; + /* 0x14 */ u32 mFlags; + +public: + ActorOnRail3() : mSomePntIdx(0), mFlags(0) {} +}; + +#endif |
