diff options
| author | engineer124 <47598039+engineer124@users.noreply.github.com> | 2023-05-19 00:29:50 +1000 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2023-05-18 10:29:50 -0400 |
| commit | 180227e7bb15bbaed77de95715ea103ac473480b (patch) | |
| tree | ce478394ea9491e6e6bb6c4146e76cf915fa5fbc /src/code | |
| parent | 83ac58d739a0ce0f177a6d4380af36085cc6c5bc (diff) | |
Quake & Distortion Docs (Again) + Math Cleanup (Camera Prep) (#1129)
* more quake docs
* more docs
* more distortion docs
* math cleanup
* fix header
* cleanup
* only partial PR review
* PR Suggestions
* fix master merge
* reverb angle change macros
* more revert
* fix enum
Diffstat (limited to 'src/code')
| -rw-r--r-- | src/code/cutscene_camera.c | 40 | ||||
| -rw-r--r-- | src/code/z_actor.c | 25 | ||||
| -rw-r--r-- | src/code/z_camera.c | 4 | ||||
| -rw-r--r-- | src/code/z_camera_data.inc.c | 4 | ||||
| -rw-r--r-- | src/code/z_demo.c | 18 | ||||
| -rw-r--r-- | src/code/z_olib.c | 104 | ||||
| -rw-r--r-- | src/code/z_play.c | 28 | ||||
| -rw-r--r-- | src/code/z_quake.c | 656 |
8 files changed, 464 insertions, 415 deletions
diff --git a/src/code/cutscene_camera.c b/src/code/cutscene_camera.c index d5f028b94..d92d119dd 100644 --- a/src/code/cutscene_camera.c +++ b/src/code/cutscene_camera.c @@ -119,23 +119,23 @@ u8 CutsceneCamera_ProcessSpline(CutsceneCamera* csCamera) { switch (csCamera->atCmd[csCamera->eyeInterp.curPoint].relativeTo) { case CS_CAM_REL_2: - OLib_DbCameraVec3fDiff(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, 2); + OLib_Vec3fDiff(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, OLIB_DIFF); break; case CS_CAM_REL_3: - OLib_DbCameraVec3fDiff(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, 1); + OLib_Vec3fDiff(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, OLIB_DIFF_OFFSET); break; case CS_CAM_REL_1: - OLib_DbCameraVec3fDiff(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, 1); + OLib_Vec3fDiff(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, OLIB_DIFF_OFFSET); break; case CS_CAM_REL_4: - OLib_DbCameraVec3fDiff(&target->world, &csCamera->camera->at, &csCamera->camera->at, 1); + OLib_Vec3fDiff(&target->world, &csCamera->camera->at, &csCamera->camera->at, OLIB_DIFF_OFFSET); break; case CS_CAM_REL_5: - OLib_DbCameraVec3fDiff(&target->world, &csCamera->camera->at, &csCamera->camera->at, 2); + OLib_Vec3fDiff(&target->world, &csCamera->camera->at, &csCamera->camera->at, OLIB_DIFF); break; default: // CS_CAM_REL_0 @@ -147,24 +147,24 @@ u8 CutsceneCamera_ProcessSpline(CutsceneCamera* csCamera) { switch (csCamera->atCmd[csCamera->eyeInterp.curPoint].relativeTo) { case CS_CAM_REL_2: - OLib_DbCameraVec3fSum(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, 2); + OLib_Vec3fAdd(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, OLIB_ADD); break; case CS_CAM_REL_3: - OLib_DbCameraVec3fSum(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, 1); + OLib_Vec3fAdd(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, OLIB_ADD_OFFSET); csCamera->camera->at.y += func_80163660(&player->actor); break; case CS_CAM_REL_1: - OLib_DbCameraVec3fSum(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, 1); + OLib_Vec3fAdd(&player->actor.world, &csCamera->camera->at, &csCamera->camera->at, OLIB_ADD_OFFSET); break; case CS_CAM_REL_4: - OLib_DbCameraVec3fSum(&target->world, &csCamera->camera->at, &csCamera->camera->at, 1); + OLib_Vec3fAdd(&target->world, &csCamera->camera->at, &csCamera->camera->at, OLIB_ADD_OFFSET); break; case CS_CAM_REL_5: - OLib_DbCameraVec3fSum(&target->world, &csCamera->camera->at, &csCamera->camera->at, 2); + OLib_Vec3fAdd(&target->world, &csCamera->camera->at, &csCamera->camera->at, OLIB_ADD); break; default: // CS_CAM_REL_0 @@ -189,23 +189,23 @@ u8 CutsceneCamera_ProcessSpline(CutsceneCamera* csCamera) { switch (csCamera->eyeCmd[csCamera->atInterp.curPoint].relativeTo) { case CS_CAM_REL_2: - OLib_DbCameraVec3fDiff(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, 2); + OLib_Vec3fDiff(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_DIFF); break; case CS_CAM_REL_3: - OLib_DbCameraVec3fDiff(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, 1); + OLib_Vec3fDiff(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_DIFF_OFFSET); break; case CS_CAM_REL_1: - OLib_DbCameraVec3fDiff(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, 1); + OLib_Vec3fDiff(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_DIFF_OFFSET); break; case CS_CAM_REL_4: - OLib_DbCameraVec3fDiff(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, 1); + OLib_Vec3fDiff(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_DIFF_OFFSET); break; case CS_CAM_REL_5: - OLib_DbCameraVec3fDiff(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, 2); + OLib_Vec3fDiff(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_DIFF); break; default: // CS_CAM_REL_0 @@ -217,24 +217,24 @@ u8 CutsceneCamera_ProcessSpline(CutsceneCamera* csCamera) { switch (csCamera->eyeCmd[csCamera->atInterp.curPoint].relativeTo) { case CS_CAM_REL_2: - OLib_DbCameraVec3fSum(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, 2); + OLib_Vec3fAdd(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_ADD); break; case CS_CAM_REL_3: - OLib_DbCameraVec3fSum(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, 1); + OLib_Vec3fAdd(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_ADD_OFFSET); csCamera->camera->eye.y += func_80163660(&player->actor); break; case CS_CAM_REL_1: - OLib_DbCameraVec3fSum(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, 1); + OLib_Vec3fAdd(&player->actor.world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_ADD_OFFSET); break; case CS_CAM_REL_4: - OLib_DbCameraVec3fSum(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, 1); + OLib_Vec3fAdd(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_ADD_OFFSET); break; case CS_CAM_REL_5: - OLib_DbCameraVec3fSum(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, 2); + OLib_Vec3fAdd(&target->world, &csCamera->camera->eye, &csCamera->camera->eye, OLIB_ADD); break; default: // CS_CAM_REL_0 diff --git a/src/code/z_actor.c b/src/code/z_actor.c index 6ede10773..a5ca767dc 100644 --- a/src/code/z_actor.c +++ b/src/code/z_actor.c @@ -2574,7 +2574,7 @@ void Actor_Draw(PlayState* play, Actor* actor) { (actor->flags & (ACTOR_FLAG_10000000 | ACTOR_FLAG_400000)) ? NULL : &actor->world.pos, play); Lights_Draw(light, play->state.gfxCtx); - if (actor->flags & ACTOR_FLAG_1000) { + if (actor->flags & ACTOR_FLAG_IGNORE_QUAKE) { Matrix_SetTranslateRotateYXZ(actor->world.pos.x + play->mainCamera.quakeOffset.x, actor->world.pos.y + ((actor->shape.yOffset * actor->scale.y) + play->mainCamera.quakeOffset.y), @@ -3791,30 +3791,29 @@ void func_800BC620(Vec3f* pos, Vec3f* scale, u8 alpha, PlayState* play) { CLOSE_DISPS(play->state.gfxCtx); } -void Actor_AddQuake(PlayState* play, s16 verticalMag, s16 countdown) { - s16 quakeIndex = Quake_Add(&play->mainCamera, QUAKE_TYPE_3); +void Actor_RequestQuake(PlayState* play, s16 y, s16 duration) { + s16 quakeIndex = Quake_Request(&play->mainCamera, QUAKE_TYPE_3); Quake_SetSpeed(quakeIndex, 20000); - Quake_SetQuakeValues(quakeIndex, verticalMag, 0, 0, 0); - Quake_SetCountdown(quakeIndex, countdown); + Quake_SetPerturbations(quakeIndex, y, 0, 0, 0); + Quake_SetDuration(quakeIndex, duration); } -void Actor_AddQuakeWithSpeed(PlayState* play, s16 verticalMag, s16 countdown, s16 speed) { - s16 quakeIndex = Quake_Add(&play->mainCamera, QUAKE_TYPE_3); +void Actor_RequestQuakeWithSpeed(PlayState* play, s16 y, s16 duration, s16 speed) { + s16 quakeIndex = Quake_Request(&play->mainCamera, QUAKE_TYPE_3); Quake_SetSpeed(quakeIndex, speed); - Quake_SetQuakeValues(quakeIndex, verticalMag, 0, 0, 0); - Quake_SetCountdown(quakeIndex, countdown); + Quake_SetPerturbations(quakeIndex, y, 0, 0, 0); + Quake_SetDuration(quakeIndex, duration); } -// Actor_RequestRumble? -void func_800BC848(Actor* actor, PlayState* play, s16 y, s16 countdown) { - if (y >= 5) { +void Actor_RequestQuakeAndRumble(Actor* actor, PlayState* play, s16 quakeY, s16 quakeDuration) { + if (quakeY >= 5) { Rumble_Request(actor->xyzDistToPlayerSq, 255, 20, 150); } else { Rumble_Request(actor->xyzDistToPlayerSq, 180, 20, 100); } - Actor_AddQuake(play, y, countdown); + Actor_RequestQuake(play, quakeY, quakeDuration); } typedef struct { diff --git a/src/code/z_camera.c b/src/code/z_camera.c index f54fc93da..6cfd65702 100644 --- a/src/code/z_camera.c +++ b/src/code/z_camera.c @@ -699,7 +699,7 @@ f32 D_801B9E60 = 0.0f; #pragma GLOBAL_ASM("asm/non_matchings/code/z_camera/Camera_Demo1.s") // Data for opening chests (default) -VecSph D_801B9E64[] = { +VecGeo D_801B9E64[] = { { 50.0f, 0xEE3A, 0xD558 }, { 75.0f, 0x0000, 0x8008 }, { 80.0f, 0xEE3A, 0x8008 }, @@ -713,7 +713,7 @@ Vec3f D_801B9E84[] = { }; // Data for opening chests (goron) -VecSph D_801B9EB4[] = { +VecGeo D_801B9EB4[] = { { 60.0f, 0xEE3A, 0xD558 }, { 95.0f, 0x0000, 0x8008 }, { 90.0f, 0xEE3A, 0x8008 }, diff --git a/src/code/z_camera_data.inc.c b/src/code/z_camera_data.inc.c index 3df77c0c4..6e1501fd8 100644 --- a/src/code/z_camera_data.inc.c +++ b/src/code/z_camera_data.inc.c @@ -3795,12 +3795,12 @@ s32 sCameraHudVisibility = 2; s32 sCameraLetterboxSize = 32; s32 sCameraNegOne = -1; -// VecSph yaw data +// VecGeo yaw data s16 D_801B9E18[] = { 0x0AAA, 0xF556, 0x1555, 0xEAAB, 0x2AAA, 0xD556, 0x3FFF, 0xC001, 0x5555, 0xAAAB, 0x6AAA, 0x9556, 0x7FFF, 0x0000, }; -// VecSph pitch data +// VecGeo pitch data s16 D_801B9E34[] = { 0x0000, 0x02C6, 0x058C, 0x0000, 0x0000, 0xFD3A, 0x0000, 0x0852, 0x0000, 0x0000, 0x0B18, 0x02C6, 0xFA74, 0x0000, }; diff --git a/src/code/z_demo.c b/src/code/z_demo.c index 79270adce..da965969f 100644 --- a/src/code/z_demo.c +++ b/src/code/z_demo.c @@ -202,10 +202,10 @@ void CutsceneCmd_Misc(PlayState* play, CutsceneContext* csCtx, CsCmdMisc* cmd) { case CS_MISC_EARTHQUAKE_MEDIUM: func_8019F128(NA_SE_EV_EARTHQUAKE_LAST - SFX_FLAG); if (isFirstFrame) { - sCutsceneQuakeIndex = Quake_Add(GET_ACTIVE_CAM(play), QUAKE_TYPE_6); + sCutsceneQuakeIndex = Quake_Request(GET_ACTIVE_CAM(play), QUAKE_TYPE_6); Quake_SetSpeed(sCutsceneQuakeIndex, 22000); - Quake_SetQuakeValues(sCutsceneQuakeIndex, 6, 4, 0, 0); - Quake_SetCountdown(sCutsceneQuakeIndex, 800); + Quake_SetPerturbations(sCutsceneQuakeIndex, 6, 4, 0, 0); + Quake_SetDuration(sCutsceneQuakeIndex, 800); } break; @@ -310,10 +310,10 @@ void CutsceneCmd_Misc(PlayState* play, CutsceneContext* csCtx, CsCmdMisc* cmd) { case CS_MISC_EARTHQUAKE_STRONG: func_8019F128(NA_SE_EV_EARTHQUAKE_LAST2 - SFX_FLAG); if (isFirstFrame) { - sCutsceneQuakeIndex = Quake_Add(GET_ACTIVE_CAM(play), QUAKE_TYPE_6); + sCutsceneQuakeIndex = Quake_Request(GET_ACTIVE_CAM(play), QUAKE_TYPE_6); Quake_SetSpeed(sCutsceneQuakeIndex, 30000); - Quake_SetQuakeValues(sCutsceneQuakeIndex, 20, 10, 0, 0); - Quake_SetCountdown(sCutsceneQuakeIndex, 800); + Quake_SetPerturbations(sCutsceneQuakeIndex, 20, 10, 0, 0); + Quake_SetDuration(sCutsceneQuakeIndex, 800); } break; @@ -372,10 +372,10 @@ void CutsceneCmd_Misc(PlayState* play, CutsceneContext* csCtx, CsCmdMisc* cmd) { case CS_MISC_EARTHQUAKE_WEAK: func_8019F128(NA_SE_EV_EARTHQUAKE_LAST - SFX_FLAG); if (isFirstFrame) { - sCutsceneQuakeIndex = Quake_Add(GET_ACTIVE_CAM(play), QUAKE_TYPE_6); + sCutsceneQuakeIndex = Quake_Request(GET_ACTIVE_CAM(play), QUAKE_TYPE_6); Quake_SetSpeed(sCutsceneQuakeIndex, 22000); - Quake_SetQuakeValues(sCutsceneQuakeIndex, 2, 1, 0, 0); - Quake_SetCountdown(sCutsceneQuakeIndex, 800); + Quake_SetPerturbations(sCutsceneQuakeIndex, 2, 1, 0, 0); + Quake_SetDuration(sCutsceneQuakeIndex, 800); } break; diff --git a/src/code/z_olib.c b/src/code/z_olib.c index ad0c2b35c..754857014 100644 --- a/src/code/z_olib.c +++ b/src/code/z_olib.c @@ -100,16 +100,16 @@ Vec3f* OLib_VecSphToVec3f(Vec3f* dest, VecSph* sph) { } /** - * Takes the geographic point `sph` and converts it into a x,y,z position + * Takes the geographic point `geo` and converts it into a x,y,z position */ -Vec3f* OLib_VecSphGeoToVec3f(Vec3f* dest, VecSph* sph) { - VecSph geo; +Vec3f* OLib_VecGeoToVec3f(Vec3f* dest, VecGeo* geo) { + VecSph sph; - geo.r = sph->r; - geo.pitch = 0x4000 - sph->pitch; - geo.yaw = sph->yaw; + sph.r = geo->r; + sph.pitch = 0x4000 - geo->pitch; + sph.yaw = geo->yaw; - return OLib_VecSphToVec3f(dest, &geo); + return OLib_VecSphToVec3f(dest, &sph); } /** @@ -117,16 +117,16 @@ Vec3f* OLib_VecSphGeoToVec3f(Vec3f* dest, VecSph* sph) { */ VecSph* OLib_Vec3fToVecSph(VecSph* dest, Vec3f* vec) { VecSph sph; - f32 distSquared = SQ(vec->x) + SQ(vec->z); - f32 dist = sqrtf(distSquared); + f32 distXZSq = SQ(vec->x) + SQ(vec->z); + f32 distXZ = sqrtf(distXZSq); - if ((dist == 0.0f) && (vec->y == 0.0f)) { + if ((distXZ == 0.0f) && (vec->y == 0.0f)) { sph.pitch = 0; } else { - sph.pitch = CAM_DEG_TO_BINANG(RAD_TO_DEG(func_80086B30(dist, vec->y))); + sph.pitch = CAM_DEG_TO_BINANG(RAD_TO_DEG(func_80086B30(distXZ, vec->y))); } - sph.r = sqrtf(SQ(vec->y) + distSquared); + sph.r = sqrtf(SQ(vec->y) + distXZSq); if ((vec->x == 0.0f) && (vec->z == 0.0f)) { sph.yaw = 0; } else { @@ -141,7 +141,7 @@ VecSph* OLib_Vec3fToVecSph(VecSph* dest, Vec3f* vec) { /** * Takes the point `vec`, and converts it to a geographic coordinate */ -VecSph* OLib_Vec3fToVecSphGeo(VecSph* dest, Vec3f* vec) { +VecGeo* OLib_Vec3fToVecGeo(VecGeo* dest, Vec3f* vec) { VecSph sph; OLib_Vec3fToVecSph(&sph, vec); @@ -156,42 +156,42 @@ VecSph* OLib_Vec3fToVecSphGeo(VecSph* dest, Vec3f* vec) { * Takes the differences of positions `a` and `b`, and converts them to spherical coordinates */ VecSph* OLib_Vec3fDiffToVecSph(VecSph* dest, Vec3f* a, Vec3f* b) { - Vec3f sph; + Vec3f diff; - sph.x = b->x - a->x; - sph.y = b->y - a->y; - sph.z = b->z - a->z; + diff.x = b->x - a->x; + diff.y = b->y - a->y; + diff.z = b->z - a->z; - return OLib_Vec3fToVecSph(dest, &sph); + return OLib_Vec3fToVecSph(dest, &diff); } /** * Takes the difference of positions `a` and `b`, and converts them to geographic coordinates */ -VecSph* OLib_Vec3fDiffToVecSphGeo(VecSph* dest, Vec3f* a, Vec3f* b) { - Vec3f sph; +VecGeo* OLib_Vec3fDiffToVecGeo(VecGeo* dest, Vec3f* a, Vec3f* b) { + Vec3f diff; - sph.x = b->x - a->x; - sph.y = b->y - a->y; - sph.z = b->z - a->z; + diff.x = b->x - a->x; + diff.y = b->y - a->y; + diff.z = b->z - a->z; - return OLib_Vec3fToVecSphGeo(dest, &sph); + return OLib_Vec3fToVecGeo(dest, &diff); } /** - * Takes the sum of positions `a` (x,y,z coordinates) and `sph` (geographic coordinates), result is in x,y,z position + * Takes the sum of positions `a` (x,y,z coordinates) and `geo` (geographic coordinates), result is in x,y,z position * Identical to Quake_AddVec from OoT */ -Vec3f* OLib_VecSphAddToVec3f(Vec3f* dest, Vec3f* a, VecSph* sph) { - Vec3f vec; +Vec3f* OLib_AddVecGeoToVec3f(Vec3f* dest, Vec3f* a, VecGeo* geo) { + Vec3f sum; Vec3f b; - OLib_VecSphGeoToVec3f(&b, sph); - vec.x = a->x + b.x; - vec.y = a->y + b.y; - vec.z = a->z + b.z; + OLib_VecGeoToVec3f(&b, geo); + sum.x = a->x + b.x; + sum.y = a->y + b.y; + sum.z = a->z + b.z; - *dest = vec; + *dest = sum; return dest; } @@ -248,46 +248,50 @@ Vec3s* OLib_Vec3fDiffBinAng(Vec3s* dest, Vec3f* a, Vec3f* b) { } /** - * Gets a x,y,z position diff depending on the dbCamera mode + * Gets a x,y,z position diff depending on the mode */ -void OLib_DbCameraVec3fDiff(PosRot* a, Vec3f* b, Vec3f* dest, s16 mode) { - VecSph sph; +void OLib_Vec3fDiff(PosRot* a, Vec3f* b, Vec3f* dest, s16 mode) { + VecGeo geo; switch (mode) { - case 1: - OLib_Vec3fDiffToVecSphGeo(&sph, &a->pos, b); - sph.yaw -= a->rot.y; - OLib_VecSphGeoToVec3f(dest, &sph); + case OLIB_DIFF_OFFSET: + OLib_Vec3fDiffToVecGeo(&geo, &a->pos, b); + geo.yaw -= a->rot.y; + OLib_VecGeoToVec3f(dest, &geo); break; - case 2: + + case OLIB_DIFF: dest->x = b->x - a->pos.x; dest->y = b->y - a->pos.y; dest->z = b->z - a->pos.z; break; - default: + + default: // OLIB_DIFF_COPY *dest = *b; break; } } /** - * Gets a x,y,z position sum depending on the dbCamera mode + * Gets a x,y,z position sum depending on the mode */ -void OLib_DbCameraVec3fSum(PosRot* a, Vec3f* b, Vec3f* dest, s16 mode) { - VecSph sph; +void OLib_Vec3fAdd(PosRot* a, Vec3f* b, Vec3f* dest, s16 mode) { + VecGeo geo; switch (mode) { - case 1: - OLib_Vec3fToVecSphGeo(&sph, b); - sph.yaw += a->rot.y; - OLib_VecSphAddToVec3f(dest, &a->pos, &sph); + case OLIB_ADD_OFFSET: + OLib_Vec3fToVecGeo(&geo, b); + geo.yaw += a->rot.y; + OLib_AddVecGeoToVec3f(dest, &a->pos, &geo); break; - case 2: + + case OLIB_ADD: dest->x = a->pos.x + b->x; dest->y = a->pos.y + b->y; dest->z = a->pos.z + b->z; break; - default: + + default: // OLIB_ADD_COPY *dest = *b; break; } diff --git a/src/code/z_play.c b/src/code/z_play.c index ca0ebcbae..1b5c046c6 100644 --- a/src/code/z_play.c +++ b/src/code/z_play.c @@ -507,39 +507,39 @@ void Play_UpdateWaterCamera(PlayState* this, Camera* camera) { if (!sIsCameraUnderwater) { Camera_SetFlags(camera, CAM_STATE_UNDERWATER); sQuakeIndex = -1; - Distortion_SetType(DISTORTION_TYPE_UNDERWATER_ENTRY); - Distortion_SetCountdown(80); + Distortion_Request(DISTORTION_TYPE_UNDERWATER_ENTRY); + Distortion_SetDuration(80); } func_801A3EC0(0x20); func_800F6834(this, lightIndex); - if ((sQuakeIndex == -1) || (Quake_GetCountdown(sQuakeIndex) == 10)) { - s16 quakeIndex = Quake_Add(camera, QUAKE_TYPE_5); + if ((sQuakeIndex == -1) || (Quake_GetTimeLeft(sQuakeIndex) == 10)) { + s16 quakeIndex = Quake_Request(camera, QUAKE_TYPE_5); sQuakeIndex = quakeIndex; if (quakeIndex != 0) { Quake_SetSpeed(sQuakeIndex, 550); - Quake_SetQuakeValues(sQuakeIndex, 1, 1, 180, 0); - Quake_SetCountdown(sQuakeIndex, 1000); + Quake_SetPerturbations(sQuakeIndex, 1, 1, 180, 0); + Quake_SetDuration(sQuakeIndex, 1000); } } if (player->stateFlags3 & PLAYER_STATE3_8000) { - Distortion_SetType(DISTORTION_TYPE_ZORA_SWIMMING); - Distortion_ClearType(DISTORTION_TYPE_NON_ZORA_SWIMMING); + Distortion_Request(DISTORTION_TYPE_ZORA_SWIMMING); + Distortion_RemoveRequest(DISTORTION_TYPE_NON_ZORA_SWIMMING); } else { - Distortion_SetType(DISTORTION_TYPE_NON_ZORA_SWIMMING); - Distortion_ClearType(DISTORTION_TYPE_ZORA_SWIMMING); + Distortion_Request(DISTORTION_TYPE_NON_ZORA_SWIMMING); + Distortion_RemoveRequest(DISTORTION_TYPE_ZORA_SWIMMING); } } else { if (sIsCameraUnderwater) { Camera_ClearFlags(camera, CAM_STATE_UNDERWATER); } - Distortion_ClearType(DISTORTION_TYPE_NON_ZORA_SWIMMING); - Distortion_ClearType(DISTORTION_TYPE_UNDERWATER_ENTRY); - Distortion_ClearType(DISTORTION_TYPE_ZORA_SWIMMING); + Distortion_RemoveRequest(DISTORTION_TYPE_NON_ZORA_SWIMMING); + Distortion_RemoveRequest(DISTORTION_TYPE_UNDERWATER_ENTRY); + Distortion_RemoveRequest(DISTORTION_TYPE_ZORA_SWIMMING); if (sQuakeIndex != 0) { - Quake_Remove(sQuakeIndex); + Quake_RemoveRequest(sQuakeIndex); } func_800F694C(this); func_801A3EC0(0); diff --git a/src/code/z_quake.c b/src/code/z_quake.c index d8d526ca3..c5115375c 100644 --- a/src/code/z_quake.c +++ b/src/code/z_quake.c @@ -3,35 +3,28 @@ #include "z64view.h" typedef struct { - /* 0x00 */ s16 randIndex; - /* 0x02 */ s16 countdownMax; + /* 0x00 */ s16 index; + /* 0x02 */ s16 duration; /* 0x04 */ Camera* camera; /* 0x08 */ u32 type; - /* 0x0C */ s16 verticalMag; - /* 0x0E */ s16 horizontalMag; - /* 0x10 */ s16 zoom; - /* 0x12 */ s16 rollOffset; - /* 0x14 */ Vec3s shakePlaneOffset; // angle deviations from shaking in the perpendicular plane + /* 0x0C */ s16 y; + /* 0x0E */ s16 x; + /* 0x10 */ s16 fov; + /* 0x12 */ s16 upRollOffset; + /* 0x14 */ Vec3s orientation; // alters the orientation of the xy perturbation. Only x (pitch) and y (yaw) are used /* 0x1A */ s16 speed; - /* 0x1C */ s16 isShakePerpendicular; - /* 0x1E */ s16 countdown; + /* 0x1C */ s16 isRelativeToScreen; // is the quake relative to the screen or on world coordinates + /* 0x1E */ s16 timer; /* 0x20 */ s16 camId; } QuakeRequest; // size = 0x24 typedef struct { /* 0x0 */ PlayState* play; /* 0x4 */ s32 type; // bitfield, highest set bit determines type - /* 0x8 */ s16 countdown; + /* 0x8 */ s16 timer; /* 0xA */ s16 state; } DistortionRequest; // size = 0xC -typedef struct { - /* 0x00 */ Vec3f atOffset; - /* 0x0C */ Vec3f eyeOffset; - /* 0x18 */ s16 rollOffset; - /* 0x1A */ s16 zoom; -} ShakeInfo; // size = 0x1C - typedef s16 (*QuakeCallbackFunc)(QuakeRequest*, ShakeInfo*); typedef enum { @@ -40,230 +33,257 @@ typedef enum { /* 2 */ DISTORTION_SETUP } DistortionState; -QuakeRequest sQuakeRequest[4]; +QuakeRequest sQuakeRequests[4]; DistortionRequest sDistortionRequest; -static s16 sIsQuakeInitialized = true; +static s16 sQuakeUnused = 1; static s16 sQuakeRequestCount = 0; f32 Quake_Random(void) { return 2.0f * (Rand_ZeroOne() - 0.5f); } -void Quake_UpdateShakeInfo(QuakeRequest* req, ShakeInfo* shake, f32 verticalPertubation, f32 horizontalPertubation) { +void Quake_UpdateShakeInfo(QuakeRequest* req, ShakeInfo* shake, f32 yOffset, f32 xOffset) { Vec3f* at = &req->camera->at; Vec3f* eye = &req->camera->eye; Vec3f atEyeOffset; - VecSph atEyeOffsetSph2; - VecSph eyeAtAngle; + VecSph geo; + VecSph eyeToAtGeo; - // isShakePerpendicular is always set to 1 before reaching this conditional - // alternative is an unused fixed vertical shake - if (req->isShakePerpendicular) { + if (req->isRelativeToScreen) { atEyeOffset.x = 0; atEyeOffset.y = 0; atEyeOffset.z = 0; - OLib_Vec3fDiffToVecSphGeo(&eyeAtAngle, eye, at); - - atEyeOffsetSph2.r = req->verticalMag * verticalPertubation; - atEyeOffsetSph2.pitch = eyeAtAngle.pitch + req->shakePlaneOffset.x + 0x4000; - atEyeOffsetSph2.yaw = eyeAtAngle.yaw + req->shakePlaneOffset.y; - OLib_VecSphAddToVec3f(&atEyeOffset, &atEyeOffset, &atEyeOffsetSph2); - - atEyeOffsetSph2.r = req->horizontalMag * horizontalPertubation; - atEyeOffsetSph2.pitch = eyeAtAngle.pitch + req->shakePlaneOffset.x; - atEyeOffsetSph2.yaw = eyeAtAngle.yaw + req->shakePlaneOffset.y + 0x4000; - OLib_VecSphAddToVec3f(&atEyeOffset, &atEyeOffset, &atEyeOffsetSph2); + OLib_Vec3fDiffToVecGeo(&eyeToAtGeo, eye, at); + + // y shake + geo.r = req->y * yOffset; + // point unit vector up, then add on `req->orientation` + geo.pitch = eyeToAtGeo.pitch + req->orientation.x + 0x4000; + geo.yaw = eyeToAtGeo.yaw + req->orientation.y; + // apply y shake + OLib_AddVecGeoToVec3f(&atEyeOffset, &atEyeOffset, &geo); + + // x shake + geo.r = req->x * xOffset; + // point unit vector left, then add on `req->orientation` + geo.pitch = eyeToAtGeo.pitch + req->orientation.x; + geo.yaw = eyeToAtGeo.yaw + req->orientation.y + 0x4000; + // apply x shake + OLib_AddVecGeoToVec3f(&atEyeOffset, &atEyeOffset, &geo); } else { atEyeOffset.x = 0; - atEyeOffset.y = req->verticalMag * verticalPertubation; + atEyeOffset.y = req->y * yOffset; atEyeOffset.z = 0; - atEyeOffsetSph2.r = req->horizontalMag * horizontalPertubation; - atEyeOffsetSph2.pitch = req->shakePlaneOffset.x; - atEyeOffsetSph2.yaw = req->shakePlaneOffset.y; + geo.r = req->x * xOffset; + geo.pitch = req->orientation.x; + geo.yaw = req->orientation.y; - OLib_VecSphAddToVec3f(&atEyeOffset, &atEyeOffset, &atEyeOffsetSph2); + OLib_AddVecGeoToVec3f(&atEyeOffset, &atEyeOffset, &geo); } shake->atOffset = shake->eyeOffset = atEyeOffset; - shake->rollOffset = req->rollOffset * verticalPertubation; - shake->zoom = req->zoom * verticalPertubation; + shake->upRollOffset = req->upRollOffset * yOffset; + shake->fovOffset = req->fov * yOffset; } s16 Quake_CallbackType1(QuakeRequest* req, ShakeInfo* shake) { - if (req->countdown > 0) { - f32 perpendicularPertubation = Math_SinS(req->speed * req->countdown); + if (req->timer > 0) { + f32 xyOffset = Math_SinS(req->speed * req->timer); - Quake_UpdateShakeInfo(req, shake, perpendicularPertubation, Rand_ZeroOne() * perpendicularPertubation); - req->countdown--; + Quake_UpdateShakeInfo(req, shake, xyOffset, Rand_ZeroOne() * xyOffset); + req->timer--; } - return req->countdown; + return req->timer; } s16 Quake_CallbackType5(QuakeRequest* req, ShakeInfo* shake) { - if (req->countdown > 0) { - f32 perpendicularPertubation = Math_SinS(req->speed * req->countdown); + if (req->timer > 0) { + f32 xyOffset = Math_SinS(req->speed * req->timer); - Quake_UpdateShakeInfo(req, shake, perpendicularPertubation, perpendicularPertubation); - req->countdown--; + Quake_UpdateShakeInfo(req, shake, xyOffset, xyOffset); + req->timer--; } - return req->countdown; + return req->timer; } s16 Quake_CallbackType6(QuakeRequest* req, ShakeInfo* shake) { - f32 perpendicularPertubation; + f32 xyOffset; + + req->timer--; + xyOffset = Math_SinS(req->speed * ((req->timer & 0xF) + 500)); + Quake_UpdateShakeInfo(req, shake, xyOffset, Rand_ZeroOne() * xyOffset); - req->countdown--; - perpendicularPertubation = Math_SinS(req->speed * ((req->countdown & 0xF) + 500)); - Quake_UpdateShakeInfo(req, shake, perpendicularPertubation, Rand_ZeroOne() * perpendicularPertubation); + // Not returning the timer ensures quake type 6 continues indefinitely until manually removed return 1; } s16 Quake_CallbackType3(QuakeRequest* req, ShakeInfo* shake) { - if (req->countdown > 0) { - f32 perpendicularPertubation = - Math_SinS(req->speed * req->countdown) * ((f32)req->countdown / (f32)req->countdownMax); + if (req->timer > 0) { + f32 xyOffset = Math_SinS(req->speed * req->timer) * ((f32)req->timer / req->duration); - Quake_UpdateShakeInfo(req, shake, perpendicularPertubation, perpendicularPertubation); - req->countdown--; + Quake_UpdateShakeInfo(req, shake, xyOffset, xyOffset); + req->timer--; } - return req->countdown; + return req->timer; } s16 Quake_CallbackType2(QuakeRequest* req, ShakeInfo* shake) { - if (req->countdown > 0) { - f32 perpendicularPertubation = Quake_Random(); + if (req->timer > 0) { + f32 xyOffset = Quake_Random(); - Quake_UpdateShakeInfo(req, shake, perpendicularPertubation, Rand_ZeroOne() * perpendicularPertubation); - req->countdown--; + Quake_UpdateShakeInfo(req, shake, xyOffset, Rand_ZeroOne() * xyOffset); + req->timer--; } - return req->countdown; + return req->timer; } s16 Quake_CallbackType4(QuakeRequest* req, ShakeInfo* shake) { - if (req->countdown > 0) { - f32 perpendicularPertubation = Quake_Random() * ((f32)req->countdown / (f32)req->countdownMax); + if (req->timer > 0) { + f32 xyOffset = Quake_Random() * ((f32)req->timer / req->duration); - Quake_UpdateShakeInfo(req, shake, perpendicularPertubation, Rand_ZeroOne() * perpendicularPertubation); - req->countdown--; + Quake_UpdateShakeInfo(req, shake, xyOffset, Rand_ZeroOne() * xyOffset); + req->timer--; } - return req->countdown; + return req->timer; } s16 Quake_GetFreeIndex(void) { s32 i; - s32 ret = 0; - s32 min = 0x10000; + s32 index = 0; + s32 timerMin = UINT16_MAX + 1; // timer is a short, so start with a value beyond its range - for (i = 0; i < ARRAY_COUNT(sQuakeRequest); i++) { - if (sQuakeRequest[i].type == 0) { - ret = i; + for (i = 0; i < ARRAY_COUNT(sQuakeRequests); i++) { + if (sQuakeRequests[i].type == QUAKE_TYPE_NONE) { + index = i; break; } - if (sQuakeRequest[i].countdown < min) { - min = sQuakeRequest[i].countdown; - ret = i; + if (timerMin > sQuakeRequests[i].timer) { + timerMin = sQuakeRequests[i].timer; + index = i; } } - return ret; + return index; } -QuakeRequest* Quake_AddImpl(Camera* camera, u32 type) { +QuakeRequest* Quake_RequestImpl(Camera* camera, u32 type) { s16 index = Quake_GetFreeIndex(); - QuakeRequest* req = &sQuakeRequest[index]; + QuakeRequest* req = &sQuakeRequests[index]; __osMemset(req, 0, sizeof(QuakeRequest)); + req->camera = camera; req->camId = camera->camId; req->type = type; - req->isShakePerpendicular = true; - req->randIndex = ((s16)(Rand_ZeroOne() * 0x10000) & ~3) + index; + req->isRelativeToScreen = true; + + // Add a unique random identifier to the upper bits of the index + // The `~3` assumes there are only 4 requests + req->index = index + ((s16)(Rand_ZeroOne() * 0x10000) & ~3); + sQuakeRequestCount++; return req; } -void Quake_RemoveRequest(QuakeRequest* req) { - req->type = 0; - req->countdown = -1; +void Quake_Remove(QuakeRequest* req) { + req->type = QUAKE_TYPE_NONE; + req->timer = -1; sQuakeRequestCount--; } -QuakeRequest* Quake_GetRequest(s16 quakeIndex) { - QuakeRequest* req = &sQuakeRequest[quakeIndex & 3]; +QuakeRequest* Quake_GetRequest(s16 index) { + QuakeRequest* req = &sQuakeRequests[index & 3]; - if (req->type == 0) { + if (req->type == QUAKE_TYPE_NONE) { return NULL; } - if (quakeIndex != req->randIndex) { + if (index != req->index) { return NULL; } return req; } -u32 Quake_SetValue(s16 quakeIndex, s16 valueType, s16 value) { - QuakeRequest* req = Quake_GetRequest(quakeIndex); +// valueType for Quake_SetValue() +#define QUAKE_SPEED (1 << 0) +#define QUAKE_Y_OFFSET (1 << 1) +#define QUAKE_X_OFFSET (1 << 2) +#define QUAKE_FOV (1 << 3) +#define QUAKE_ROLL (1 << 4) +#define QUAKE_ORIENTATION_PITCH (1 << 5) +#define QUAKE_ORIENTATION_YAW (1 << 6) +#define QUAKE_ORIENTATION_ROLL (1 << 7) +#define QUAKE_DURATION (1 << 8) +#define QUAKE_IS_RELATIVE_TO_SCREEN (1 << 9) + +u32 Quake_SetValue(s16 index, s16 valueType, s16 value) { + QuakeRequest* req = Quake_GetRequest(index); if (req == NULL) { return false; - } else { - switch (valueType) { - case QUAKE_SPEED: - req->speed = value; - break; - - case QUAKE_VERTICAL_MAG: - req->verticalMag = value; - break; - - case QUAKE_HORIZONTAL_MAG: - req->horizontalMag = value; - break; - - case QUAKE_ZOOM: - req->zoom = value; - break; - - case QUAKE_ROLL_OFFSET: - req->rollOffset = value; - break; - - case QUAKE_SHAKE_PLANE_OFFSET_X: - req->shakePlaneOffset.x = value; - break; - - case QUAKE_SHAKE_PLANE_OFFSET_Y: - req->shakePlaneOffset.y = value; - break; - - case QUAKE_SHAKE_PLANE_OFFSET_Z: - req->shakePlaneOffset.z = value; - break; - - case QUAKE_COUNTDOWN: - req->countdown = value; - req->countdownMax = req->countdown; - break; - - case QUAKE_IS_SHAKE_PERPENDICULAR: - req->isShakePerpendicular = value; - break; - - default: - break; - } + } - return true; + switch (valueType) { + case QUAKE_SPEED: + req->speed = value; + break; + + case QUAKE_Y_OFFSET: + req->y = value; + break; + + case QUAKE_X_OFFSET: + req->x = value; + break; + + case QUAKE_FOV: + req->fov = value; + break; + + case QUAKE_ROLL: + req->upRollOffset = value; + break; + + case QUAKE_ORIENTATION_PITCH: + req->orientation.x = value; + break; + + case QUAKE_ORIENTATION_YAW: + req->orientation.y = value; + break; + + case QUAKE_ORIENTATION_ROLL: + req->orientation.z = value; + break; + + case QUAKE_DURATION: + req->timer = value; + req->duration = req->timer; + break; + + case QUAKE_IS_RELATIVE_TO_SCREEN: + req->isRelativeToScreen = value; + break; + + default: + break; } + + return true; } -u32 Quake_SetSpeed(s16 quakeIndex, s16 speed) { - QuakeRequest* req = Quake_GetRequest(quakeIndex); +/** + * @param index + * @param speed for periodic types only, the angular frequency of the sine wave (binang / frame) + * @return true if successfully applied, false if the request does not exist + */ +u32 Quake_SetSpeed(s16 index, s16 speed) { + QuakeRequest* req = Quake_GetRequest(index); if (req != NULL) { req->speed = speed; @@ -272,45 +292,67 @@ u32 Quake_SetSpeed(s16 quakeIndex, s16 speed) { return false; } -u32 Quake_SetCountdown(s16 quakeIndex, s16 countdown) { - QuakeRequest* req = Quake_GetRequest(quakeIndex); +/** + * @param index quake request index to apply + * @param duration number of frames to apply the quake + * @return true if successfully applied, false if the request does not exist + */ +u32 Quake_SetDuration(s16 index, s16 duration) { + QuakeRequest* req = Quake_GetRequest(index); if (req != NULL) { - req->countdown = countdown; - req->countdownMax = req->countdown; + req->duration = req->timer = duration; return true; } return false; } -s16 Quake_GetCountdown(s16 quakeIndex) { - QuakeRequest* req = Quake_GetRequest(quakeIndex); +/** + * @param index quake request index to get + * @return number of frames until the quake is finished + */ +s16 Quake_GetTimeLeft(s16 index) { + QuakeRequest* req = Quake_GetRequest(index); if (req != NULL) { - return req->countdown; + return req->timer; } return 0; } -u32 Quake_SetQuakeValues(s16 quakeIndex, s16 verticalMag, s16 horizontalMag, s16 zoom, s16 rollOffset) { - QuakeRequest* req = Quake_GetRequest(quakeIndex); +/** + * @param index quake request index to apply + * @param y apply up/down shake + * @param x apply left/right shake + * @param fov apply zooming in/out shake (binang) + * @param roll apply rolling shake (binang) + * @return true if successfully applied, false if the request does not exist + */ +u32 Quake_SetPerturbations(s16 index, s16 y, s16 x, s16 fov, s16 roll) { + QuakeRequest* req = Quake_GetRequest(index); if (req != NULL) { - req->verticalMag = verticalMag; - req->horizontalMag = horizontalMag; - req->zoom = zoom; - req->rollOffset = rollOffset; + req->y = y; + req->x = x; + req->fov = fov; + req->upRollOffset = roll; return true; } return false; } -u32 Quake_SetQuakeValues2(s16 quakeIndex, s16 isShakePerpendicular, Vec3s shakePlaneOffset) { - QuakeRequest* req = Quake_GetRequest(quakeIndex); +/** + * @param index quake request index to apply + * @param isRelativeToScreen is the quake applied relative to the screen or in absolute world coordinates + * @param orientation orient the x/y shake to a different direction + * @return true if successfully applied, false if the request does not exist + */ +u32 Quake_SetOrientation(s16 index, s16 isRelativeToScreen, Vec3s orientation) { + QuakeRequest* req = Quake_GetRequest(index); if (req != NULL) { - req->isShakePerpendicular = isShakePerpendicular; - req->shakePlaneOffset = shakePlaneOffset; + req->isRelativeToScreen = isRelativeToScreen; + req->orientation = orientation; return true; } return false; @@ -319,156 +361,167 @@ u32 Quake_SetQuakeValues2(s16 quakeIndex, s16 isShakePerpendicular, Vec3s shakeP void Quake_Init(void) { s16 i; - for (i = 0; i < ARRAY_COUNT(sQuakeRequest); i++) { - sQuakeRequest[i].type = 0; - sQuakeRequest[i].countdown = 0; + for (i = 0; i < ARRAY_COUNT(sQuakeRequests); i++) { + sQuakeRequests[i].type = QUAKE_TYPE_NONE; + sQuakeRequests[i].timer = 0; } - sIsQuakeInitialized = true; + sQuakeUnused = 1; sQuakeRequestCount = 0; } -s16 Quake_Add(Camera* camera, u32 type) { - return Quake_AddImpl(camera, type)->randIndex; +s16 Quake_Request(Camera* camera, u32 type) { + return Quake_RequestImpl(camera, type)->index; } -u32 Quake_Remove(s16 index) { +u32 Quake_RemoveRequest(s16 index) { QuakeRequest* req = Quake_GetRequest(index); if (req != NULL) { - Quake_RemoveRequest(req); + Quake_Remove(req); return true; } return false; } static QuakeCallbackFunc sQuakeCallbacks[] = { - NULL, - Quake_CallbackType1, - Quake_CallbackType2, - Quake_CallbackType3, - Quake_CallbackType4, - Quake_CallbackType5, - Quake_CallbackType6, + NULL, // QUAKE_TYPE_NONE + Quake_CallbackType1, // QUAKE_TYPE_1 + Quake_CallbackType2, // QUAKE_TYPE_2 + Quake_CallbackType3, // QUAKE_TYPE_3 + Quake_CallbackType4, // QUAKE_TYPE_4 + Quake_CallbackType5, // QUAKE_TYPE_5 + Quake_CallbackType6, // QUAKE_TYPE_6 }; -s16 Quake_Calc(Camera* camera, QuakeCamCalc* camData) { - s32 pad; - QuakeRequest* req; - ShakeInfo shake; +s16 Quake_Update(Camera* camera, ShakeInfo* camShake) { f32 absSpeedDiv; + ShakeInfo shake; + QuakeRequest* req; f32 maxCurr; f32 maxNext; s32 index; - s32 ret; - u32 eq; - Vec3f originVec; + s32 numQuakesApplied; + u32 isDifferentCamId; + Vec3f zeroVec; PlayState* play = camera->play; - originVec.x = 0.0f; - originVec.y = 0.0f; - originVec.z = 0.0f; - camData->atOffset.x = 0.0f; - camData->atOffset.y = 0.0f; - camData->atOffset.z = 0.0f; - camData->eyeOffset.x = 0.0f; - camData->eyeOffset.y = 0.0f; - camData->eyeOffset.z = 0.0f; - camData->rollOffset = 0; - camData->zoom = 0; - camData->max = 0.0f; + zeroVec.x = 0.0f; + zeroVec.y = 0.0f; + zeroVec.z = 0.0f; + + camShake->atOffset.x = 0.0f; + camShake->atOffset.y = 0.0f; + camShake->atOffset.z = 0.0f; + + camShake->eyeOffset.x = 0.0f; + camShake->eyeOffset.y = 0.0f; + camShake->eyeOffset.z = 0.0f; + + camShake->upRollOffset = 0; + camShake->fovOffset = 0; + camShake->maxOffset = 0.0f; if (sQuakeRequestCount == 0) { return 0; } - ret = 0; - for (index = 0; index < ARRAY_COUNT(sQuakeRequest); index++) { - req = &sQuakeRequest[index]; - if (req->type != 0) { - if (play->cameraPtrs[req->camId] == NULL) { - Quake_RemoveRequest(req); - } else { - eq = (camera->camId != req->camera->camId); - absSpeedDiv = ABS(req->speed) / (f32)0x8000; - if (sQuakeCallbacks[req->type](req, &shake) == 0) { - Quake_RemoveRequest(req); - } else if (eq == 0) { - if (fabsf(camData->atOffset.x) < fabsf(shake.atOffset.x)) { - camData->atOffset.x = shake.atOffset.x; - } - if (fabsf(camData->atOffset.y) < fabsf(shake.atOffset.y)) { - camData->atOffset.y = shake.atOffset.y; - } - if (fabsf(camData->atOffset.z) < fabsf(shake.atOffset.z)) { - camData->atOffset.z = shake.atOffset.z; - } - if (fabsf(camData->eyeOffset.x) < fabsf(shake.eyeOffset.x)) { - camData->eyeOffset.x = shake.eyeOffset.x; - } - if (fabsf(camData->eyeOffset.y) < fabsf(shake.eyeOffset.y)) { - camData->eyeOffset.y = shake.eyeOffset.y; - } - if (fabsf(camData->eyeOffset.z) < fabsf(shake.eyeOffset.z)) { - camData->eyeOffset.z = shake.eyeOffset.z; - } - if (camData->rollOffset < shake.rollOffset) { - camData->rollOffset = shake.rollOffset; - } - if (camData->zoom < shake.zoom) { - camData->zoom = shake.zoom; - } - - maxCurr = OLib_Vec3fDist(&shake.atOffset, &originVec) * absSpeedDiv; - - maxNext = OLib_Vec3fDist(&shake.eyeOffset, &originVec) * absSpeedDiv; - maxCurr = CLAMP_MIN(maxCurr, maxNext); - - maxNext = (camData->rollOffset * (7.0f / 2500.0f)) * absSpeedDiv; - maxCurr = CLAMP_MIN(maxCurr, maxNext); - - maxNext = (camData->zoom * (7.0f / 2500.0f)) * absSpeedDiv; - maxCurr = CLAMP_MIN(maxCurr, maxNext); - - if (camData->max < maxCurr) { - camData->max = maxCurr; - } - - ret++; - } - } + numQuakesApplied = 0; + for (index = 0; index < ARRAY_COUNT(sQuakeRequests); index++) { + req = &sQuakeRequests[index]; + if (req->type == QUAKE_TYPE_NONE) { + continue; + } + + if (play->cameraPtrs[req->camId] == NULL) { + Quake_Remove(req); + continue; + } + + isDifferentCamId = (camera->camId != req->camera->camId); + absSpeedDiv = (f32)ABS(req->speed) / 0x8000; + if (sQuakeCallbacks[req->type](req, &shake) == 0) { + // Quake has reached the end of its timer. + Quake_Remove(req); + continue; + } + + if (isDifferentCamId) { + // Quake is attached to a different camId + continue; + } + + if (fabsf(camShake->atOffset.x) < fabsf(shake.atOffset.x)) { + camShake->atOffset.x = shake.atOffset.x; + } + if (fabsf(camShake->atOffset.y) < fabsf(shake.atOffset.y)) { + camShake->atOffset.y = shake.atOffset.y; + } + if (fabsf(camShake->atOffset.z) < fabsf(shake.atOffset.z)) { + camShake->atOffset.z = shake.atOffset.z; + } + if (fabsf(camShake->eyeOffset.x) < fabsf(shake.eyeOffset.x)) { + camShake->eyeOffset.x = shake.eyeOffset.x; } + if (fabsf(camShake->eyeOffset.y) < fabsf(shake.eyeOffset.y)) { + camShake->eyeOffset.y = shake.eyeOffset.y; + } + if (fabsf(camShake->eyeOffset.z) < fabsf(shake.eyeOffset.z)) { + camShake->eyeOffset.z = shake.eyeOffset.z; + } + if (camShake->upRollOffset < shake.upRollOffset) { + camShake->upRollOffset = shake.upRollOffset; + } + if (camShake->fovOffset < shake.fovOffset) { + camShake->fovOffset = shake.fovOffset; + } + + maxCurr = OLib_Vec3fDist(&shake.atOffset, &zeroVec) * absSpeedDiv; + maxNext = OLib_Vec3fDist(&shake.eyeOffset, &zeroVec) * absSpeedDiv; + maxCurr = CLAMP_MIN(maxCurr, maxNext); + + maxNext = (camShake->upRollOffset * (7.0f / 2500.0f)) * absSpeedDiv; + maxCurr = CLAMP_MIN(maxCurr, maxNext); + + maxNext = (camShake->fovOffset * (7.0f / 2500.0f)) * absSpeedDiv; + maxCurr = CLAMP_MIN(maxCurr, maxNext); + + if (camShake->maxOffset < maxCurr) { + camShake->maxOffset = maxCurr; + } + + numQuakesApplied++; } - return ret; + return numQuakesApplied; } void Distortion_Init(PlayState* play) { sDistortionRequest.play = play; View_ClearDistortion(&play->view); sDistortionRequest.type = 0; - sDistortionRequest.countdown = 0; + sDistortionRequest.timer = 0; sDistortionRequest.state = DISTORTION_INACTIVE; } -void Distortion_SetCountdown(s16 countdown) { - sDistortionRequest.countdown = countdown; +void Distortion_SetDuration(s16 duration) { + sDistortionRequest.timer = duration; sDistortionRequest.state = DISTORTION_SETUP; } -s16 Distortion_GetCountdown(void) { - return sDistortionRequest.countdown; +s16 Distortion_GetTimeLeft(void) { + return sDistortionRequest.timer; } s16 Distortion_GetType(void) { return sDistortionRequest.type; } -void Distortion_SetType(s32 type) { +void Distortion_Request(s32 type) { if (sDistortionRequest.type < type) { sDistortionRequest.type = type; } } -void Distortion_ClearType(s32 type) { +void Distortion_RemoveRequest(s32 type) { if (sDistortionRequest.type == type) { sDistortionRequest.type = 0; } @@ -489,7 +542,7 @@ ConveyorSpeed Distortion_GetUnderwaterCurrentSpeed(Player* player) { void Distortion_Update(void) { static s16 depthPhase = 0x3F0; static s16 screenPlanePhase = 0x156; - static s16 countdownMax = 1; + static s16 duration = 1; f32 xyScaleFactor; f32 zScaleFactor; f32 speedScaleFactor; @@ -511,8 +564,8 @@ void Distortion_Update(void) { f32 speedRatio = CLAMP_MAX(camera->speedRatio, 1.0f); if (sDistortionRequest.type != 0) { - if (sDistortionRequest.type & DISTORTION_TYPE_B) { - sDistortionRequest.countdown = 2; + if (sDistortionRequest.type & DISTORTION_TYPE_MASK_TRANSFORM_2) { + sDistortionRequest.timer = 2; depthPhase = 0x3F0; screenPlanePhase = 0x156; @@ -528,17 +581,17 @@ void Distortion_Update(void) { zScale = 0.0f; speed = 0.6f; - xyScaleFactor = zScaleFactor = sDistortionRequest.countdown / 60.0f; + xyScaleFactor = zScaleFactor = sDistortionRequest.timer / 60.0f; speedScaleFactor = 1.0f; - } else if (sDistortionRequest.type & DISTORTION_TYPE_A) { + } else if (sDistortionRequest.type & DISTORTION_TYPE_BOSS_WARP) { if (sDistortionRequest.state == DISTORTION_SETUP) { - countdownMax = sDistortionRequest.countdown; + duration = sDistortionRequest.timer; depthPhase = 0x3F0; screenPlanePhase = 0x156; } depthPhaseStep = 0.0f; - screenPlanePhaseStep = 50.0f / countdownMax; + screenPlanePhaseStep = 50.0f / duration; rotX = 0.0f; rotY = 0.0f; @@ -549,11 +602,11 @@ void Distortion_Update(void) { zScale = 0.0f; speed = 0.4f; - xyScaleFactor = zScaleFactor = ((f32)countdownMax - sDistortionRequest.countdown) / (f32)countdownMax; + xyScaleFactor = zScaleFactor = ((f32)duration - sDistortionRequest.timer) / (f32)duration; speedScaleFactor = 0.5f; - } else if (sDistortionRequest.type & DISTORTION_TYPE_9) { + } else if (sDistortionRequest.type & DISTORTION_TYPE_MASK_TRANSFORM_1) { if (sDistortionRequest.state == DISTORTION_SETUP) { - countdownMax = sDistortionRequest.countdown; + duration = sDistortionRequest.timer; depthPhase = 0x1FC; screenPlanePhase = 0x156; } @@ -570,11 +623,11 @@ void Distortion_Update(void) { zScale = 0.0f; speed = 0.1f; - xyScaleFactor = zScaleFactor = ((f32)countdownMax - sDistortionRequest.countdown) / (f32)countdownMax; + xyScaleFactor = zScaleFactor = ((f32)duration - sDistortionRequest.timer) / (f32)duration; speedScaleFactor = 1.0f; - } else if (sDistortionRequest.type & DISTORTION_TYPE_8) { + } else if (sDistortionRequest.type & DISTORTION_TYPE_GORON_BUTT) { if (sDistortionRequest.state == DISTORTION_SETUP) { - countdownMax = sDistortionRequest.countdown; + duration = sDistortionRequest.timer; depthPhase = 0x2710; screenPlanePhase = 0x3E8; } @@ -591,15 +644,15 @@ void Distortion_Update(void) { zScale = 0.01f; speed = 1.5f; - if (sDistortionRequest.countdown < 5) { - xyScaleFactor = zScaleFactor = ((f32)countdownMax - sDistortionRequest.countdown) / (f32)countdownMax; + if (sDistortionRequest.timer < 5) { + xyScaleFactor = zScaleFactor = ((f32)duration - sDistortionRequest.timer) / (f32)duration; } else { xyScaleFactor = zScaleFactor = 0.0f; } speedScaleFactor = 1.0f; - } else if (sDistortionRequest.type & DISTORTION_TYPE_7) { + } else if (sDistortionRequest.type & DISTORTION_TYPE_UNK_ATTACK) { if (sDistortionRequest.state == DISTORTION_SETUP) { - countdownMax = sDistortionRequest.countdown; + duration = sDistortionRequest.timer; depthPhase = 0x4B0; screenPlanePhase = 0x7D0; } @@ -616,11 +669,11 @@ void Distortion_Update(void) { zScale = 0.01f; speed = 1.5f; - xyScaleFactor = zScaleFactor = sDistortionRequest.countdown / (f32)countdownMax; + xyScaleFactor = zScaleFactor = sDistortionRequest.timer / (f32)duration; speedScaleFactor = 1.0f; - } else if (sDistortionRequest.type & DISTORTION_TYPE_6) { + } else if (sDistortionRequest.type & DISTORTION_TYPE_ZORA_KICK) { if (sDistortionRequest.state == DISTORTION_SETUP) { - countdownMax = sDistortionRequest.countdown; + duration = sDistortionRequest.timer; depthPhase = 0x9C4; screenPlanePhase = 0xBB8; } @@ -637,14 +690,14 @@ void Distortion_Update(void) { zScale = 0.01f; speed = 1.3f; - if (sDistortionRequest.countdown < 4) { - xyScaleFactor = zScaleFactor = sDistortionRequest.countdown / (f32)countdownMax; + if (sDistortionRequest.timer < 4) { + xyScaleFactor = zScaleFactor = sDistortionRequest.timer / (f32)duration; } else { xyScaleFactor = zScaleFactor = 0.0f; } speedScaleFactor = 1.0f; - } else if (sDistortionRequest.type & DISTORTION_TYPE_5) { - sDistortionRequest.countdown = 2; + } else if (sDistortionRequest.type & DISTORTION_TYPE_SONG_OF_TIME) { + sDistortionRequest.timer = 2; if (sDistortionRequest.state == DISTORTION_SETUP) { depthPhase = 0x9C4; screenPlanePhase = 0xBB8; @@ -670,7 +723,7 @@ void Distortion_Update(void) { speedScaleFactor = 1.0f; } else if (sDistortionRequest.type & DISTORTION_TYPE_UNDERWATER_ENTRY) { if (sDistortionRequest.state == DISTORTION_SETUP) { - countdownMax = sDistortionRequest.countdown; + duration = sDistortionRequest.timer; depthPhase = 0x760; screenPlanePhase = 0x1BC; } @@ -687,14 +740,14 @@ void Distortion_Update(void) { zScale = 0.2f; speed = 0.25f; - countdownRatio = sDistortionRequest.countdown / (f32)countdownMax; + countdownRatio = sDistortionRequest.timer / (f32)duration; zScaleFactor = xyScaleFactor = countdownRatio; speedScaleFactor = 1.0f; } else if (sDistortionRequest.type & DISTORTION_TYPE_ZORA_SWIMMING) { depthPhase = 0x3F0; screenPlanePhase = 0x156; - sDistortionRequest.countdown = 2; + sDistortionRequest.timer = 2; player = GET_PLAYER(play); if (player != NULL) { @@ -749,7 +802,7 @@ void Distortion_Update(void) { depthPhase = 0x3F0; screenPlanePhase = 0x156; - sDistortionRequest.countdown = 2; + sDistortionRequest.timer = 2; player = GET_PLAYER(play); depthPhaseStep = 359.2f; @@ -796,12 +849,12 @@ void Distortion_Update(void) { xyScaleFactor = speedScaleFactor = (waterYScaleFactor * 0.15f) + 0.35f + (speedRatio * 0.4f); zScaleFactor = 0.9f - xyScaleFactor; - } else if (sDistortionRequest.type & DISTORTION_TYPE_0) { + } else if (sDistortionRequest.type & DISTORTION_TYPE_HOT_ROOM) { // Gives a small mirage-like appearance depthPhase = 0x3F0; screenPlanePhase = 0x156; - sDistortionRequest.countdown = 2; + sDistortionRequest.timer = 2; depthPhaseStep = 0.0f; screenPlanePhaseStep = 150.0f; @@ -840,32 +893,25 @@ void Distortion_Update(void) { View_ClearDistortion(&play->view); sDistortionRequest.state = DISTORTION_INACTIVE; - sDistortionRequest.countdown = 0; + sDistortionRequest.timer = 0; } - if (sDistortionRequest.countdown != 0) { - sDistortionRequest.countdown--; - if (sDistortionRequest.countdown == 0) { + if (sDistortionRequest.timer != 0) { + sDistortionRequest.timer--; + if (sDistortionRequest.timer == 0) { sDistortionRequest.type = 0; } } } -s32 Quake_NumActiveQuakes(void) { - QuakeRequest* req = sQuakeRequest; +s32 Quake_GetNumActiveQuakes(void) { s32 numActiveQuakes = 0; + s32 i; - if (req[0].type != 0) { - numActiveQuakes++; - } - if (req[1].type != 0) { - numActiveQuakes++; - } - if (req[2].type != 0) { - numActiveQuakes++; - } - if (req[3].type != 0) { - numActiveQuakes++; + for (i = 0; i < ARRAY_COUNT(sQuakeRequests); i++) { + if (sQuakeRequests[i].type != QUAKE_TYPE_NONE) { + numActiveQuakes++; + } } return numActiveQuakes; |
