summaryrefslogtreecommitdiff
path: root/src/engine/objects/GrandPrixBalloons.cpp
diff options
context:
space:
mode:
authorMegaMech <MegaMech@users.noreply.github.com>2025-05-14 18:30:32 -0600
committerGitHub <noreply@github.com>2025-05-14 18:30:32 -0600
commit32632cacdb316d7f2d3b6ecdb634f0ef9aebadf0 (patch)
treed374a84675fc0f49100c275aa34828bc9db538f8 /src/engine/objects/GrandPrixBalloons.cpp
parent70f049cb6c326dede27e0ba7e88ac0d67b7651a4 (diff)
Impl new intro (#193)
* Update menus * Update CMakeLists.txt * Add Ship * Impl hm ship actors * Update HM course * Impl new intro * Finish intro scene * Rename * Start Editor Work * raycast works * Fix ScreenRayTrace in widescreen * Basic Actor Picking * wip * Editor use vtx collision * gizmo work * otr works for object picking * Impl objects for editor * actor init * Update * Add all axis move (freemove) * Docking Windows works here * Setup imgui layout for editor * Editor Snap to Ground works * Basic Scene Explorer Works * Editor get actor names * Impl editor object names * impl Editor Play and Pause buttons * Editor translate works while paused * Fix freecam lighting * Added adjustable track properties to editor * Editor matrix, icons, rotation, impl light * Setup Track Properties 1 * Editor tooling wip * Load modded o2rs * Don't enable hud if editor is enabled * Updates * SceneManager nearly working * Fix mario kart 64 intro logo sizing * Fix Rotator * Finish new matrix translation code * Cleanup headers * Cleanup * Cleanup 2 * Cleanup 3 * Prevent divize by zero crash * Add visible circle for translate in all axis * Editor scaling/rot works properly now * Scale All_Axis evenly * Fixes to includes to work on Linux. * Removed overfilled arguments in gfx_create_framebuffer() * Added missing function definitions to Game.h * Editor sun face the camera * Add rotation model to gizmo * Add new handles * Failed attempt at transforming collision * Impl water volume * Import fast64 paths * water surface * Scene Setup 1 * Custom Track O2R almost working needs testing * Custom Track Load path O2r * Render custom track. Wip collision * Add missing function * Debug Spawning Custom O2R Track * Import courses working now * Fix memory leak * Remove New Track Button * Engine.cpp more consistent with sf64 * Fix Editor Enable Button * Editor Accurate mouse click drag objects * Editor selects closest object and cleanup * Gizmo rot and scale collision working * Remove constexpr from IRotator * Impl properties for location/rot/scale * Better Properties display, swap rot handles * Fix content browser dock and editor now disabled by default * Remove GameInfoWindow, Multiplayer Button, and FPS Slider * Disable Editor when its disabled * Add new logo to hm intro * Fix pause menu item box cursor * Remove minimap from Course::from_json and to_json * Impl Import Minimap * Fix custom minimap rendering * minimap uses extension .png * Refactor minimap * Freecam only for player 1 * GrandPrix Balloons work in custom track * Track Id is now std::string and outside of Props * Moved editor assets to be included in ship.o2r * Fixed GenerateO2R to package the correct folder and save to the correct filename * Linux specific changes. * Added "#include <stdio.h>" that required them * Changed how the "ship.o2r" file is loaded to allow it to load the file from within appimages. * Changed the Linuxdeploy version to avoid errors later when the Github Actions creates appimages(same fix applied to other ports.) * Revert "Moved editor assets to be included in ship.o2r" This reverts commit 05704c01f761baa67a83e357d9765f5c6b5e3fdb. * Added back files(this time without LUS changes) * Changed workflow file to use correct filename for assets file. * Missed a few spots in the workflow file. * Added .desktop file and made corrections to the main workflow. * Added the rest of upstream CMakeLists.txt * disabled USE_NETWORKING * New InverseMatrix * Renamed both .o2r files to be more accurate to its contents. * Reverted CmakeList.txt --------- Co-authored-by: MegaMech <7255464+MegaMech@users.noreply.github.com> Co-authored-by: sitton76 <58642183+sitton76@users.noreply.github.com>
Diffstat (limited to 'src/engine/objects/GrandPrixBalloons.cpp')
-rw-r--r--src/engine/objects/GrandPrixBalloons.cpp231
1 files changed, 231 insertions, 0 deletions
diff --git a/src/engine/objects/GrandPrixBalloons.cpp b/src/engine/objects/GrandPrixBalloons.cpp
new file mode 100644
index 000000000..819bde1c6
--- /dev/null
+++ b/src/engine/objects/GrandPrixBalloons.cpp
@@ -0,0 +1,231 @@
+#include "GrandPrixBalloons.h"
+
+#include "port/Game.h"
+#include "assets/other_textures.h"
+#include "assets/common_data.h"
+
+extern "C" {
+#include "update_objects.h"
+#include "render_objects.h"
+#include "code_80057C60.h"
+#include "code_80086E70.h"
+#include "math_util.h"
+#include "math_util_2.h"
+#include "menus.h"
+}
+
+size_t OGrandPrixBalloons::_count = 0;
+
+OGrandPrixBalloons::OGrandPrixBalloons(const FVector& pos) {
+ Pos = pos;
+
+ _active = 1;
+ if (gPlayerCount == 1) {
+ _numBalloons = 0x64;
+ _numBalloons2 = 0x3C;
+ _numBalloons3 = 0x1E;
+ } else {
+ _numBalloons = 0x32;
+ _numBalloons2 = 0x1E;
+ _numBalloons3 = 0xA;
+ }
+
+ for (size_t i = 0; i < _numBalloons; i++) {
+ find_unused_obj_index(&gObjectParticle3[i]);
+ init_object(gObjectParticle3[i], 0);
+ }
+}
+
+void OGrandPrixBalloons::Tick() {
+ s32 someIndex;
+ s32 objectIndex;
+ s32 someCount;
+ Object* object;
+
+ if (!_active) {
+ return;
+ }
+ someCount = 0;
+ for (someIndex = 0; someIndex < _numBalloons; someIndex++) {
+ objectIndex = gObjectParticle3[someIndex];
+ if (objectIndex != DELETED_OBJECT_ID) {
+ object = &gObjectList[objectIndex];
+ if (object->state != 0) {
+ OGrandPrixBalloons::func_80074E28(objectIndex);
+ OGrandPrixBalloons::func_80074D94(objectIndex);
+ if (object->state == 0) {
+ delete_object_wrapper(&gObjectParticle3[someIndex]);
+ this->Destroy();
+ }
+ someCount += 1;
+ }
+ }
+ }
+ if (someCount == 0) {
+ _active = 0;
+ }
+}
+
+void OGrandPrixBalloons::Draw(s32 cameraId) {
+ s32 var_s1;
+ s32 objectIndex;
+ if (!_active) {
+ return;
+ }
+
+ gSPDisplayList(gDisplayListHead++, (Gfx*)D_0D007E98);
+ gDPLoadTLUT_pal256(gDisplayListHead++, gTLUTOnomatopoeia);
+ func_8004B614(0, 0, 0, 0, 0, 0, 0);
+ gDPSetAlphaCompare(gDisplayListHead++, G_AC_THRESHOLD);
+ gDPSetRenderMode(gDisplayListHead++,
+ AA_EN | Z_CMP | Z_UPD | IM_RD | CVG_DST_WRAP | ZMODE_XLU | FORCE_BL |
+ GBL_c1(G_BL_CLR_IN, G_BL_A_IN, G_BL_CLR_MEM, G_BL_1MA),
+ AA_EN | Z_CMP | Z_UPD | IM_RD | CVG_DST_WRAP | ZMODE_XLU | FORCE_BL |
+ GBL_c2(G_BL_CLR_IN, G_BL_A_IN, G_BL_CLR_MEM, G_BL_1MA));
+ D_80183E80[0] = 0;
+ D_80183E80[1] = 0x8000;
+ rsp_load_texture((uint8_t*)gTextureBalloon1, 64, 32);
+ for (var_s1 = 0; var_s1 < _numBalloons; var_s1++) {
+ objectIndex = gObjectParticle3[var_s1];
+ if ((objectIndex != NULL_OBJECT_ID) && (gObjectList[objectIndex].state >= 2)) {
+ OGrandPrixBalloons::func_80053D74(objectIndex, cameraId, 0);
+ }
+ }
+ rsp_load_texture((uint8_t*)gTextureBalloon2, 64, 32);
+ for (var_s1 = 0; var_s1 < _numBalloons; var_s1++) {
+ objectIndex = gObjectParticle3[var_s1];
+ if ((objectIndex != NULL_OBJECT_ID) && (gObjectList[objectIndex].state >= 2)) {
+ OGrandPrixBalloons::func_80053D74(objectIndex, cameraId, 4);
+ }
+ }
+}
+
+void OGrandPrixBalloons::func_80053D74(s32 objectIndex, UNUSED s32 arg1, s32 vertexIndex) {
+ Object* object;
+
+ Vtx* vtx = (Vtx*) LOAD_ASSET_RAW(common_vtx_hedgehog);
+
+ if (gMatrixHudCount <= MTX_HUD_POOL_SIZE_MAX) {
+ object = &gObjectList[objectIndex];
+ D_80183E80[2] = (s16) (object->unk_084[6] + 0x8000);
+ rsp_set_matrix_transformation(object->pos, (u16*) D_80183E80, object->sizeScaling);
+ set_color_render((s32) object->unk_084[0], (s32) object->unk_084[1], (s32) object->unk_084[2],
+ (s32) object->unk_084[3], (s32) object->unk_084[4], (s32) object->unk_084[5],
+ (s32) object->primAlpha);
+ gSPVertex(gDisplayListHead++, (uintptr_t)&vtx[vertexIndex], 4, 0);
+ gSPDisplayList(gDisplayListHead++, (Gfx*)common_rectangle_display);
+ }
+}
+
+void OGrandPrixBalloons::func_80074924(s32 objectIndex) {
+ s32 sp2C = 0;
+ s32 sp28;
+ s32 sp24;
+ s32 sp20 = 0;
+ s32 temp_a0;
+ Object* object;
+
+ object = &gObjectList[objectIndex];
+ object->sizeScaling = 0.15f;
+
+ if (GetCourse() == GetMarioRaceway()) {
+ sp2C = random_int(0x00C8U);
+ sp28 = random_int(_numBalloons3);
+ sp24 = random_int(0x0096U);
+ sp20 = random_int(0x2000U);
+ object->origin_pos[0] = (f32) ((((f64) Pos.x + 100.0) - (f64) sp2C) * (f64) xOrientation);
+ object->origin_pos[1] = (f32) (Pos.y + sp28);
+ object->origin_pos[2] = (f32) (((f64) Pos.z + 200.0) - (f64) sp24);
+ } else if (GetCourse() == GetRoyalRaceway()) {
+ sp2C = random_int(0x0168U);
+ sp28 = random_int(_numBalloons3);
+ sp24 = random_int(0x00B4U);
+ sp20 = random_int(0x2000U);
+ object->origin_pos[0] = (f32) ((((f64) Pos.x + 180.0) - (f64) sp2C) * (f64) xOrientation);
+ object->origin_pos[1] = (f32) (Pos.y + sp28);
+ object->origin_pos[2] = (f32) (((f64) Pos.z + 200.0) - (f64) sp24);
+ } else if (GetCourse() == GetLuigiRaceway()) {
+ sp2C = random_int(0x012CU);
+ sp28 = random_int(_numBalloons3);
+ sp24 = random_int(0x0096U);
+ sp20 = random_int(0x2000U);
+ object->origin_pos[0] = (f32) ((((f64) Pos.x + 150.0) - (f64) sp2C) * (f64) xOrientation);
+ object->origin_pos[1] = (f32) (Pos.y + sp28);
+ object->origin_pos[2] = (f32) (((f64) Pos.z + 200.0) - (f64) sp24);
+ } else { // any track
+ sp2C = random_int(0x00C8U);
+ sp28 = random_int(_numBalloons3);
+ sp24 = random_int(0x0096U);
+ sp20 = random_int(0x2000U);
+ object->origin_pos[0] = (f32) ((((f64) Pos.x + 100.0) - (f64) sp2C) * (f64) xOrientation);
+ object->origin_pos[1] = (f32) (Pos.y + sp28);
+ object->origin_pos[2] = (f32) (((f64) Pos.z + 200.0) - (f64) sp24);
+ }
+
+ set_obj_origin_offset(objectIndex, 0, 0, 0);
+ if (gPlayerCount == 1) {
+ object->velocity[1] = (f32) (((f64) (f32) (sp2C % 4) * 0.25) + 0.8);
+ } else {
+ object->velocity[1] = (f32) (((f64) (f32) (sp2C % 3) * 0.2) + 0.4);
+ }
+ temp_a0 = sp2C % 8;
+ object->unk_084[0] = D_800E6F30[temp_a0][0];
+ object->unk_084[1] = D_800E6F30[temp_a0][1];
+ object->unk_084[2] = D_800E6F30[temp_a0][2];
+ object->unk_084[3] = D_800E6F48[temp_a0][0];
+ object->unk_084[4] = D_800E6F48[temp_a0][1];
+ object->unk_084[5] = D_800E6F48[temp_a0][2];
+ object->unk_084[6] = sp20 - 0x1000;
+ if (sp2C & 1) {
+ object->unk_084[7] = (sp20 / 32) + 0x100;
+ } else {
+ object->unk_084[7] = -0x100 - (sp20 / 32);
+ }
+ object->primAlpha = 0x00E6;
+ object_next_state(objectIndex);
+}
+
+void OGrandPrixBalloons::func_80074D94(s32 objectIndex) {
+ if (gObjectList[objectIndex].unk_0AE == 1) {
+ if ((_numBalloons2 <= gObjectList[objectIndex].offset[1]) &&
+ (s16_step_down_towards(&gObjectList[objectIndex].primAlpha, 0, 8) != 0)) {
+ func_80086F60(objectIndex);
+ }
+ object_add_velocity_offset_y(objectIndex);
+ }
+ object_calculate_new_pos_offset(objectIndex);
+}
+
+void OGrandPrixBalloons::func_80074E28(s32 objectIndex) {
+ switch (gObjectList[objectIndex].state) {
+ case 1:
+ OGrandPrixBalloons::func_80074924(objectIndex);
+ break;
+ case 2:
+ if (set_and_run_timer_object(objectIndex, 1) != false) {
+ func_80086E70(objectIndex);
+ break;
+ }
+ case 0:
+ break;
+ case 3:
+ OGrandPrixBalloons::func_80041480(&gObjectList[objectIndex].unk_084[6], -0x1000, 0x1000, &gObjectList[objectIndex].unk_084[7]);
+ if (gObjectList[objectIndex].unk_0AE == 0) {
+ func_80072428(objectIndex);
+ }
+ break;
+ }
+}
+
+void OGrandPrixBalloons::func_80041480(s16* arg0, s16 arg1, s16 arg2, s16* arg3) {
+ *arg0 += *arg3;
+ if (*arg3 >= 0) {
+ if (*arg0 >= arg2) {
+ *arg0 = arg2;
+ *arg3 = -*arg3;
+ }
+ } else if (arg1 >= *arg0) {
+ *arg0 = arg1;
+ *arg3 = -*arg3;
+ }
+} \ No newline at end of file