14 interpreter->
cursor = zero;
58 if (object->
flags == 0) {
59 second =
object->targetX;
62 first =
object->targetY;
64 first =
object->targetX;
67 if (first != second || object->
targetZ != first)
104 s32 maxTerrainChange;
111 objectsRemaining--,
object++) {
131 if (object->
wait != 0) {
145 object->scriptCursor++;
157 if (object->
frozen == 0) {
162 dx = (
object->targetX -
x) / 65536;
163 dy = (
object->targetY -
y) / 65536;
164 dz = (
object->targetZ -
z) / 65536;
174 object->velocityX += dx * ratio;
175 object->velocityY += dy * ratio;
176 object->velocityZ += dz * ratio;
191 dx =
object->velocityX;
192 dy =
object->velocityY;
193 dz =
object->velocityZ;
197 reducedSpeed = speed -
object->acceleration;
198 if (reducedSpeed < 0)
210 dx = (
object->targetX -
x) / 65536;
211 dz = (
object->targetZ -
z) / 65536;
217 if (distance <= 0x00ffffff) {
218 dx =
object->targetX -
x;
219 dz =
object->targetZ -
z;
240 dx =
object->velocityX;
241 dz =
object->velocityZ;
244 reducedSpeed = speed -
object->acceleration;
245 if (reducedSpeed < 0)
251 object->velocityX = 0;
252 object->velocityZ = 0;
266 velocityY = ground -
object->terrainHeight;
267 if (ground -
y > -0x40000)
271 maxTerrainChange =
object->acceleration / 2;
276 dx =
object->velocityX;
277 dy =
object->velocityY;
278 dz =
object->velocityZ;
283 if (reducedSpeed < 0)
290 object->terrainHeight = ground;
295 ground =
object->terrainHeight;
297 object->velocityY -=
object->gravity;
304 object->velocityY = 0;
310 phase = (
object->vertical.phase & 0x3f);
317 object->vertical.phase++;
322 x +=
object->velocityX;
323 y +=
object->velocityY;
324 z +=
object->velocityZ;
358 if (arrivedAtTarget != 0) {
361 object->velocityX = 0;
363 object->velocityZ = 0;
366 object->velocityY = 0;
372 object->arrivalAxis = 0;
380 x =
object->velocityX;
381 z =
object->velocityZ;
382 if (
x != 0 ||
z != 0) {
383 s32 maximumFacingStep;
386 maximumFacingStep = 0x1000;
387 if (facingStep > maximumFacingStep)
388 facingStep = maximumFacingStep;
389 maximumFacingStep = -0x1000;
390 if (facingStep < maximumFacingStep)
391 facingStep = maximumFacingStep;
392 object->facing += facingStep;
430 dx = (
x -
object->x) / 0x10000;
431 distance = (
y -
object->y) / 0x10000;
432 dz = (
z -
object->z) / 0x10000;
434 distance =
Iwram_Sqrt(dx * dx + distance * distance + squaredZ) << 16;
436 if (distance < 0x100000) {
438 distance =
y -
object->y;
444 if (distance < 0x10000) {
457 if (distance > brakingDistance)
458 brakingDistance = distance - brakingDistance / 2;
460 brakingDistance = distance / 2;
472 distance =
y -
object->y;
476 if ((dx < 0 ? -dx : dx) < (dz < 0 ? -dz : dz)) {
480 if (object->
flags == 0) {
483 if (dx < (distance < 0 ? -distance : distance))
490 void (*updateObjects)(void);
504 s32 objectsRemaining;
519 for (objectsRemaining = 13; objectsRemaining >= 0;
520 objectsRemaining--,
object++) {
532 if (object->
frozen == 0) {
539 dx = (
object->targetX -
x) / 65536;
540 dz = (
object->targetZ -
z) / 65536;
541 distance =
Iwram_Sqrt(dx * dx + dz * dz) << 16;
542 if (distance <= 0xffffff) {
543 dx =
object->targetX -
x;
544 dz =
object->targetZ -
z;
556 object->velocityZ = dx;
567 dx =
object->velocityX;
568 dz =
object->velocityZ;
569 if ((dx | dz) != 0) {
574 object->velocityX = 0;
575 object->velocityZ = 0;
583 object->velocityX = 0;
584 object->velocityZ = 0;
591 object->velocityY -=
object->gravity;
593 y =
object->terrainHeight;
598 object->velocityY = 0;
602 x +=
object->velocityX;
603 y +=
object->velocityY;
604 z +=
object->velocityZ;
624 if (arrivedAtTarget) {
626 object->velocityX = 0;
627 object->velocityZ = 0;
632 object->velocityY = 0;
638 object->arrivalAxis = 0;
643 x =
object->velocityX;
644 z =
object->velocityZ;
645 if (
x != 0 ||
z != 0) {
647 if (facingStep > 0x1000)
649 if (facingStep < -0x1000)
650 facingStep = -0x1000;
651 object->facing += facingStep;
const s32 gScriptObject_CycleTable[32]
One period of a triangle wave, which bobs a floating object up and down.
u8 Object_UpdateAllCodeSize[]
What every part of the field object shares: its includes and the few names more than one part uses.
#define TARGET_UNSET
A movement target coordinate that is not set.
void WaitFrames(s32 frames)
The game's frame loop: runs frames frames and returns.
static s32 Iwram_RatioMulQ14(s32 divisor, s32 value)
All calls go through this layer.
static s32 Iwram_Sqrt(s32 value)
#define Iwram_MulQ16(left, right)
#define SET_VELOCITY(p, vx, vy, vz)
#define SET_POSITION(p, px, py, pz)
Sets the position or the velocity of a particle, a piece of debris or an object in one statement.
#define SET_VECTOR(v, x, y, z)
Sets the x, y and z of a three-part vector: a position about to be projected, a per-frame step,...
s32 ArcTan2(s32 x, s32 y)
Returns the angle of the vector (x, y), in 1/65536 turns, measured from the y axis: 0 along +y,...
s32 FixedSqrt(s32 value)
Square root of a 16.16 fixed-point value, in 16.16.
void MemFree(void *buffer)
void Object_SetMoveTarget(struct ObjectRuntime *object, s32 x, s32 y, s32 z)
Sends an object towards (x, y, z), in 16.16 pixels.
UNUSED void Object_RunUpdateAllFromHeap(void)
Copies Object_UpdateAll (ARM code) to the heap, runs it once and frees it.
s32 Script_SetBase(struct ScriptInterpreter *interpreter)
SC_BASE: restarts the script at the next word, and returns 1 to run on.
s32 Script_ClearByte54(struct ScriptInterpreter *interpreter)
SC_B54_OFF: clears spriteStorageKind, hiding the sprites, and moves on to the next command.
s32 Object_IsTargetUnset(struct ObjectRuntime *object)
Returns 1 when the object has no movement target: none of its target coordinates set,...
s32 Script_SetByte54(struct ScriptInterpreter *interpreter)
SC_B54_ON: sets spriteStorageKind to 1, one sprite drawn, and moves on to the next command.
void FieldObject_WaitForMove(void *fieldObject)
Waits a frame at a time until a field object has arrived at its target, at most 600 frames.
void Object_UpdateAllThumb(void)
Advances all 64 field objects by one frame, as Object_UpdateAll does for the eight script objects,...
void Object_UpdateAllMotion(void)
Advances the first 14 objects' motion by one frame, without running their scripts: steering towards a...
void Object_SetPositionAndResetMotion(struct ObjectRuntime *object, s32 x, s32 y, s32 z)
Places the object at (x, y, z), in 16.16 pixels, clears its movement target and stops it.
static __inline__ s32 ObjectMotion_Square(s32 value)
const ScriptCommand gScriptObject_CommandTable[47]
The handler for each script command number; 0x24 onwards act as SC_END.
#define RamCode_Load(to, code, bytes)
Allocates a heap copy; release it with MemFree when finished.
s32 ScriptObject_CheckOverlap(struct ScriptObjectEntry *object, s32 *values)
Returns -1 when an object at position values would overlap a solid object (bit 0 of collisionFlags),...
One of the 64 field objects in the object pool (heap slot 5): its script, position,...
s32 targetZ
16.16 fixed-point pixels; 0x80000000 when unset
u8 snapToTarget
nonzero lands it exactly on its target
s32 z
16.16 fixed-point pixels
s32 acceleration
Added toward the target each frame, or taken off the speed when there is none, in 16....
u8 flags
FieldActor.motionFlags: 3 when created, 4 for a placed actor above the ground; zero is free flight in...
s32 x
16.16 fixed-point pixels
s32 speedLimit
16.16 fixed-point pixels per frame
s32 y
16.16 fixed-point pixels
The prefix that command handlers read from a field object's 0x70-byte slot.
u8 spriteStorageKind
FieldActor's spriteStorageKind: SC_B54_ON sets 1, one sprite drawn, and SC_B54_OFF sets 0,...
s16 cursor
the word index of the next command in script
const s32 * script
the running script; SC_END sets gScript_MainScript
A field object as the motion code sees it: its script, position, motion toward a target,...
s32 acceleration
Added toward the target each frame, or taken off the speed when there is none, in 16....
s32 terrainHeight
16.16 fixed-point pixels
s32 targetX
16.16 fixed-point pixels; 0x80000000 when unset
s32 x
16.16 fixed-point pixels
u8 arrivalAxis
the ARRIVAL_AXIS_* that decides arrival
u16 scriptCursor
in words; read signed
s32 velocityY
16.16 fixed-point pixels per frame
s32 speedLimit
16.16 fixed-point pixels per frame
u8 paused
nonzero skips its script and motion, not its hook
void(*) hook(union FieldObject *object)
Called each frame before its script.
u8 collisionFlags
bit 7: a solid object refuses its move
s32 velocityX
16.16 fixed-point pixels per frame
s32 targetY
16.16 fixed-point pixels; 0x80000000 when unset
u8 motionFlags
bits: 4 no slowdown on slopes | 3 bigger float | 2 floats | 1 falls | 0 follows the terrain; zero is ...
const ScriptMotionWords * script
null when the object is free
s32 gravity
Taken off velocityY each frame above the ground, 16.16 fixed-point pixels per frame; also scales a fl...
union ScriptMotionObject::@251026000204114031114155171320036163006104311101 vertical
u8 terrainId
the map layer whose ground height it follows
u8 steeringFlags
bit 0: turns toward its velocity, 1/16 turn a frame
s16 wait
frames left before its script runs again
u8 frozen
nonzero skips steering, terrain, gravity and floating
u8 snapToTarget
nonzero lands it exactly on its target
s32 y
16.16 fixed-point pixels
s32 z
16.16 fixed-point pixels
s32 targetZ
16.16 fixed-point pixels; 0x80000000 when unset
s32 velocityZ
16.16 fixed-point pixels per frame
The words of an object's script, as its script pointer reads them.
A field object as the script commands' overlap checks see it.
s32 Map_GetTerrainHeight(s32 layer, s32 x, s32 y)
Returns the ground height of a layer at (x, y) in 16.16 pixels: the height function of the cell's ter...
An object on the field, read as an actor or as an effect.
struct ScriptMotionObject * gObjectSlots
void Object_UpdateAll(void)
Advances the eight script-driven objects by one frame.