diff --git a/Doxyfile b/Doxyfile index 4239ac9a..ea24a7eb 100644 --- a/Doxyfile +++ b/Doxyfile @@ -386,7 +386,7 @@ IDL_PROPERTY_SUPPORT = YES # all members of a group must be documented explicitly. # The default value is: NO. -DISTRIBUTE_GROUP_DOC = NO +DISTRIBUTE_GROUP_DOC = YES # If one adds a struct or class to a group and this option is enabled, then also # any nested class or struct is added to the same group. By default this option diff --git a/asm/enemy.s b/asm/enemy.s index d8bdd174..899451cb 100644 --- a/asm/enemy.s +++ b/asm/enemy.s @@ -18,7 +18,7 @@ EnemyUpdate: @ 0x080011C4 bne _080011EA bl DeleteThisEntity _080011DC: - bl CheckDontUpdate + bl EntityIsDeleted cmp r0, #0 bne _0800120A adds r0, r4, #0 diff --git a/asm/non_matching/arm_proxy/NPCUpdate.inc b/asm/non_matching/arm_proxy/NPCUpdate.inc index 3f6098ff..67ad06ec 100644 --- a/asm/non_matching/arm_proxy/NPCUpdate.inc +++ b/asm/non_matching/arm_proxy/NPCUpdate.inc @@ -26,7 +26,7 @@ _08017550: bl NPCInit _08017566: adds r0, r4, #0 - bl CheckDontUpdate + bl EntityIsDeleted cmp r0, #0 bne _08017584 ldr r2, _080175DC @ =gNPCFunctions diff --git a/asm/object/object11.s b/asm/object/object11.s index 2c8211d8..9974cab4 100644 --- a/asm/object/object11.s +++ b/asm/object/object11.s @@ -11,7 +11,7 @@ Object11: @ 0x08084D34 push {r4, lr} adds r4, r0, #0 - bl CheckDontUpdate + bl EntityIsDeleted cmp r0, #0 bne _08084D50 ldr r0, _08084D54 @ =gUnk_0812057C diff --git a/asm/object/object1E.s b/asm/object/object1E.s index 81b20f1a..3791f55e 100644 --- a/asm/object/object1E.s +++ b/asm/object/object1E.s @@ -11,7 +11,7 @@ Object1E: @ 0x08087504 push {r4, lr} adds r4, r0, #0 - bl CheckDontUpdate + bl EntityIsDeleted cmp r0, #0 bne _08087520 ldr r0, _08087524 @ =gUnk_081208B8 diff --git a/asm/projectileUpdate.s b/asm/projectileUpdate.s index 9defa1b5..590744ce 100644 --- a/asm/projectileUpdate.s +++ b/asm/projectileUpdate.s @@ -18,7 +18,7 @@ ProjectileUpdate: @ 0x08016AE4 bne _08016B0A bl DeleteThisEntity _08016AFC: - bl CheckDontUpdate + bl EntityIsDeleted cmp r0, #0 bne _08016B22 adds r0, r4, #0 diff --git a/include/common.h b/include/common.h index 6b4763c4..62f3acba 100644 --- a/include/common.h +++ b/include/common.h @@ -5,72 +5,112 @@ struct Entity_; +/** + * Holds input information from system registers. + */ typedef struct { - u16 heldKeys; - u16 newKeys; + u16 heldKeys; /**< Keys held since last frame. */ + u16 newKeys; /** Keys newly pressed this frame. */ u16 unk4; u8 unk6; u8 unk7; } Input; -extern Input gInput; +extern Input gInput; /**< Input instance. */ void LoadPalettes(const u8*, s32, s32); + +/** + * Loads a packed group of palettes. + * + * @param group Group number. + */ void LoadPaletteGroup(u32 group); + +/** + * Loads a packed group of tiles. + * + * @param group Group number. + */ void LoadGfxGroup(u32 group); + +/** + * Set color in the palette. + * + * @param colorIndex Color index. + * @param color Color. + */ void SetColor(u32 colorIndex, u32 color); + void SetFillColor(u32 color, u32 arg1); /** * Fill memory with 16 bit value. + * + * @param value Fill value. + * @param dest Destination. + * @param size Byte count. */ void MemFill16(u32 value, void* dest, u32 size); /** * Fill memory with 32 bit value. + * + * @param value Fill value. + * @param dest Destination. + * @param size Byte count. */ void MemFill32(u32 value, void* dest, u32 size); /** * Clear memory. + * + * @param dest Destination + * @param size Byte count. */ void MemClear(void* dest, u32 size); /** * Copy memory. + * + * @param src Source. + * @param dest Destination. + * @param size Byte count. */ void MemCopy(const void* src, void* dest, u32 size); /** - * Refresh gInput from hardware registers. + * Refresh #gInput from system registers. */ void ReadKeyInput(void); +/** + * Initialize the heap. + */ void zMallocInit(void); /** * Allocate memory on heap. * * The heap size is 0x1000 bytes and should be used sparingly. - * It is customary for entities store the returned handle in their 'myHeap' field. + * It is customary for entities store the returned pointer in the Entity.myHeap field. * - * @param size u32 Size to be allocated - * @return void* Pointer to allocated memory + * @param size u32 Size to be allocated. + * @return Pointer to allocated memory. */ void* zMalloc(u32 size); /** * Free memory from heap. + * The Entity system will automatically free the pointer stored in the Entity.myHeap field. * - * The entity system will automatically free the address stored in the 'myHeap' field. - * - * @param ptr void* Handle to be freed + * @param ptr Pointer to be freed. */ void zFree(void* ptr); /** - * Reset All display hardware registers. + * Reset All display system registers. * - * @param refresh bool32 Request refresh of HUD layer (bg 0) + * @param refresh Request refresh of HUD layer (bg 0). */ void DispReset(bool32 refresh); diff --git a/include/entity.h b/include/entity.h index 7d61134e..1e5f8f41 100644 --- a/include/entity.h +++ b/include/entity.h @@ -8,15 +8,68 @@ #define MAX_ENTITIES 71 +/** Kinds of Entity's supported by the game. */ +enum EntityKind { + PLAYER = 1, /**< There is only one id assigned to the Player kind. + * The player Entity shares much of its code with LTTP GBA, however the game only supports + * one player Entity active at a time, assigned to the global #gPlayerEntity. + * Works next to PlayerState to control player behavior. + */ + ENEMY = 3, /**< Can give and take damage in relation to the player. + * Most enemies call the a set of external helper functions which calculate what behavior to execute. + */ + PROJECTILE = 4, /**< May damage the player. They are typically spawned by enemies. + */ + OBJECT = 6, /**< Encapsulates any sort of prop. Generally they cannot be interacted with directly, + * but they may react to a player action or script event. + */ + NPC = 7, /**< May be interacted with by the player. Almost every NPC is assigned a script. + * NPCs have three entry points: one for the head, one for the body, and one for kinstone fusion. + */ + PLAYER_ITEM = 8, /**< Displays sprites for items outside of the inventory (check). + */ + MANAGER = 9, /**< Utility Entity's that serve as a proxy between gameplay and the engine. + * Examples: drawing clouds, ezlo hints, playing cutscenes. + * Updates independently of other entities, and does not add to maximum entity count. + */ +}; + +/** Entity flags. */ +enum EntityFlags { + ENT_DID_INIT = 0x1, /**< Graphics and other data loaded. */ + ENT_SCRIPTED = 0x2, /**< Execute in a scripted environment. */ + ENT_DELETED = 0x10, /**< Queue deletion next frame. */ + ENT_PERSIST = 0x20, /**< Persist between rooms. */ + ENT_COLLIDE = 0x80, /**< Collide with other Entity's. */ +}; + +/** Priority level to determine what events will block an Entity from updating. */ typedef enum { - PLAYER = 1, - ENEMY = 3, - PROJECTILE = 4, - OBJECT = 6, - NPC = 7, - PLAYER_ITEM = 8, - MANAGER = 9, -} EntityType; + PRIO_MIN, /**< Default priority. */ + PRIO_PLAYER, /**< Default priority for player. */ + PRIO_MESSAGE, /**< Do not block during message. */ + PRIO_NO_BLOCK, /**< Do not block during entity requested priority. @see RequestPriority */ + PRIO_4, /**< Unused. */ + PRIO_5, /**< Unused. */ + PRIO_PLAYER_EVENT, /**< Do not block during special player event. */ + PRIO_HIGHEST, /**< Do not block EVER. */ +} Priority; + +/** Animation state. */ +enum AnimationState { + IdleNorth = 0x0, /**< Idle facing north. */ + IdleEast = 0x2, /**< Idle facing east. */ + IdleSouth = 0x4, /**< Idle facing south. */ + IdleWest = 0x6, /**< Idle facing west. */ +}; + +/** Direction. */ +enum Direction { + DirectionNorth = 0x00, /**< North. */ + DirectionEast = 0x08, /**< East. */ + DirectionSouth = 0x10, /**< South. */ + DirectionWest = 0x18, /**< West. */ +}; typedef struct { void* entity1; @@ -24,6 +77,9 @@ typedef struct { u8 filler[14]; } UnkStruct; +/** + * Hitbox structure. + */ typedef struct { s8 offset_x; s8 offset_y; @@ -32,6 +88,9 @@ typedef struct { u8 height; } Hitbox; +/** + * Hitbox structure supporting depth. + */ typedef struct { s8 offset_x; s8 offset_y; @@ -42,38 +101,41 @@ typedef struct { u8 unknown2[3]; } Hitbox3D; +/** + * Container for instantiable behavior. + */ typedef struct Entity_ { - /*0x00*/ struct Entity_* prev; - /*0x04*/ struct Entity_* next; - /*0x08*/ u8 kind; - /*0x09*/ u8 id; - /*0x0a*/ u8 type; - /*0x0b*/ u8 type2; - /*0x0c*/ u8 action; - /*0x0d*/ u8 subAction; - /*0x0e*/ u8 actionDelay; - /*0x0f*/ u8 field_0xf; - /*0x10*/ u8 flags; - /*0x11*/ u8 updatePriority : 4; // Current priority -- See RequestPriority - /* */ u8 updatePriorityPrev : 4; // Priority to restore after request is over + /*0x00*/ struct Entity_* prev; /**< previous Entity */ + /*0x04*/ struct Entity_* next; /**< next Entity */ + /*0x08*/ u8 kind; /**< @see EntityKind */ + /*0x09*/ u8 id; /**< Entity id. */ + /*0x0a*/ u8 type; /**< For use internally to allow different variations. */ + /*0x0b*/ u8 type2; /**< For use internally. */ + /*0x0c*/ u8 action; /**< Current action. Usually used to index a function table. */ + /*0x0d*/ u8 subAction; /**< Optional sub-action. */ + /*0x0e*/ u8 actionDelay; /**< General purpose timer. */ + /*0x0f*/ u8 field_0xf; /**< General purpose timer. */ + /*0x10*/ u8 flags; /**< @see EntityFlags */ + /*0x11*/ u8 updatePriority : 4; /**< Current priority. @see Priority */ + /* */ u8 updatePriorityPrev : 4; /**< Priority to restore after request is over. @see RequestPriority. */ /*0x12*/ s16 spriteIndex; - /*0x14*/ u8 animationState; - /*0x15*/ u8 direction; + /*0x14*/ u8 animationState; /**< Animation state. @see AnimationState */ + /*0x15*/ u8 direction; /**< Facing direction. @see Direction */ /*0x16*/ u8 field_0x16; /*0x17*/ u8 field_0x17; /*0x18*/ struct { - /* */ u32 draw : 2; // 0 = no draw, 1 = draw clip, 3 = force draw - /* */ u32 ss2 : 1; // 4 - /* */ u32 ss3 : 1; // 8 - /* */ u32 shadow : 2; //0x10-0x20 - /* */ u32 flipX : 1; //0x40 - /* */ u32 flipY : 1; //0x80 + /* */ u32 draw : 2; /**< Draw type. 0 = disabled, 1 = clip to screen, 3 = draw always */ /* 0x2 */ + /* */ u32 ss2 : 1; /* 4 */ + /* */ u32 ss3 : 1; /* 8 */ + /* */ u32 shadow : 2; /* 0x10-0x20 */ + /* */ u32 flipX : 1; /**< Flip sprite horizontally. */ /* 0x40 */ + /* */ u32 flipY : 1; /**< Flip sprite vertically. */ /* 0x80 */ /* */ } PACKED spriteSettings; /*0x19*/ struct { - /* */ u32 b0 : 2; // 1-2 - /* */ u32 alphaBlend : 2; // 4-8 - /* */ u32 b2 : 2; //0x10 - /* */ u32 b3 : 2; //0x40 + /* */ u32 b0 : 2; /* 1-2 */ + /* */ u32 alphaBlend : 2; /* 4-8 */ + /* */ u32 b2 : 2; /* 0x10 */ + /* */ u32 b3 : 2; /* 0x40 */ /* */ } PACKED spriteRendering; /*0x1a*/ union { /* */ u8 raw; @@ -83,46 +145,46 @@ typedef struct Entity_ { /* */ } PACKED b; /* */ } PACKED palette; /*0x1b*/ struct { - /* */ u32 b0 : 1; - /* */ u32 b1 : 5; //0x10 - /* */ u32 flipY : 2; //0x40 + /* */ u32 b0 : 1; /* 1 */ + /* */ u32 b1 : 5; /* 0x2-0x10 */ + /* */ u32 flipY : 2; /* 0x20-0x40 */ /* */ } PACKED spriteOrientation; /*0x1c*/ u8 field_0x1c; /*0x1d*/ u8 field_0x1d; /*0x1e*/ u8 frameIndex; /*0x1f*/ u8 lastFrameIndex; - /*0x20*/ s32 zVelocity; - /*0x24*/ s16 speed; + /*0x20*/ s32 zVelocity; /**< Z axis speed. */ + /*0x24*/ s16 speed; /**< Magnitude of speed. */ /*0x26*/ u8 spriteAnimation[3]; /*0x29*/ struct { - /* */ u8 b0 : 3; // 1-4 - /* */ u8 b1 : 3; // 8 - /* */ u8 b2 : 1; // 0x40 - /* */ u8 b3 : 1; // 0x80 + /* */ u8 b0 : 3; /* 1-4 */ + /* */ u8 b1 : 3; /* 8 */ + /* */ u8 b2 : 1; /* 0x40 */ + /* */ u8 b3 : 1; /* 0x80 */ /* */ } PACKED spritePriority; /*0x2a*/ u16 collisions; - /*0x2c*/ union SplitWord x; - /*0x30*/ union SplitWord y; - /*0x34*/ union SplitWord z; - /*0x38*/ u8 collisionLayer; + /*0x2c*/ union SplitWord x; /**< X position, fixed point. */ + /*0x30*/ union SplitWord y; /**< Y position, fixed point. */ + /*0x34*/ union SplitWord z; /**< Z position, fixed point. */ + /*0x38*/ u8 collisionLayer; /**< Collision layer. */ /*0x39*/ s8 interactType; /*0x3a*/ u8 field_0x3a; /*0x3b*/ u8 flags2; /*0x3c*/ u8 field_0x3c; - /*0x3d*/ s8 iframes; - /*0x3e*/ u8 knockbackDirection; - /*0x3f*/ u8 hitType; // behavior as a collision sender - /*0x40*/ u8 hurtType; // behavior as a collision reciever + /*0x3d*/ s8 iframes; /**< Invulnerability frames. */ + /*0x3e*/ u8 knockbackDirection; /**< Direction of knockback. */ + /*0x3f*/ u8 hitType; /**< Behavior as a collision sender. */ + /*0x40*/ u8 hurtType; /**< behavior as a collision receiver. */ /*0x41*/ u8 bitfield; - /*0x42*/ u8 knockbackDuration; + /*0x42*/ u8 knockbackDuration; /**< Duration of knockback. */ /*0x43*/ u8 field_0x43; - /*0x44*/ u8 damage; - /*0x45*/ u8 health; + /*0x44*/ u8 damage; /**< Damage this Entity inflicts. */ + /*0x45*/ u8 health; /**< Health of this Entity. */ /*0x46*/ u16 field_0x46; - /*0x48*/ Hitbox* hitbox; + /*0x48*/ Hitbox* hitbox; /**< Hitbox associated with this Entity. */ /*0x4c*/ struct Entity_* field_0x4c; - /*0x50*/ struct Entity_* parent; - /*0x54*/ struct Entity_* child; + /*0x50*/ struct Entity_* parent; /**< Parent Entity. Sometimes points to associated data. */ + /*0x54*/ struct Entity_* child; /**< Child Entity. Sometimes points to associated data. */ /*0x58*/ u8 animIndex; /*0x59*/ u8 frameDuration; /*0x5a*/ u8 frame; @@ -131,7 +193,7 @@ typedef struct Entity_ { /*0x60*/ u16 spriteVramOffset; /*0x62*/ u8 spriteOffsetX; /*0x63*/ s8 spriteOffsetY; - /*0x64*/ u32* myHeap; + /*0x64*/ u32* myHeap; /**< Heap data allocated with #zMalloc. */ #ifndef NENT_DEPRECATED /*0x68*/ union SplitHWord field_0x68; /*0x6a*/ union SplitHWord field_0x6a; @@ -150,78 +212,24 @@ typedef struct Entity_ { #endif } Entity; -typedef void(EntityAction)(Entity*); -typedef void(*EntityActionPtr)(Entity*); -typedef void(*const* EntityActionArray)(Entity*); - +/** + * Entity linked list structure. + */ typedef struct LinkedList { Entity* last; Entity* first; } LinkedList; -extern LinkedList gEntityLists[9]; +typedef void(EntityAction)(Entity*); +typedef void (*EntityActionPtr)(Entity*); +typedef void (*const* EntityActionArray)(Entity*); -enum { - ENT_DID_INIT = 0x1, - ENT_SCRIPTED = 0x2, - ENT_DELETED = 0x10, - ENT_PERSIST = 0x20, - ENT_COLLIDE = 0x80, -}; - -#define COLLISION_OFF(entity) ((entity)->flags &= ~ENT_COLLIDE) -#define COLLISION_ON(entity) ((entity)->flags |= ENT_COLLIDE) - -#define TILE(x, y) \ - (((((x) - gRoomControls.origin_x) >> 4) & 0x3F) | \ - ((((y) - gRoomControls.origin_y) >> 4) & 0x3F) << 6) - -#define COORD_TO_TILE(entity) \ - TILE((entity)->x.HALF.HI, (entity)->y.HALF.HI) - -#define COORD_TO_TILE_OFFSET(entity, xOff, yOff) \ - TILE((entity)->x.HALF.HI - (xOff), (entity)->y.HALF.HI - (yOff)) - -enum { - IdleNorth = 0x0, - IdleEast = 0x2, - IdleSouth = 0x4, - IdleWest = 0x6, -}; - -enum { - DirectionNorth = 0x00, - DirectionEast = 0x08, - DirectionSouth = 0x10, - DirectionWest = 0x18, -}; - -#define AnimationStateTurnAround(expr) ((expr) ^ 0x4) -#define AnimationStateIdle(expr) ((expr) & 0x6) -#define AnimationStateWalk(expr) ((expr) & 0xe) - -#define DirectionRound(expr) ((expr) & 0x18) -#define DirectionRoundUp(expr) DirectionRound((expr) + 4) -#define DirectionIsHorizontal(expr) ((expr) & 0x08) -#define DirectionIsVertical(expr) ((expr) & 0x10) -#define DirectionTurnAround(expr) ((expr) ^ 0x10) -#define DirectionToAnimationState(expr) (DirectionRoundUp(expr) >> 3) -#define DirectionFromAnimationState(expr) ((expr) << 3) -#define DirectionNormalize(expr) ((expr) & 0x1f) - -#define Direction8Round(expr) ((expr) & 0x1c) -#define Direction8RoundUp(expr) Direction8Round((expr) + 2) -#define Direction8TurnAround(expr) (Direction8RoundUp(expr) ^ 0x10) -#define Direction8ToAnimationState(expr) ((expr) >> 2) -#define Direction8FromAnimationState(expr) ((expr) << 2) - -Entity* GetEmptyEntity(void); -void DrawEntity(Entity*); -Entity* CreateEnemy(u32 id, u32 type); -Entity* CreateNPC(u32 id, u32 type, u32 type2); -Entity* CreateObject(u32 id, u32 type, u32 type2); -Entity* CreateObjectWithParent(Entity* parent, u32 id, u32 type, u32 type2); -Entity* CreateFx(Entity* parent, u32 type, u32 type2); +/** + * Draw an Entity. + * + * @param entity Entity to be drawn. + */ +void DrawEntity(Entity* entity); void InitializeAnimation(Entity*, u32); void InitAnimationForceUpdate(Entity*, u32); @@ -234,112 +242,270 @@ void SetSpriteSubEntryOffsetData1(Entity*, u32, u32); void SetSpriteSubEntryOffsetData2(Entity*, u32, u32); u8* GetSpriteSubEntryOffsetDataPointer(u32, u32); -u32 GetFacingDirection(Entity*, Entity*); +/** + * Return the direction pointing from one Entity to another. + * + * @param origin Entity to orient. + * @param target Entity to look at. + * @return Direction facing target. + */ +u32 GetFacingDirection(Entity* origin, Entity* target); u32 ProcessMovement(Entity*); +/// @{ /** - * @brief Delete the entity currently in execution. + * Allocate a new Entity. + * + * @return Allocated Entity or NULL if failed. + */ +Entity* GetEmptyEntity(void); +Entity* CreateEnemy(u32 id, u32 type); +Entity* CreateNPC(u32 id, u32 type, u32 type2); +Entity* CreateObject(u32 id, u32 type, u32 type2); +Entity* CreateObjectWithParent(Entity* parent, u32 id, u32 type, u32 type2); +Entity* CreateFx(Entity* parent, u32 type, u32 type2); +/// @} + +/** + * Iteratively execute every Entity. Call once per frame. + */ +void UpdateEntities(void); + +/** + * Iteratively execute every Manager. Call once per frame. + */ +void UpdateManagers(void); + +/** + * Delete a manager. + * + * @param manager Manager to delete. + */ +void DeleteManager(void* manager); +/** + * Delete Manager or Entity. + * + * @param entity Entity or Manager to be deleted. + */ +void DeleteEntityAny(Entity* entity); + +/** + * Erase all Entity's. + */ +void EraseAllEntities(void); + +/** + * Delete the Entity currently in execution. + * + * @see UpdateContext */ void DeleteThisEntity(void); /** - * @brief Delete an entity. + * Delete an Entity. + * + * @param entity Entity to delete. */ -void DeleteEntity(Entity*); +void DeleteEntity(Entity* entity); +/** + * Add an Entity to the end of a LinkedList. + * + * @param entity Entity to add. + * @param listIndex Target LinkedList. + */ void AppendEntityToList(Entity* entity, u32 listIndex); + +/** + * Add an Entity to the start of a LinkedList. + * + * @param entity Entity to add. + * @param listIndex Target LinkedList. + */ void PrependEntityToList(Entity* entity, u32 listIndex); /** - * @brief Find an entity for a given kind and ID. - * @return Entity* First result or NULL if none found + * Find an Entity for a given kind and id, and LinkedList. + * + * @return Entity* First result or NULL if none found. */ Entity* FindEntityByID(u32 kind, u32 id, u32 listIndex); /** - * @brief Search all lists for an entity of same kind and id. - * @return Entity* First result or NULL if none found + * Search all lists for an Entity of same kind and id. + * + * @return Entity* First result or NULL if none found. */ Entity* DeepFindEntityByID(u32 kind, u32 id); /** - * @brief Search all lists for entity of same kind and id. - * @return bool32 Duplicate was entity found + * Search all lists for Entity of same kind and id. + * + * @return bool32 Duplicate was found. */ -bool32 EntityHasDuplicateID(Entity* ent); +bool32 EntityHasDuplicateID(Entity* entity); /** - * @brief Find an entity of same kind and id in list. - * @return Entity* First result or NULL if none found + * Find an Entity of same kind and id in LinkedList. + * + * @return Entity* First result or NULL if none found. */ -Entity* FindNextDuplicateID(Entity* ent, int listIndex); +Entity* FindNextDuplicateID(Entity* entity, int listIndex); /** - * @brief Find Entity with full identifiers. - * @return Entity* First result or NULL if none found + * Find an Entity with full identifiers. + * + * @return Entity* First result or NULL if none found. */ Entity* FindEntity(u32 kind, u32 id, u32 listIndex, u32 type, u32 type2); -void DeleteManager(void*); -void DeleteEntityAny(Entity* ent); - -void UpdateEntities(void); -void UpdateManagers(void); - -void EraseAllEntities(void); - -enum { - PRIO_MIN = 0, - PRIO_PLAYER = 1, - PRIO_MESSAGE = 2, /* do not block during message */ - PRIO_NO_BLOCK = 3, /* do not block during entity requested priority */ - PRIO_PLAYER_EVENT = 6, /* do not block during special player event */ - PRIO_HIGHEST = 7, /* do not block EVER */ -}; - /** - * @brief Set the default priority for entity. + * Set the default priority for entity. + * + * @param entity Entity to set the priority of. + * @param prio #Priority level. */ -void SetDefaultPriority(Entity* ent, u32 prio); +void SetDefaultPriority(Entity* entity, u32 prio); /** - * @brief Check if entity should sleep this frame (according to priority). + * Check if entity will be deleted next frame. */ -bool32 CheckDontUpdate(Entity* this); +bool32 EntityIsDeleted(Entity* entity); /** - * @brief Check if system or entity is blocking updates. + * Check if system or entity is blocking updates. */ bool32 AnyPrioritySet(void); - -/// Entity Priority: Update blocking events requested by an entity. - +/** + * Set the minimum Entity priority. + * + * @param prio Minimum #Priority. + * @return Success. + */ s32 SetMinPriority(u32 prio); -void RequestPriority(Entity* this); -void RevokePriority(Entity* e); +/** + * Request indefinite priority for an Entity. + * + * @param entity Entity requesting priority. + */ +void RequestPriority(Entity* entity); -void RequestPriorityDuration(Entity* this, u32 time); +/** + * Revoke priority from an Entity. + * + * @param entity Entity which requested priority. + */ +void RevokePriority(Entity* entity); + +/** + * Request update priority over other Entity's for a period of time. + * + * @param entity Entity requesting priority. + * @param time Number of frames. + */ +void RequestPriorityDuration(Entity* entity, u32 time); + +/** + * Set the remaining frames of Entity priority. + * + * @param time Number of frames. + */ void SetPriorityTimer(u32 time); -void RequestPriorityOverPlayer(Entity* this); -void RevokePriorityOverPlayer(Entity* this); +/** + * Request priority over player update. + * + * @param entity Entity requesting priority. + */ +void RequestPriorityOverPlayer(Entity* entity); +/** + * Revoke priority over player update. + * + * @param entity Entity which requested priority. + */ +void RevokePriorityOverPlayer(Entity* entity); + +/** + * Reset a priority event requested by an Entity. + */ void ResetEntityPriority(void); - -/// System Priority: Update blocking events sent by the engine. - +/** + * Set entity and system priority to #PRIO_PLAYER_EVENT. + */ void SetPlayerEventPriority(void); + +/** + * Reset entity and system priority to defaults. + */ void ResetPlayerEventPriority(void); + +/** + * Set system priority to #PRIO_PLAYER_EVENT. + */ void SetRoomReloadPriority(void); + +/** + * Set system priority to #PRIO_HIGHEST. + */ void SetInitializationPriority(void); +/** + * Reset the system update priority. + */ void ResetSystemPriority(void); +/** + * LinkedList's which point to allocate Entities. + * These work together with Entity.prev and Entity.next fields + * to allow the iteration of all Entity's. + */ +extern LinkedList gEntityLists[9]; + +/** + * Current number of entities. + * @see Entity + */ extern u8 gEntCount; +/** + * Current number of managers. + * @see Manager + */ extern u8 gManagerCount; -#endif +#define COLLISION_OFF(entity) ((entity)->flags &= ~ENT_COLLIDE) +#define COLLISION_ON(entity) ((entity)->flags |= ENT_COLLIDE) + +/** @name Tile Macros */ /// @{ +#define TILE(x, y) (((((x)-gRoomControls.origin_x) >> 4) & 0x3F) | ((((y)-gRoomControls.origin_y) >> 4) & 0x3F) << 6) +#define COORD_TO_TILE(entity) TILE((entity)->x.HALF.HI, (entity)->y.HALF.HI) +#define COORD_TO_TILE_OFFSET(entity, xOff, yOff) TILE((entity)->x.HALF.HI - (xOff), (entity)->y.HALF.HI - (yOff)) +/// @} + +/** @name Animation State Macros */ ///@{ +#define AnimationStateTurnAround(expr) ((expr) ^ 0x4) +#define AnimationStateIdle(expr) ((expr)&0x6) +#define AnimationStateWalk(expr) ((expr)&0xe) +///@} + +/** @name Direction Macros */ ///@{ +#define DirectionRound(expr) ((expr)&0x18) +#define DirectionRoundUp(expr) DirectionRound((expr) + 4) +#define DirectionIsHorizontal(expr) ((expr) & 0x08) +#define DirectionIsVertical(expr) ((expr) & 0x10) +#define DirectionTurnAround(expr) ((expr) ^ 0x10) +#define DirectionToAnimationState(expr) (DirectionRoundUp(expr) >> 3) +#define DirectionFromAnimationState(expr) ((expr) << 3) +#define DirectionNormalize(expr) ((expr) & 0x1f) +#define Direction8Round(expr) ((expr) & 0x1c) +#define Direction8RoundUp(expr) Direction8Round((expr) + 2) +#define Direction8TurnAround(expr) (Direction8RoundUp(expr) ^ 0x10) +#define Direction8ToAnimationState(expr) ((expr) >> 2) +#define Direction8FromAnimationState(expr) ((expr) << 2) +///@} + +#endif // ENTITY_H diff --git a/include/fade.h b/include/fade.h index 4e830fca..0de28da9 100644 --- a/include/fade.h +++ b/include/fade.h @@ -25,7 +25,7 @@ typedef struct { u16 win_inside_cnt; u16 win_outside_cnt; } FadeControl; -extern FadeControl gFadeControl; /**< Fade control instance. */ +extern FadeControl gFadeControl; /**< FadeControl instance. */ /** Set game brightness. * @param brightness brightness level, 0-2 diff --git a/src/entity.c b/src/entity.c index 8092dd71..cdd1118c 100644 --- a/src/entity.c +++ b/src/entity.c @@ -80,7 +80,7 @@ void SetDefaultPriority(Entity* ent, u32 prio) { ent->updatePriority = prio; } -bool32 CheckDontUpdate(Entity* this) { +bool32 EntityIsDeleted(Entity* this) { u32 value; if (this->flags & ENT_DELETED) diff --git a/src/fade.c b/src/fade.c index 92ce3b08..fc95752b 100644 --- a/src/fade.c +++ b/src/fade.c @@ -94,8 +94,8 @@ void SetFade(u32 type, u32 speed) { } } -void SetFadeInverted(u32 arg0) { - gFadeControl.speed = arg0; +void SetFadeInverted(u32 speed) { + gFadeControl.speed = speed; gFadeControl.type ^= 1; gFadeControl.active = 1; gFadeControl.progress = 256; diff --git a/src/interrupts.c b/src/interrupts.c index e7c6463d..23633a5c 100644 --- a/src/interrupts.c +++ b/src/interrupts.c @@ -220,7 +220,7 @@ void PlayerUpdate(Entity* this) { else gPlayerState.flags &= ~PL_DRUGGED; - if (CheckDontUpdate(this) == 0) { + if (EntityIsDeleted(this) == 0) { if (gPlayerState.flags & PL_MOLDWORM_CAPTURED) { sub_08077B20(); if (gPlayerState.flags & PL_MOLDWORM_RELEASED) { diff --git a/src/main.c b/src/main.c index a93ad7eb..ced56ca5 100644 --- a/src/main.c +++ b/src/main.c @@ -57,14 +57,6 @@ void AgbMain(void) { DoSoftReset(); } - // if (gInput.newKeys & B_BUTTON) { - // ResetFadeMask(); - // } - - // if (gInput.newKeys & A_BUTTON) { - // SetFade(0x7, 1); - // } - switch (gMain.sleepStatus) { case SLEEP: SetSleepMode(); diff --git a/src/manager.c b/src/manager.c index eda605a0..dc6b4138 100644 --- a/src/manager.c +++ b/src/manager.c @@ -14,6 +14,6 @@ void (*const gManagerFunctions[])() = { }; void ManagerUpdate(Entity* this) { - if (!CheckDontUpdate(this)) + if (!EntityIsDeleted(this)) gManagerFunctions[this->id](this); } diff --git a/src/npc.c b/src/npc.c index dbc4253b..12a9364a 100644 --- a/src/npc.c +++ b/src/npc.c @@ -154,7 +154,7 @@ NONMATCH("asm/non_matching/arm_proxy/NPCUpdate.inc", void NPCUpdate(Entity* this DeleteThisEntity(); if (this->action == 0 && (this->flags & ENT_DID_INIT) == 0) InitNPC(this); - if (!CheckDontUpdate(this)) + if (!EntityIsDeleted(this)) gNPCFunctions[this->id][0](this); if (this->next != NULL) { if (gNPCFunctions[this->id][1] != NULL) diff --git a/src/object.c b/src/object.c index 819cb970..ae22d2a3 100644 --- a/src/object.c +++ b/src/object.c @@ -205,7 +205,7 @@ void ObjectUpdate(Entity* this) { ObjectInit(this); if (this->iframes != 0) this->iframes++; - if (!CheckDontUpdate(this)) { + if (!EntityIsDeleted(this)) { gObjectFunctions[this->id](this); this->bitfield &= ~0x80; } diff --git a/src/playerItem.c b/src/playerItem.c index bb91563e..48b67c0a 100644 --- a/src/playerItem.c +++ b/src/playerItem.c @@ -71,7 +71,7 @@ void ItemUpdate(Entity* this) { if ((this->flags & ENT_DID_INIT) == 0 && this->action == 0 && this->subAction == 0) ItemInit(this); - if (!CheckDontUpdate(this)) { + if (!EntityIsDeleted(this)) { gPlayerItemFunctions[this->id](this); this->bitfield &= ~0x80; if (this->iframes != 0) {