-
Notifications
You must be signed in to change notification settings - Fork 5
Curves
Curves are objects that define a path for other objects to follow.
Not to be confused with AnimCurv which also defines curves that objects can follow. That system is mainly used for animation sequences, while this one is used by objects that move during play, such as barrel grabbers.
Object ID 0x491, named "curve" but often referred to as "romcurve", handled by DLL 0x125.
These seem to always appear at the end of the romlist and use the acts0, loadFlags, acts1, bound, and cullDist fields differently. (TODO: investigate)
Despite the name, each object defines only one point; a curve is made from several points (and is also not really curved).
Their objdef parameters are:
Offs | Type | Description |
---|---|---|
0x18 | u8 | Action |
0x19 | u8 | Type |
0x1A | ? | ? |
0x1B | u8 | Flags |
0x1C | ObjectId | next1 |
0x20 | ObjectId | next2 |
0x24 | ObjectId | next3 |
0x28 | ObjectId | next4 |
0x2C | s8 | rotZ |
0x2D | s8 | rotY |
0x2E | s8 | rotX |
0x2F | ? | Probably padding |
0x30 | GameBit16 | Enable |
0x32 | GameBit16 | Disable |
- Action: tells the object what to do when it reaches this point. Values depend on the object.
- Type: used to find the correct curve. Has no effect on the curve itself; objects will look for a nearby curve of a specific type.
- Flags: used to disable some "next" points: (no idea why this exists)
- 0x01: disable next1
- 0x02: disable next2
- 0x04: disable next3
- 0x08: disable next4
- nextN: defines the actual path by specifying what Object Unique ID is the next curve to move toward from this one.
- rot: defines rotation, which can influence how some objects will follow the path.
- Enable: If not -1, specifies a GameBit which must be nonzero for the curve to be returned by certain "find nearby curve" functions.
- Disable: As above, but the GameBit must be zero.
Each point can have up to 4 "next" points, with unused entries set to -1. This allows for branching paths. An object chooses its next point like so:
- Copy every valid "next" point into a list
- A point is valid if:
- It is not the point the object came from to reach this one (prevents objects from bouncing back and forth between two points)
- It does not specify Object Unique ID -1, and
- Its disable flag is not set
- A point is valid if:
- If the path index is -1, return a random point from the list
- Otherwise, if the path index is >= the list's length, return the last entry in the list
- Otherwise, return the specified entry
This allows multiple paths to exist, which share some segments, without having to redundantly define those segments. (Though, there's no apparent benefit, but it might save some RAM?)
Usually, following each point's "next2" defines the "forward" path, and "next1" defines the "reverse" path (ie both are the same path in opposite directions), but there is no technical requirement for this convention, and it is not always followed.
A curve can have no "next" point (all "next" IDs set to -1); this is sometimes used to define a single target point for an object.
Known types:
- 0x01: Everything in Dragon Rock Bottom
- 0x02: WB (flying enemy)
- 0x03: HagabonMK2
- 0x15: DIM2PathGenerator
- 0x16: something important, as the DLL has a method that looks specifically for this type
- 0x19: Barrel grabbers in DarkIce Mines
- 0x1F: Tunnels you can crawl through
- while crawling you will follow the path exactly, even through the air
- action seems to be ignored
- 0x23: CurveFish
- 0x24: used by Tricky
- 0x2A: DrakorHoverPad
Objects can be quite fussy about following curves (and may not correctly account for lag) and wind up going backward, stopping, or getting completely lost if the curve isn't perfect. Some barrel grabbers have been observed getting lost even in an unmodified game.
DLL 0x14 (maybe called "network curve") is responsible for interpolating the romcurve data to calculate in-between positions. This has not been extensively researched.
There are at least three different types of curve. This is not related to the RomCurve Type field (used for objects to find their curves). Two of them are Hermite and Bezier; these require a multiple of four points, and appear to require the points to be define in order (point, control 1, control 2). The others don't use control points at all?
It's not clear whether all three types are actually used.