diff --git a/games/THE BROKEN SEAL/recon/en/main/08092878.c b/games/THE BROKEN SEAL/recon/en/main/08092878.c index 00e00646a..09714b9a0 100644 --- a/games/THE BROKEN SEAL/recon/en/main/08092878.c +++ b/games/THE BROKEN SEAL/recon/en/main/08092878.c @@ -1,9 +1,19 @@ #include "TYPES.H" #include "FIXED_MATH.H" -#define FIELD(base, type, offset) (*(type)((u8 *)(base) + (offset))) +struct ObjectPairPosition { + u8 unknown_00[6]; + s16 angle; + s32 x; + s32 y; + s32 z; +}; -void ObjectLink_RotatePairToward(void *source, void *target) +s32 ArcTan2(s32, s32); +s32 WaitFrames(s32); + +void ObjectLink_RotatePairToward(struct ObjectPairPosition *source, + struct ObjectPairPosition *target) { s32 source_angle_delta; s32 target_angle_delta; @@ -15,13 +25,11 @@ void ObjectLink_RotatePairToward(void *source, void *target) u32 source_angle_target; if (source != 0 && target != 0) { - source_angle_target = (u16)ArcTan2( - FIELD(target, s32 *, 0x10) - FIELD(source, s32 *, 0x10), - FIELD(target, s32 *, 8) - FIELD(source, s32 *, 8)); + source_angle_target = (u16)ArcTan2(target->z - source->z, target->x - source->x); target_angle = source_angle_target + 0x8000; counter = 0; loop: - source_angle = FIELD(source, u16 *, 6); + source_angle = source->angle; source_angle_delta = (s16)(source_angle_target - source_angle); remaining = 2; if (source_angle_delta != 0) { @@ -29,19 +37,19 @@ void ObjectLink_RotatePairToward(void *source, void *target) source_angle_delta = 0x1000; if (source_angle_delta < -0x1000) source_angle_delta = -0x1000; - FIELD(source, u16 *, 6) = source_angle + source_angle_delta; + source->angle = source_angle + source_angle_delta; } else { remaining = 1; } - target_angle_current = FIELD(target, u16 *, 6); + target_angle_current = target->angle; target_angle_delta = (s16)(target_angle - target_angle_current); if (target_angle_delta != 0) { if (target_angle_delta > 0x1000) target_angle_delta = 0x1000; if (target_angle_delta < -0x1000) target_angle_delta = -0x1000; - FIELD(target, u16 *, 6) = target_angle_current + target_angle_delta; + target->angle = target_angle_current + target_angle_delta; } else { remaining--; } diff --git a/games/THE BROKEN SEAL/recon/en/main/080fa514.c b/games/THE BROKEN SEAL/recon/en/main/080fa514.c index a614171b9..97dbd61e1 100644 --- a/games/THE BROKEN SEAL/recon/en/main/080fa514.c +++ b/games/THE BROKEN SEAL/recon/en/main/080fa514.c @@ -1,41 +1,40 @@ -#include "AUDIO_ENGINE_SYMBOLS.H" -#include "TYPES.H" +#include "AUDIO_ENGINE.H" #define MusicPlayer_ResetActiveTracks Func_080fa514 -void AudioCommand_InvokeSlot35(u8 *track); +void AudioCommand_InvokeSlot35(void *block); static __inline__ s32 masked_track_status(s32 mask, s32 status) { return mask & status; } -void MusicPlayer_ResetActiveTracks(u8 *player) +void MusicPlayer_ResetActiveTracks(struct SoundPlayer *player) { - s32 count = player[8]; - u8 *track = *(u8 **)(player + 44); + s32 count = player->track_count; + struct SoundTrack *track = player->tracks; if (count > 0) { s32 active_mask = 0x80; do { register s32 playing_mask; - s32 status = track[0]; + s32 status = track->flags; if (masked_track_status(active_mask, status) != 0) { playing_mask = 0x40; if (masked_track_status(playing_mask, status) != 0) { AudioCommand_InvokeSlot35(track); - track[0] = active_mask; - track[15] = 2; - track[19] = playing_mask; - track[25] = 22; - track[36] = 1; + track->flags = active_mask; + track->bend_range = 2; + track->volume_scale = playing_mask; + track->lfo_speed = 22; + track->voice.kind = 1; } } count--; - track += 80; + track++; } while (count > 0); } } diff --git a/games/THE BROKEN SEAL/recon/en/overlays/advance_effect_motion.c b/games/THE BROKEN SEAL/recon/en/overlays/advance_effect_motion.c new file mode 100644 index 000000000..03b3960bc --- /dev/null +++ b/games/THE BROKEN SEAL/recon/en/overlays/advance_effect_motion.c @@ -0,0 +1,29 @@ +#include "TYPES.H" +#include "FIELD_EFFECT.H" + +/* + * Ordinary spelling of the five overlay copies of main:0809a65c + * (ParticleEffect_UpdateMotionAndScale). Those copies still sit in area + * modules behind a do { } while (0) load-order barrier. Recheck them from + * this text with __divsi3 bound to each overlay's divide veneer: + * resource_3b2:02000da4 + * resource_3c5:02000cf0 + * resource_396:0200185c + * resource_3c4:02001068 + * resource_3c8:0200096c + * Withdraw rather than keep the barrier if this does not match. + */ + +void ParticleEffect_UpdateMotionAndScale(union FieldObject *object) +{ + struct FieldEffect *effect = &object->effect; + + effect->x += effect->velocity_x; + effect->y += effect->velocity_y; + effect->z += effect->velocity_z; + effect->velocity_x -= effect->velocity_x / 18; + effect->velocity_z -= effect->velocity_z / 16; + effect->scale_x += effect->scale_rate_x; + effect->scale_y += effect->scale_rate_y; + effect->sprite->rotation += effect->spin; +} diff --git a/games/THE BROKEN SEAL/recon/en/overlays/effect_move.c b/games/THE BROKEN SEAL/recon/en/overlays/effect_move.c new file mode 100644 index 000000000..811391425 --- /dev/null +++ b/games/THE BROKEN SEAL/recon/en/overlays/effect_move.c @@ -0,0 +1,21 @@ +#include "TYPES.H" +#include "FIELD_EFFECT.H" + +/* + * Shared per-frame effect integrator. Lunpa already compiles this as + * Effect_Move. Overlay listings keep the same 54 instruction bytes after + * AlchemyC_020000a0 for: + * resource_382, 387, 396, 39b, 39c, 39e, 3a0, 3a5, 3a6, 3b3, 3be, 3c0, 3c9 + * Adopt as one translation unit with instances; 54-byte function then + * two-byte alignment, same as runpa-mura-effect. + */ + +void Effect_Move(union FieldObject *object) +{ + object->effect.x += object->effect.velocity_x; + object->effect.y += object->effect.velocity_y; + object->effect.z += object->effect.velocity_z; + object->effect.scale_x += object->effect.scale_rate_x; + object->effect.scale_y += object->effect.scale_rate_y; + object->effect.sprite->rotation += object->effect.spin; +}