diff --git a/src/carma2/newcommon/10-loading2.c b/src/carma2/newcommon/10-loading2.c index 4c05b01a2c..4a3454d2ce 100644 --- a/src/carma2/newcommon/10-loading2.c +++ b/src/carma2/newcommon/10-loading2.c @@ -461,11 +461,16 @@ void C2_HOOK_FASTCALL LoadKeyMapping(void) { PFfclose(f); } -// LoadInterfaceStuff +// FUNCTION: CARMA2_HW 0x00487ea0 +void C2_HOOK_FASTCALL LoadInterfaceStuff(int pWithin_race) { + + // empty +} // FUNCTION: CARMA2_HW 0x00487eb0 void C2_HOOK_FASTCALL InitInterfaceLoadState(void) { + // empty } // AdjustCarCoordinates diff --git a/src/carma2/newcommon/10-loading2.h b/src/carma2/newcommon/10-loading2.h index 064a5f892a..b50026f8e0 100644 --- a/src/carma2/newcommon/10-loading2.h +++ b/src/carma2/newcommon/10-loading2.h @@ -20,7 +20,7 @@ extern void C2_HOOK_FASTCALL FinishLoadingGeneral(void); extern void C2_HOOK_FASTCALL LoadKeyMapping(void); -// LoadInterfaceStuff +extern void C2_HOOK_FASTCALL LoadInterfaceStuff(int pWithin_race); extern void C2_HOOK_FASTCALL InitInterfaceLoadState(void); diff --git a/src/carma2/newcommon/16-graphics1.c b/src/carma2/newcommon/16-graphics1.c index 31e7e3ac92..5cb1bb538c 100644 --- a/src/carma2/newcommon/16-graphics1.c +++ b/src/carma2/newcommon/16-graphics1.c @@ -182,7 +182,10 @@ void C2_HOOK_FASTCALL InitWobbleStuff(void) { // StartRenderingHeadups -// RenderThisHeadup +// STUB: CARMA2_HW 0x004e5ad0 +void C2_HOOK_FASTCALL RenderThisHeadup(br_actor* pActor) { + NOT_IMPLEMENTED(); +} // StopRenderingHeadups diff --git a/src/carma2/newcommon/16-graphics1.h b/src/carma2/newcommon/16-graphics1.h index 5ef255f794..110ee454df 100644 --- a/src/carma2/newcommon/16-graphics1.h +++ b/src/carma2/newcommon/16-graphics1.h @@ -74,7 +74,7 @@ extern void C2_HOOK_FASTCALL InitWobbleStuff(void); // StartRenderingHeadups -// RenderThisHeadup +extern void C2_HOOK_FASTCALL RenderThisHeadup(br_actor* pActor); // StopRenderingHeadups diff --git a/src/carma2/newcommon/17-world2.c b/src/carma2/newcommon/17-world2.c index 9d655bda93..ebb2714711 100644 --- a/src/carma2/newcommon/17-world2.c +++ b/src/carma2/newcommon/17-world2.c @@ -2,6 +2,7 @@ #include "41-utility.h" #include "globvars.h" +#include "rec2_macros.h" #include "c2_string.h" @@ -20,21 +21,149 @@ int gCar_simplification_level; // GLOBAL: CARMA2_HW 0x00591368 int gRendering_accessories = 1; -// InitialiseExtraRenders +// GLOBAL: CARMA2_HW 0x006a22c0 +int gCount_extra_renders; -// AddExtraRender +// GLOBAL: CARMA2_HW 0x006a22c8 +tExtra_render gExtra_renders[6]; -// PointOutOfSight +// GLOBAL: CARMA2_HW 0x00704e40 +int gMirror_on__graphics; -// CancelificateClipulatingPlaneyThings +// GLOBAL: CARMA2_HW 0x0065cf30 +br_colour gRGB_colours[9] = { + 0x000000, 0xffffff, 0xff0000, 0x00ff00, + 0x0000ff, 0xffff00, 0x00ffff, 0xff00ff, + 0xd04702, +}; -// FixificateClipulatingPlaneyThings +// GLOBAL: CARMA2_HW 0x0074a620 +br_colour gColours[9]; -// ProcessModelFaceMaterials +// FUNCTION: CARMA2_HW 0x004e5cb0 +void C2_HOOK_FASTCALL InitialiseExtraRenders(void) { -// ProcessModelFaceMaterials2 + gCount_extra_renders = 0; +} + +// FUNCTION: CARMA2_HW 0x004e5cc0 +void C2_HOOK_FASTCALL AddExtraRender(br_actor* pActor, br_material* pMaterial) { + + gExtra_renders[gCount_extra_renders].actor = pActor; + gExtra_renders[gCount_extra_renders].material = pMaterial; + gCount_extra_renders += 1; +} + +// FUNCTION: CARMA2_HW 0x004e5ce0 +int C2_HOOK_FASTCALL PointOutOfSight(const br_vector3* pPoint, undefined4 pArg2, br_scalar pMax_distance) { + br_vector3 distance_vector; + int i; + +#define CAMERA_MAX_DISTANCE(A) ((pMax_distance != 0.f) ? pMax_distance : REC2_SQR(((br_camera*)(A)->type_data)->yon_z)) + + if (gMirror_on__graphics) { + BrVector3Sub(&distance_vector, pPoint, (br_vector3*)gRearview_camera_to_world.m[3]); + if (BrVector3LengthSquared(&distance_vector) < CAMERA_MAX_DISTANCE(gRearview_camera) + && BrVector3Dot(&distance_vector, (br_vector3*)gRearview_camera_to_world.m[2]) < 0.f) { + + return 0; + } + } + + for (i = 0; i < gCount_extra_renders; i++) { + br_actor* a = gExtra_renders[i].actor; + + BrVector3Sub(&distance_vector, pPoint, &a->t.t.translate.t); + if (BrVector3LengthSquared(&distance_vector) < CAMERA_MAX_DISTANCE(a)) { + + return 0; + } + } + + BrVector3Sub(&distance_vector, pPoint, (br_vector3*)gCamera_to_world.m[3]); + if (BrVector3LengthSquared(&distance_vector) >= CAMERA_MAX_DISTANCE(gCamera)) { + return 1; + } + if (BrVector3Dot(&distance_vector, (br_vector3*)gCamera_to_world.m[2]) >= 0.f) { + + return 1; + } +#undef CAMERA_MAX_DISTANCE + return 0; +} + +// FUNCTION: CARMA2_HW 0x004e5ef0 +void C2_HOOK_FASTCALL CancelificateClipulatingPlaneyThings(void) { + + // empty +} + +// FUNCTION: CARMA2_HW 0x004e5f00 +void C2_HOOK_FASTCALL FixificateClipulatingPlaneyThings(void) { + + // empty +} + +void C2_HOOK_FASTCALL ProcessModelFaceMaterials(br_model* pModel, tPMFMCB* pCallback) { + tU16 f; + br_material* possible_mat; + br_material* new_mat = NULL; + + for (f = 0; f < pModel->nfaces; f++) { + + if (pModel->faces[f].material == NULL) { + continue; + } + possible_mat = pCallback(pModel, f); + if (possible_mat == NULL) { + continue; + } + pModel->faces[f].material = possible_mat; + new_mat = possible_mat; + } + if (new_mat != NULL) { + BrModelUpdate(pModel, BR_MODU_ALL); + } +} + +// FUNCTION: CARMA2_HW 0x00448fd0 +void C2_HOOK_FASTCALL ProcessModelFaceMaterials2(br_model* pModel, material_cbfn* pCallback) { + tU32 i; + tU32 j; + + if (pModel->faces == NULL) { + if (pModel->prepared != NULL) { + for (i = 0; i < pModel->prepared->ngroups; i++) { + + /* FIXME: can this inner loop be removed? */ + for (j = 0; j < pModel->prepared->groups[i].nfaces; j++) { + if (*pModel->prepared->groups[i].face_colours.materials != NULL) { + pCallback(*pModel->prepared->groups[i].face_colours.materials); + } + } + } + } + } else if (pModel->faces != NULL) { + for (i = 0; i < pModel->nfaces; i++) { + if (pModel->faces[i].material != NULL) { + pCallback(pModel->faces[i].material); + } + } + } +} + +// FUNCTION: CARMA2_HW 0x00448850 +intptr_t C2_HOOK_CDECL ProcessFaceMaterials(br_actor* pActor, void* pData) { + tPMFMCB* callback = pData; -// ProcessFaceMaterials + if (pActor->identifier != NULL && pActor->identifier[0] == '&') { + return 0; + } + if (pActor->type == BR_ACTOR_MODEL && pActor->model != NULL) { + ProcessModelFaceMaterials(pActor->model, callback); + } + return BrActorEnum(pActor, ProcessFaceMaterials, pData); +} // FUNCTION: CARMA2_HW 0x004475c0 int C2_HOOK_FASTCALL DRPixelmapHasZeros(br_pixelmap* pm) { @@ -190,7 +319,7 @@ tCar_texturing_level C2_HOOK_FASTCALL GetCarTexturingLevel(void) { } // FUNCTION: CARMA2_HW 0x00448ce0 -int C2_HOOK_FASTCALL HasThisSuffix(char* pIdent, char* pSuffix) { +int C2_HOOK_FASTCALL HasThisSuffix(const char* pIdent, const char* pSuffix) { size_t len_ident; size_t len_suffix; @@ -205,15 +334,69 @@ int C2_HOOK_FASTCALL HasThisSuffix(char* pIdent, char* pSuffix) { return strcmp(pIdent + len_ident - len_suffix, pSuffix) == 0; } -// UnsuffixedMaterial +// FUNCTION: CARMA2_HW 0x00448d70 +br_material* C2_HOOK_FASTCALL UnsuffixedMaterial(const char* pOld_ident, const char* pSuffix) { + br_material* result; + int unsuffixed_len; + char* new_id; + + unsuffixed_len = strlen(pOld_ident) - strlen(pSuffix); + new_id = BrMemAllocate(unsuffixed_len + 1, kMem_new_mat_id); + sprintf(new_id, "%.*s", unsuffixed_len, pOld_ident); + result = BrMaterialFind(new_id); + BrMemFree(new_id); + return result; +} -// RoadUntexToPersp +// FUNCTION: CARMA2_HW 0x00447c60 +br_material* C2_HOOK_FASTCALL RoadUntexToPersp(br_model* pModel, tU16 pFace) { + br_material* old_mat; + br_material* new_mat; + + old_mat = pModel->faces[pFace].material; + if (HasThisSuffix(old_mat->identifier, ".road")) { + new_mat = UnsuffixedMaterial(old_mat->identifier, ".road"); + } else { + new_mat = NULL; + } + return new_mat; +} -// WallUntexToPersp +// FUNCTION: CARMA2_HW 0x004481d0 +br_material* C2_HOOK_FASTCALL WallUntexToPersp(br_model* pModel, tU16 pFace) { + br_material* old_mat; + br_material* new_mat; + + old_mat = pModel->faces[pFace].material; + if (HasThisSuffix(old_mat->identifier, ".lwall")) { + new_mat = UnsuffixedMaterial(old_mat->identifier, ".lwall"); + } else if (HasThisSuffix(old_mat->identifier, ".pwall")) { + new_mat = UnsuffixedMaterial(old_mat->identifier, ".pwall"); + } else { + new_mat = NULL; + } + return new_mat; +} -// WallLinearToPersp +// FUNCTION: CARMA2_HW 0x00448390 +br_material* C2_HOOK_FASTCALL WallLinearToPersp(br_model* pModel, tU16 pFace) { + br_material* old_mat; + br_material* new_mat; -// GetRoadTexturingLevel + old_mat = pModel->faces[pFace].material; + if (HasThisSuffix(old_mat->identifier, ".pwall")) { + new_mat = UnsuffixedMaterial(old_mat->identifier, ".pwall"); + } else { + new_mat = NULL; + } + return new_mat; +} + +// FUNCTION: CARMA2_HW 0x00448770 +tRoad_texturing_level C2_HOOK_FASTCALL GetRoadTexturingLevel(void) { + + return gRoad_texturing_level; +} // FUNCTION: CARMA2_HW 0x00448780 void C2_HOOK_FASTCALL SetRoadTexturingLevel(tRoad_texturing_level pLevel) { @@ -229,7 +412,43 @@ void C2_HOOK_FASTCALL SetWallTexturingLevel(tWall_texturing_level pLevel) { gWall_texturing_level = pLevel; } -// DisposeSuffixedMaterials +// FUNCTION: CARMA2_HW 0x00448dd0 +br_material* C2_HOOK_FASTCALL DisposeSuffixedMaterials(br_model* pModel, tU16 pFace) { + size_t max_suffix_len; + br_material* mat; + br_material* victim; + // GLOBAL: CARMA2_HW 0x005913a0 + static const char* suffixes[3] = { + ".road", + ".pwall", + ".lwall", + }; + int s; + char* id; + + mat = pModel->faces[pFace].material; + if (mat->identifier != NULL) { + max_suffix_len = 0; + for (s = 0; s < REC2_ASIZE(suffixes); s++) { + if (max_suffix_len < strlen(suffixes[s])) { + max_suffix_len = strlen(suffixes[s]); + } + } + id = BrMemAllocate(strlen(mat->identifier) + max_suffix_len + 1, kMem_new_mat_id); + for (s = 0; s < REC2_ASIZE(suffixes); s++) { + sprintf(id, "%s%s", mat->identifier, suffixes[s]); + victim = BrMaterialFind(id); + if (victim != NULL) { + BrMaterialRemove(victim); + BrMaterialFree(victim); + } + } +#ifdef REC2_FIX_BUGS + BrMemFree(id); +#endif + } + return NULL; +} // DisposeTexturingMaterials @@ -257,7 +476,11 @@ void C2_HOOK_FASTCALL SetAccessoryRendering(int pOn) { gRendering_accessories = pOn; } -// GetAccessoryRendering +// FUNCTION: CARMA2_HW 0x00448f00 +int C2_HOOK_FASTCALL GetAccessoryRendering(void) { + + return gRendering_accessories; +} // FUNCTION: CARMA2_HW 0x00448f10 void C2_HOOK_FASTCALL SetCarSimplificationLevel(int pLevel) { @@ -267,10 +490,45 @@ void C2_HOOK_FASTCALL SetCarSimplificationLevel(int pLevel) { // GetCarSimplificationLevel -// STUB: CARMA2_HW 0x00448f90 -intptr_t C2_HOOK_CDECL ProcessMaterials(br_actor* pActor, material_cbfn* pCallback) { - NOT_IMPLEMENTED(); +// FUNCTION: CARMA2_HW 0x00448f90 +intptr_t C2_HOOK_CDECL ProcessMaterials(br_actor* pActor, void* pContext) { + material_cbfn* callback = pContext; + + if (pActor->material != NULL) { + callback(pActor->material); + } + if (pActor->type == BR_ACTOR_MODEL && pActor->model != NULL) { + ProcessModelFaceMaterials2(pActor->model, callback); + } + return BrActorEnum(pActor, ProcessMaterials, callback); } -// BuildColourTable +// FUNCTION: CARMA2_HW 0x004b4ed0 +void C2_HOOK_FASTCALL BuildColourTable(br_pixelmap* pPalette) { + int i; + int j; + int nearest_index; + int red; + int green; + int blue; + float nearest_distance; + float distance; + + for (i = 0; i < (int)REC2_ASIZE(gRGB_colours); i++) { + nearest_distance = 196608.f; + red = (gRGB_colours[i] >> 16) & 0xFF; + green = (gRGB_colours[i] >> 8) & 0xFF; + blue = gRGB_colours[i] & 0xFF; + for (j = 0; j < 256; j++) { + distance = (float)(sqr((double)(signed int)(*((br_uint_8*)pPalette->pixels + 4 * j + 2) - red)) + + sqr((double)(signed int)(*((br_uint_8*)pPalette->pixels + 4 * j) - blue)) + + sqr((double)(signed int)(*((br_uint_8*)pPalette->pixels + 4 * j + 1) - green))); + if (distance < nearest_distance) { + nearest_index = j; + nearest_distance = distance; + } + } + gColours[i] = nearest_index; + } +} diff --git a/src/carma2/newcommon/17-world2.h b/src/carma2/newcommon/17-world2.h index e4133c52f7..fea5e89304 100644 --- a/src/carma2/newcommon/17-world2.h +++ b/src/carma2/newcommon/17-world2.h @@ -4,21 +4,21 @@ #include "c2_hooks.h" #include "rec2_types.h" -// InitialiseExtraRenders +extern void C2_HOOK_FASTCALL InitialiseExtraRenders(void); -// AddExtraRender +extern void C2_HOOK_FASTCALL AddExtraRender(br_actor* pActor, br_material* pMaterial); -// PointOutOfSight +extern int C2_HOOK_FASTCALL PointOutOfSight(const br_vector3* pPoint, undefined4 pArg2, br_scalar pMax_distance); -// CancelificateClipulatingPlaneyThings +extern void C2_HOOK_FASTCALL CancelificateClipulatingPlaneyThings(void); -// FixificateClipulatingPlaneyThings +extern void C2_HOOK_FASTCALL FixificateClipulatingPlaneyThings(void); -// ProcessModelFaceMaterials +extern void C2_HOOK_FASTCALL ProcessModelFaceMaterials(br_model* pModel, tPMFMCB* pCallback); -// ProcessModelFaceMaterials2 +extern void C2_HOOK_FASTCALL ProcessModelFaceMaterials2(br_model* pModel, material_cbfn* pCallback); -// ProcessFaceMaterials +extern intptr_t C2_HOOK_CDECL ProcessFaceMaterials(br_actor* pActor, void* pData); extern int C2_HOOK_FASTCALL DRPixelmapHasZeros(br_pixelmap* pm); @@ -38,17 +38,17 @@ extern tCar_texturing_level C2_HOOK_FASTCALL GetCarTexturingLevel(void); extern void C2_HOOK_FASTCALL SetCarTexturingLevel(tCar_texturing_level pLevel); -extern int C2_HOOK_FASTCALL HasThisSuffix(char* pIdent, char* pSuffix); +extern int C2_HOOK_FASTCALL HasThisSuffix(const char* pIdent, const char* pSuffix); -// UnsuffixedMaterial +extern br_material* C2_HOOK_FASTCALL UnsuffixedMaterial(const char* pOld_ident, const char* pSuffix); -// RoadUntexToPersp +extern br_material* C2_HOOK_FASTCALL RoadUntexToPersp(br_model* pModel, tU16 pFace); -// WallUntexToPersp +extern br_material* C2_HOOK_FASTCALL WallUntexToPersp(br_model* pModel, tU16 pFace); -// WallLinearToPersp +extern br_material* C2_HOOK_FASTCALL WallLinearToPersp(br_model* pModel, tU16 pFace); -// GetRoadTexturingLevel +extern tRoad_texturing_level C2_HOOK_FASTCALL GetRoadTexturingLevel(void); extern void C2_HOOK_FASTCALL SetRoadTexturingLevel(tRoad_texturing_level pLevel); @@ -56,7 +56,7 @@ extern void C2_HOOK_FASTCALL SetRoadTexturingLevel(tRoad_texturing_level pLevel) extern void C2_HOOK_FASTCALL SetWallTexturingLevel(tWall_texturing_level pLevel); -// DisposeSuffixedMaterials +extern br_material* C2_HOOK_FASTCALL DisposeSuffixedMaterials(br_model* pModel, tU16 pFace); // DisposeTexturingMaterials @@ -64,14 +64,14 @@ extern intptr_t C2_HOOK_CDECL SetAccessoryRenderingCB(br_actor* pActor, void* pF extern void C2_HOOK_FASTCALL SetAccessoryRendering(int pOn); -// GetAccessoryRendering +extern int C2_HOOK_FASTCALL GetAccessoryRendering(void); extern void C2_HOOK_FASTCALL SetCarSimplificationLevel(int pLevel); // GetCarSimplificationLevel -extern intptr_t C2_HOOK_CDECL ProcessMaterials(br_actor* pActor, material_cbfn* pCallback); +extern intptr_t C2_HOOK_CDECL ProcessMaterials(br_actor* pActor, void* pContext); -// BuildColourTable +extern void C2_HOOK_FASTCALL BuildColourTable(br_pixelmap* pPalette); #endif // GUARD_17_WORLD2_H diff --git a/src/carma2/newcommon/18-graphics2.c b/src/carma2/newcommon/18-graphics2.c index dc315b730e..580b911cd2 100644 --- a/src/carma2/newcommon/18-graphics2.c +++ b/src/carma2/newcommon/18-graphics2.c @@ -177,7 +177,10 @@ void C2_HOOK_FASTCALL InitTransientBitmaps(void) { // DeallocateAllTransientBitmaps -// RemoveTransientBitmaps +// STUB: CARMA2_HW 0x0043e010 +void C2_HOOK_FASTCALL RemoveTransientBitmaps(int pGraphically_remove_them) { + NOT_IMPLEMENTED(); +} // SaveTransient @@ -189,7 +192,10 @@ void C2_HOOK_FASTCALL InitTransientBitmaps(void) { // StartMouseCursor -// EndMouseCursor +// STUB: CARMA2_HW 0x0043e710 +void C2_HOOK_FASTCALL EndMouseCursor(void) { + NOT_IMPLEMENTED(); +} // DRDrawLine @@ -200,7 +206,10 @@ void C2_HOOK_FASTCALL ClearEntireScreen(void) { // DistanceFromPlane -// KillSplashScreen +// STUB: CARMA2_HW 0x0047b960 +void C2_HOOK_FASTCALL KillSplashScreen(void) { + NOT_IMPLEMENTED(); +} // SplashScreenWith diff --git a/src/carma2/newcommon/18-graphics2.h b/src/carma2/newcommon/18-graphics2.h index 30f42fcb8d..86ad4fe552 100644 --- a/src/carma2/newcommon/18-graphics2.h +++ b/src/carma2/newcommon/18-graphics2.h @@ -46,7 +46,7 @@ extern void C2_HOOK_FASTCALL InitTransientBitmaps(void); // DeallocateAllTransientBitmaps -// RemoveTransientBitmaps +extern void C2_HOOK_FASTCALL RemoveTransientBitmaps(int pGraphically_remove_them); // SaveTransient @@ -58,7 +58,7 @@ extern void C2_HOOK_FASTCALL InitTransientBitmaps(void); // StartMouseCursor -// EndMouseCursor +extern void C2_HOOK_FASTCALL EndMouseCursor(void); // DRDrawLine @@ -66,7 +66,7 @@ extern void C2_HOOK_FASTCALL ClearEntireScreen(void); // DistanceFromPlane -// KillSplashScreen +extern void C2_HOOK_FASTCALL KillSplashScreen(void); // SplashScreenWith diff --git a/src/carma2/newcommon/27-powerup.c b/src/carma2/newcommon/27-powerup.c index 7e5dda80a8..74fc0d8a98 100644 --- a/src/carma2/newcommon/27-powerup.c +++ b/src/carma2/newcommon/27-powerup.c @@ -1,5 +1,12 @@ #include "27-powerup.h" +#include "16-graphics1.h" +#include "32-spark.h" +#include "globvrpb.h" +#include "rec2_macros.h" + +#include "c2_string.h" + // GLOBAL: CARMA2_HW 0x006a0ad4 const char* gPowerup_txt_path; @@ -39,6 +46,15 @@ float gMass_mutant_tail_ball; // GLOBAL: CARMA2_HW 0x0065ebbc float gMass_mine = 1.0f; +// GLOBAL: CARMA2_HW 0x006a0454 +int gCount_cloaked_cars; + +// GLOBAL: CARMA2_HW 0x006a0910 +tCar_spec* gCloaked_cars[12]; + +// GLOBAL: CARMA2_HW 0x006a0a54 +tPowerup* gPowerup_array; + // GetNextGoodyTime // DoPowerupTextHeadup @@ -424,12 +440,165 @@ void C2_HOOK_FASTCALL RemoveTail(void) { // ARUndoPowerupRespawn -// PrintPowerupIconIn3D +// FUNCTION: CARMA2_HW 0x004e07f0 +void C2_HOOK_FASTCALL PrintPowerupIconIn3D(int pX, int pY, tHeadup_icon* pIcon, tPowerup* pPowerup, int pScale, tU32 pTime) { + float f; + float scale; + br_fixed_ls prev_opacity; + + if (pIcon == NULL) { + pPowerup->icon_actor->render_style = BR_RSTYLE_FACES; + BrVector3Set(&pIcon->icon_actor->t.t.translate.t, (float)pX + 16.0f, (float)-(pY + 16), 0.0f); + RenderThisHeadup(pIcon->icon_actor); + return; + } + if (pIcon->icon_actor != NULL) { + pIcon->icon_actor->render_style = BR_RSTYLE_FACES; + if (pScale != 0) { + f = (float)(pTime - pIcon->fizzle_start) / 600.0f; + if (pIcon->fizzle_direction > 0) { + f = 1.0f - f; + scale = 1.0f + 5.0f * f; + BrMatrix34Scale(&pIcon->icon_actor->t.t.mat, scale, scale, 1.0f); + } else { + BrMatrix34Scale(&pIcon->icon_actor->t.t.mat, 1.01f - f, 1.01f - f, 1.0f); + } + BrMatrix34PostRotateZ(&pIcon->icon_actor->t.t.mat, (br_angle)((1.0f - f / 2.0f) * 65536.0f)); + pIcon->icon_actor->material->extra_prim[1].v.x = BR_FIXED_INT((1.0f - f) * 255.0f); + BrMaterialUpdate(pIcon->icon_actor->material, BR_MATU_EXTRA_PRIM); + } else { + prev_opacity = pIcon->icon_actor->material->extra_prim[1].v.x; + pIcon->icon_actor->material->extra_prim[1].v.x = BR_FIXED_INT(255); + if (prev_opacity != pIcon->icon_actor->material->extra_prim[1].v.x) { + BrMaterialUpdate(pIcon->icon_actor->material, BR_MATU_EXTRA_PRIM); + } + BrMatrix34Identity(&pIcon->icon_actor->t.t.mat); + } + BrVector3Set(&pIcon->icon_actor->t.t.translate.t, (float)pX + 16.0f, (float)-(pY + 16), 0.0f); + RenderThisHeadup(pIcon->icon_actor); + } +} -// CreateBillBoard +// FUNCTION: CARMA2_HW 0x004e09d0 +br_actor* C2_HOOK_FASTCALL CreateBillBoard(br_pixelmap* pTexture) { + br_actor* actor; + br_material* material; + br_model* model; + int width; + int height; + br_scalar left; + br_scalar right; + br_scalar top; + br_scalar bottom; + + width = pTexture->width; + height = pTexture->height; + model = BrModelAllocate("Billboard Model", 4, 2); + material = BrMaterialAllocate("Billboard Material"); + actor = BrActorAllocate(BR_ACTOR_MODEL, NULL); + actor->identifier = "Billboard Actor"; + actor->model = model; + actor->material = material; + actor->render_style = BR_RSTYLE_FACES; + model->faces[0].vertices[0] = 0; + model->faces[0].vertices[1] = 1; + model->faces[0].vertices[2] = 2; + model->faces[1].vertices[0] = 2; + model->faces[1].vertices[1] = 3; + model->faces[1].vertices[2] = 0; + model->faces[0].material = NULL; + model->faces[1].material = NULL; + left = (float)-(width / 2); + top = (float)+(height / 2); + BrVector3Set(&model->vertices[0].p, left, top, -2.0f); + bottom = (float)-(height / 2); + BrVector3Set(&model->vertices[1].p, left, bottom, -2.0f); + right = (float)+(width / 2); + BrVector3Set(&model->vertices[2].p, right, bottom, -2.0f); + BrVector3Set(&model->vertices[3].p, right, top, -2.0f); + BrVector2Set(&model->vertices[0].map, 0.0f, 0.0f); + BrVector2Set(&model->vertices[1].map, 0.0f, 1.0f); + BrVector2Set(&model->vertices[2].map, 1.0f, 1.0f); + BrVector2Set(&model->vertices[3].map, 1.0f, 0.0f); + material->colour = 0; + material->colour_map = pTexture; + material->flags = BR_MATF_ALWAYS_VISIBLE | BR_MATF_FORCE_FRONT; + model->flags |= BR_MODF_KEEP_ORIGINAL; + BrMapAdd(pTexture); + BrMaterialAdd(material); + BrModelAdd(model); + return actor; +} // FUNCTION: CARMA2_HW 0x004e0c00 void C2_HOOK_FASTCALL SetDefaultPowerupFilename(void) { gPowerup_txt_path = "POWERUP.TXT"; } +// FUNCTION: CARMA2_HW 0x004e0c40 +int C2_HOOK_FASTCALL TurnOnCloaking(tPowerup* pPowerup, tCar_spec* pCar) { + + if (gNet_mode != eNet_mode_none && !IsCarCloaked(pCar)) { + BlendifyCar(pCar); + MasterDisableCarFunks(pCar); + gCloaked_cars[gCount_cloaked_cars++] = pCar; + } + return pPowerup - gPowerup_array; +} + +// FUNCTION: CARMA2_HW 0x004e0cb0 +void C2_HOOK_FASTCALL RemoveFromCloakingList(tCar_spec* pCar) { + int i; + + if (gNet_mode != eNet_mode_none) { + for (i = 0; i < gCount_cloaked_cars; i++) { + + if (gCloaked_cars[i] == pCar) { +#ifdef REC2_FIX_BUGS + memmove(&gCloaked_cars[i], &gCloaked_cars[i + 1], (gCount_cloaked_cars - i - 1) * sizeof(tCar_spec*)); +#else + memcpy(&gCloaked_cars[i], &gCloaked_cars[i + 1], (REC2_ASIZE(gCloaked_cars) - i - 1) * sizeof(tCar_spec*)); +#endif + gCount_cloaked_cars -= 1; + break; + } + } + } +} + +// FUNCTION: CARMA2_HW 0x004e0d10 +int C2_HOOK_FASTCALL IsCarCloaked(tCar_spec* pCar) { + int i; + + if (gNet_mode != eNet_mode_none) { + for (i = 0; i < gCount_cloaked_cars; i++) { + if (gCloaked_cars[i] == pCar) { + return 1; + } + } + } + return 0; +} + +// FUNCTION: CARMA2_HW 0x004e0d50 +void C2_HOOK_FASTCALL TurnOffCloaking(tPowerup* pPowerup, tCar_spec* pCar) { + + if (gNet_mode != eNet_mode_none) { + UnBlendifyCar(pCar); + RemoveFromCloakingList(pCar); + MasterEnableCarFunks(pCar); + RestoreCarPixelmaps(pCar); + } +} + +// FUNCTION: CARMA2_HW 0x004e0de0 +void C2_HOOK_FASTCALL PeriodicCloaking(void) { + int i; + + if (gNet_mode != eNet_mode_none) { + + for (i = 0; i < gCount_cloaked_cars; i++) { + DoCamouflageThing(gCloaked_cars[i]); + } + } +} diff --git a/src/carma2/newcommon/27-powerup.h b/src/carma2/newcommon/27-powerup.h index 8c3886ce7a..77efe93c33 100644 --- a/src/carma2/newcommon/27-powerup.h +++ b/src/carma2/newcommon/27-powerup.h @@ -389,10 +389,20 @@ extern void C2_HOOK_FASTCALL RemoveTail(void); // ARUndoPowerupRespawn -// PrintPowerupIconIn3D +extern void C2_HOOK_FASTCALL PrintPowerupIconIn3D(int pX, int pY, tHeadup_icon* pIcon, tPowerup* pPowerup, int pScale, tU32 pTime); -// CreateBillBoard +extern br_actor* C2_HOOK_FASTCALL CreateBillBoard(br_pixelmap* pTexture); extern void C2_HOOK_FASTCALL SetDefaultPowerupFilename(void); +extern int C2_HOOK_FASTCALL TurnOnCloaking(tPowerup* pPowerup, tCar_spec* pCar); + +extern void C2_HOOK_FASTCALL RemoveFromCloakingList(tCar_spec* pCar); + +extern int C2_HOOK_FASTCALL IsCarCloaked(tCar_spec* pCar); + +extern void C2_HOOK_FASTCALL TurnOffCloaking(tPowerup* pPowerup, tCar_spec* pCar); + +// PeriodicCloaking + #endif // GUARD_27_POWERUP_H diff --git a/src/carma2/newcommon/28-world3.c b/src/carma2/newcommon/28-world3.c index 743639cf5c..ec8c1da804 100644 --- a/src/carma2/newcommon/28-world3.c +++ b/src/carma2/newcommon/28-world3.c @@ -1,10 +1,14 @@ #include "28-world3.h" +#include "08-loading1.h" #include "41-utility.h" +#include "50-fog.h" #include "52-errors.h" #include "63-loading3.h" #include "69-sound.h" #include "70-packfile.h" +#include "globvars.h" +#include "globvrpb.h" #include "rec2_macros.h" #include @@ -30,19 +34,31 @@ br_model* gDuplicate_model; // GLOBAL: CARMA2_HW 0x00660cb8 tRendererShadingType gMaterial_shading_for_callback = kRendererShadingType_Undefined; -// TurnOnCloaking - -// RemoveFromCloakingList - -// IsCarCloaked - -// TurnOffCloaking - -// PeriodicCloaking - -// STUB: CARMA2_HW 0x00504b30 +// FUNCTION: CARMA2_HW 0x00504b30 void C2_HOOK_FASTCALL InitTreeSurgery(void) { - NOT_IMPLEMENTED(); + tPath_name the_path; + FILE* file; + int i; + + PathCat(the_path, gApplication_path, "TreeSurgery.TXT"); + file = PFfopen(the_path, "rt"); + if (file != NULL) { + gTree_surgery_pass1_count = GetAnInt(file); + for (i = 0; i < gTree_surgery_pass1_count; i++) { + GetAString(file, gTree_surgery_pass1[i].name); + } + gTree_surgery_pass2_count = GetAnInt(file); + for (i = 0; i < gTree_surgery_pass2_count; i++) { + GetAString(file, gTree_surgery_pass2[i].original); + GetAString(file, gTree_surgery_pass2[i].replacement); + } +#ifdef REC2_FIX_BUGS + PFfclose(file); +#endif + } else { + gTree_surgery_pass1_count = 0; + gTree_surgery_pass2_count = 0; + } } // ModelIsATree @@ -101,11 +117,40 @@ void C2_HOOK_FASTCALL InitialiseStorageSpace(int pUnknown, tBrender_storage* pSt pStorage_space->materialProps = BrMemCalloc(pMax_materials, sizeof(br_material*), kMem_stor_space_table); } -// DisposeStorageSpace +// FUNCTION: CARMA2_HW 0x00500e10 +void C2_HOOK_FASTCALL DisposeStorageSpace(tBrender_storage* pStorage) { -// STUB: CARMA2_HW 0x00500e60 -void C2_HOOK_FASTCALL ClearMatertrialSetFromStorageSpace(tBrender_storage* pStorage_space, int pOld_count, int pNew_count) { - NOT_IMPLEMENTED(); + BrMemFree(pStorage->pixelmaps); + BrMemFree(pStorage->shade_tables); + BrMemFree(pStorage->materials); + BrMemFree(pStorage->models); + BrMemFree(pStorage->sounds); + BrMemFree(pStorage->materialProps); +} + +// FUNCTION: CARMA2_HW 0x00500e60 +void C2_HOOK_FASTCALL ClearMatertrialSetFromStorageSpace(tBrender_storage* pStorage_space, int pStart, int pEnd) { + int i; + int move_to; + + for (i = pStart; i < pEnd && i < pStorage_space->materials_count; i++) { + BrMaterialRemove(pStorage_space->materials[i]); + BrMaterialFree(pStorage_space->materials[i]); + RemoveMaterialFromFogification(pStorage_space->materials[i]); + } + for (move_to = pStart, i = pEnd; i < pStorage_space->materials_count; ) { + pStorage_space->materials[move_to++] = pStorage_space->materials[i++]; + } + pStorage_space->materials_count = move_to; + if (pStorage_space == &gNet_cars_storage_space) { + for (i = 0; i < gNumber_of_net_players; i++) { + tCar_spec* car = gNet_players[i].car; + if (car != NULL && car->old_material_count >= pEnd) { + car->old_material_count += pStart - pEnd; + car->new_material_count += pStart - pEnd; + } + } + } } // FUNCTION: CARMA2_HW 0x00500f30 @@ -294,7 +339,34 @@ int C2_HOOK_FASTCALL AddPixelmaps(tBrender_storage* pStorage_space, const char* return total; } -// LoadSinglePixelmap +// FUNCTION: CARMA2_HW 0x00501560 +br_pixelmap* C2_HOOK_FASTCALL LoadSinglePixelmap(tBrender_storage* pStorage, const char* pName) { + br_pixelmap* map; + tAdd_to_storage_result addResult; + + map = LoadPixelmap(pName); + if (map == NULL) { + return BrMapFind(pName); + } + + addResult = AddPixelmapToStorage(pStorage, map); + switch (addResult) { + case eStorage_allocated: + BrMapAdd(map); + return map; + case eStorage_duplicate: + if (gDisallow_duplicates) { + FatalError(kFatalError_DuplicatePixelmap_S, map->identifier); + } else { + BrPixelmapFree(map); + } + return gDuplicate_pixelmap; + case eStorage_not_enough_room: + FatalError(kFatalError_InsufficientPixelmapSlots); + break; + } + return NULL; +} // FUNCTION: CARMA2_HW 0x005016a0 br_pixelmap* C2_HOOK_FASTCALL LoadSingleShadeTable(tBrender_storage* pStorage_space, const char* pName) { @@ -324,7 +396,34 @@ br_pixelmap* C2_HOOK_FASTCALL LoadSingleShadeTable(tBrender_storage* pStorage_sp return NULL; } -// LoadSingleMaterial +// FUNCTION: CARMA2_HW 0x005017e0 +br_material* C2_HOOK_FASTCALL LoadSingleMaterial(tBrender_storage* pStorage_space, const char* pName) { + br_material* material; + + material = LoadMaterial(pName); + if (material == NULL) { + return BrMaterialFind(pName); + } + + switch (AddMaterialToStorage(pStorage_space, material)) { + case eStorage_allocated: + BrMaterialAdd(material); + return material; + case eStorage_duplicate: + if (gDisallow_duplicates) { + FatalError(kFatalError_DuplicateMaterial_S, material->identifier); + } else { + BrMaterialFree(material); + } + return gDuplicate_material; + case eStorage_not_enough_room: + FatalError(kFatalError_InsufficientMaterialSlots); + return NULL; + } +#ifdef REC2_FIX_BUGS + return NULL; +#endif +} // FUNCTION: CARMA2_HW 0x00501930 tAdd_to_storage_result C2_HOOK_FASTCALL LoadSingleSound(tBrender_storage* pStorage_space, int pSound_id) { @@ -632,11 +731,20 @@ void C2_HOOK_FASTCALL LoadAllShadeTablesInDirectory(tBrender_storage* pStorage, PFForEveryFile(pPath, LoadIfItsAShadeTable); } -// LoadAllStuffInDirectory +// FUNCTION: CARMA2_HW 0x00502cf0 +void C2_HOOK_FASTCALL LoadAllStuffInDirectory(tBrender_storage* pStorage, const char* pPath, tRendererShadingType pShading) { + + LoadAllShadeTablesInDirectory(pStorage, pPath); + LoadAllPixelmapsInDirectory(pStorage, pPath); + LoadAllImagesInDirectory(pStorage, pPath); + LoadAllMaterialsInDirectory(pStorage, pPath, pShading); + LoadAllModelsInDirectory(pStorage, pPath); +} // FUNCTION: CARMA2_HW 0x00502d60 void C2_HOOK_FASTCALL DisallowDuplicates(void) { + // empty } // FUNCTION: CARMA2_HW 0x00502d70 diff --git a/src/carma2/newcommon/28-world3.h b/src/carma2/newcommon/28-world3.h index 9265531165..b5f1eb4f60 100644 --- a/src/carma2/newcommon/28-world3.h +++ b/src/carma2/newcommon/28-world3.h @@ -6,16 +6,6 @@ extern br_actor* gAdditional_actors; -// TurnOnCloaking - -// RemoveFromCloakingList - -// IsCarCloaked - -// TurnOffCloaking - -// PeriodicCloaking - extern void C2_HOOK_FASTCALL InitTreeSurgery(void); // ModelIsATree @@ -54,9 +44,9 @@ extern void C2_HOOK_FASTCALL InitTreeSurgery(void); extern void C2_HOOK_FASTCALL InitialiseStorageSpace(int pUnknown, tBrender_storage* pStorage_space, int pMax_pixelmaps, int pMax_shade_tables, int pMax_materials, int pMax_models, int pMax_sounds); -// DisposeStorageSpace +extern void C2_HOOK_FASTCALL DisposeStorageSpace(tBrender_storage* pStorage); -extern void C2_HOOK_FASTCALL ClearMatertrialSetFromStorageSpace(tBrender_storage* pStorage_space, int pOld_count, int pNew_count); +extern void C2_HOOK_FASTCALL ClearMatertrialSetFromStorageSpace(tBrender_storage* pStorage_space, int pStart, int pEnd); extern void C2_HOOK_FASTCALL ClearOutStorageSpace(tBrender_storage* pStorage_space); @@ -72,11 +62,11 @@ extern tAdd_to_storage_result C2_HOOK_FASTCALL AddSoundToStorage(tBrender_storag extern int C2_HOOK_FASTCALL AddPixelmaps(tBrender_storage* pStorage_space, const char* path); -// LoadSinglePixelmap +extern br_pixelmap* C2_HOOK_FASTCALL LoadSinglePixelmap(tBrender_storage* pStorage, const char* pName); extern br_pixelmap* C2_HOOK_FASTCALL LoadSingleShadeTable(tBrender_storage* pStorage_space, const char* pName); -// LoadSingleMaterial +extern br_material* C2_HOOK_FASTCALL LoadSingleMaterial(tBrender_storage* pStorage_space, const char* pName); extern tAdd_to_storage_result C2_HOOK_FASTCALL LoadSingleSound(tBrender_storage* pStorage_space, int pSound_id); @@ -106,11 +96,11 @@ extern void C2_HOOK_FASTCALL LoadIfItsAModel(const char* pPath); extern void C2_HOOK_FASTCALL LoadAllModelsInDirectory(tBrender_storage *pStorage, const char* pPath); -// LoadIfItsAShadeTable +extern void C2_HOOK_FASTCALL LoadIfItsAShadeTable(const char* pPath); extern void C2_HOOK_FASTCALL LoadAllShadeTablesInDirectory(tBrender_storage* pStorage, const char* pPath); -extern void C2_HOOK_FASTCALL LoadIfItsAShadeTable(const char* pPath); +extern void C2_HOOK_FASTCALL LoadAllStuffInDirectory(tBrender_storage* pStorage, const char* pPath, tRendererShadingType pShading); extern void C2_HOOK_FASTCALL DisallowDuplicates(void); diff --git a/src/carma2/newcommon/32-spark.c b/src/carma2/newcommon/32-spark.c index c650043e70..7b9eb9072c 100644 --- a/src/carma2/newcommon/32-spark.c +++ b/src/carma2/newcommon/32-spark.c @@ -53,13 +53,22 @@ int gSmoke_on = 1; // ActorFunks -// MasterDisableCarFunks +// STUB: CARMA2_HW 0x004f8ca0 +void C2_HOOK_FASTCALL MasterDisableCarFunks(tCar_spec* pCar) { + NOT_IMPLEMENTED(); +} -// MasterEnableCarFunks +// STUB: CARMA2_HW 0x004f8e10 +void C2_HOOK_FASTCALL MasterEnableCarFunks(tCar_spec* pCar) { + NOT_IMPLEMENTED(); +} // SetPixelmap -// DoCamouflageThing +// STUB: CARMA2_HW 0x004f8f30 +void C2_HOOK_FASTCALL DoCamouflageThing(tCar_spec* pCar) { + NOT_IMPLEMENTED(); +} // DoSolidGraniteThing @@ -79,7 +88,10 @@ int gSmoke_on = 1; // RestorePixelmap -// RestoreCarPixelmaps +// STUB: CARMA2_HW 0x004f9620 +void C2_HOOK_FASTCALL RestoreCarPixelmaps(tCar_spec* pCar_spec) { + NOT_IMPLEMENTED(); +} // MungeShrapnel @@ -211,11 +223,17 @@ int C2_HOOK_FASTCALL GetSmokeOn(void) { // BlendifyMaterialCB -// BlendifyCar +// STUB: CARMA2_HW 0x004fecf0 +void C2_HOOK_FASTCALL BlendifyCar(tCar_spec* pCar) { + NOT_IMPLEMENTED(); +} // UnBlendifyMaterialCB -// UnBlendifyCar +// STUB: CARMA2_HW 0x004fed40 +void C2_HOOK_FASTCALL UnBlendifyCar(tCar_spec* pCar_spec) { + NOT_IMPLEMENTED(); +} // IsCarSmoking diff --git a/src/carma2/newcommon/32-spark.h b/src/carma2/newcommon/32-spark.h index 0a0e8b8781..42686ffd83 100644 --- a/src/carma2/newcommon/32-spark.h +++ b/src/carma2/newcommon/32-spark.h @@ -2,6 +2,7 @@ #define GUARD_32_SPARK_H #include "c2_hooks.h" +#include "rec2_types.h" // DrawDot @@ -53,13 +54,13 @@ // ActorFunks -// MasterDisableCarFunks +extern void C2_HOOK_FASTCALL MasterDisableCarFunks(tCar_spec* pCar); -// MasterEnableCarFunks +extern void C2_HOOK_FASTCALL MasterEnableCarFunks(tCar_spec* pCar_spec); // SetPixelmap -// DoCamouflageThing +extern void C2_HOOK_FASTCALL DoCamouflageThing(tCar_spec* pCar); // DoSolidGraniteThing @@ -79,7 +80,7 @@ // RestorePixelmap -// RestoreCarPixelmaps +extern void C2_HOOK_FASTCALL RestoreCarPixelmaps(tCar_spec* pCar); // MungeShrapnel @@ -197,11 +198,11 @@ extern int C2_HOOK_FASTCALL GetSmokeOn(void); // BlendifyMaterialCB -// BlendifyCar +extern void C2_HOOK_FASTCALL BlendifyCar(tCar_spec* pCar); // UnBlendifyMaterialCB -// UnBlendifyCar +extern void C2_HOOK_FASTCALL UnBlendifyCar(tCar_spec* pCar); // IsCarSmoking diff --git a/src/carma2/newcommon/35-intrface.c b/src/carma2/newcommon/35-intrface.c index 2f89cb3850..5ff081d578 100644 --- a/src/carma2/newcommon/35-intrface.c +++ b/src/carma2/newcommon/35-intrface.c @@ -1,20 +1,344 @@ #include "35-intrface.h" -// SetAlwaysTyping +#include "08-loading1.h" +#include "10-loading2.h" +#include "18-graphics2.h" +#include "19-font.h" +#include "38-flicplay.h" +#include "42-input.h" +#include "69-sound.h" +#include "globvars.h" +#include "platform.h" -// ClearAlwaysTyping +// GLOBAL: CARMA2_HW 0x0068c1f0 +int gAlways_typing; -// ChoiceDisabled +// GLOBAL: CARMA2_HW 0x0068c1ec +int gDisabled_count; -// ResetInterfaceTimeout +// GLOBAL: CARMA2_HW 0x0068c1f8 +int gDisabled_choices[10]; -// ChangeSelection +// GLOBAL: CARMA2_HW 0x0075b8fc +int gTyping_slot; + +// GLOBAL: CARMA2_HW 0x0068c1e8 +const tInterface_spec* gSpec; + +// GLOBAL: CARMA2_HW 0x0068c220 +int gCurrent_mode; + +// GLOBAL: CARMA2_HW 0x0068c224 +int gCurrent_choice; + +// GLOBAL: CARMA2_HW 0x0068c228 +tU32 gStart_time; + +// GLOBAL: CARMA2_HW 0x0079ecb8 +int gMouse_in_use; + +// FUNCTION: CARMA2_HW 0x00484620 +void C2_HOOK_FASTCALL SetAlwaysTyping(void) { + + gAlways_typing = 1; +} + +// FUNCTION: CARMA2_HW 0x00484630 +void C2_HOOK_FASTCALL ClearAlwaysTyping(void) { + + gAlways_typing = 0; +} + +int C2_HOOK_FASTCALL ChoiceDisabled(int pChoice) { + int i; + + for (i = 0; i < gDisabled_count; ++i) { + if (gDisabled_choices[i] == pChoice) { + return 1; + } + } + return 0; +} + +void C2_HOOK_FASTCALL ResetInterfaceTimeout__intrface(void) { + + gStart_time = PDGetTotalTime(); +} + +// FUNCTION: CARMA2_HW 0x00484dd0 +void C2_HOOK_FASTCALL ChangeSelection(const tInterface_spec* pSpec, int* pOld_selection, int* pNew_selection, int pMode, int pSkip_disabled) { + + if (ChoiceDisabled(*pNew_selection)) { + if (pSkip_disabled) { + if (*pOld_selection < *pNew_selection) { + do { + *pNew_selection += 1; + if (*pNew_selection < pSpec->move_up_min[pMode]) { + *pNew_selection = pSpec->move_up_max[pMode]; + } + if (*pNew_selection > pSpec->move_up_max[pMode]) { + *pNew_selection = pSpec->move_up_min[pMode]; + } + } while (*pNew_selection != *pOld_selection && ChoiceDisabled(*pNew_selection)); + } else { + do { + *pNew_selection -= 1; + if (*pNew_selection < pSpec->move_up_min[pMode]) { + *pNew_selection = pSpec->move_up_max[pMode]; + } + if (*pNew_selection > pSpec->move_up_max[pMode]) { + *pNew_selection = pSpec->move_up_min[pMode]; + } + } while (*pNew_selection != *pOld_selection && ChoiceDisabled(*pNew_selection)); + } + } else { + *pNew_selection = *pOld_selection; + } + } + + if (*pOld_selection != *pNew_selection) { + *pOld_selection = *pNew_selection; + } +} // RecopyAreas -// DoInterfaceScreen +// FUNCTION: CARMA2_HW 0x004846e0 +int C2_HOOK_FASTCALL DoInterfaceScreen(const tInterface_spec* pSpec, int pOptions, int pCurrent_choice) { + tProg_status entry_status; + int i; + int last_choice; + int escaped; + int timed_out; + int go_ahead; + int result; + int the_key; + int the_max; + int defeat_mode_change; + char the_str[256]; + + entry_status = gProgram_state.prog_status; + gTyping_slot = -1; + EdgeTriggerModeOn(); + gSpec = pSpec; + gDisabled_count = 0; + LoadInterfaceStuff(gProgram_state.racing); + gProgram_state.dont_save_or_load = pSpec->dont_save_or_load; + for (i = 0; i < pSpec->number_of_button_flics; i++) { + LoadFlic(pSpec->flicker_on_flics[i].flic_index); + LoadFlic(pSpec->flicker_off_flics[i].flic_index); + LoadFlic(pSpec->pushed_flics[i].flic_index); + } + + InitFlicQueue(); + ResetInterfaceTimeout__intrface(); + gCurrent_choice = pCurrent_choice; + gCurrent_mode = pSpec->initial_imode; + if (pSpec->font_needed) { + InitRollingLetters(); + LoadFont(0); + } + KillSplashScreen(); + if (pSpec->start_proc1 != NULL) { + pSpec->start_proc1(); + } + if (pSpec->start_proc2 != NULL) { + pSpec->start_proc2(); + } + last_choice = -1; + ChangeSelection(pSpec, &last_choice, &gCurrent_choice, gCurrent_mode, 0); + WaitForNoKeys(); + gMouse_in_use = 0; + last_choice = gCurrent_choice; + for (;;) { + if (last_choice != gCurrent_choice) { + ChangeSelection(pSpec, &last_choice, &gCurrent_choice, gCurrent_mode, 1); + } + last_choice = gCurrent_choice; + PollKeys(); + EdgeTriggerModeOff(); + the_key = PDAnyKeyDown(); + if (the_key != -1 && the_key != 4) { + gMouse_in_use = 0; + ResetInterfaceTimeout__intrface(); + } + EdgeTriggerModeOn(); + if ((gTyping_slot < 0 || gAlways_typing) && (PDKeyDown(70) || PDKeyDown(85))) { + if (pSpec->move_left_delta[gCurrent_mode] != 0) { + gCurrent_choice += pSpec->move_left_delta[gCurrent_mode]; + if (gCurrent_choice < pSpec->move_left_min[gCurrent_mode]) { + gCurrent_choice = pSpec->move_left_max[gCurrent_mode]; + } + if (gCurrent_choice > pSpec->move_left_max[gCurrent_mode]) { + gCurrent_choice = pSpec->move_left_min[gCurrent_mode]; + } + DRS3StartSound(gEffects_outlet, eSoundId_LeftButton); + } + if (pSpec->move_left_proc[gCurrent_mode] != NULL) { + defeat_mode_change = pSpec->move_left_proc[gCurrent_mode](&gCurrent_choice, &gCurrent_mode); + } else { + defeat_mode_change = 0; + } + if (pSpec->move_left_new_mode[gCurrent_mode] >= 0 && !defeat_mode_change) { + gCurrent_mode = pSpec->move_left_new_mode[gCurrent_mode]; + } + } + if ((gTyping_slot < 0 || gAlways_typing) && (PDKeyDown(71) || PDKeyDown(87))) { + if (pSpec->move_right_delta[gCurrent_mode] != 0) { + gCurrent_choice += pSpec->move_right_delta[gCurrent_mode]; + if (gCurrent_choice < pSpec->move_right_min[gCurrent_mode]) { + gCurrent_choice = pSpec->move_right_max[gCurrent_mode]; + } + if (gCurrent_choice > pSpec->move_right_max[gCurrent_mode]) { + gCurrent_choice = pSpec->move_right_min[gCurrent_mode]; + } + DRS3StartSound(gEffects_outlet, eSoundId_LeftButton); + } + if (pSpec->move_right_proc[gCurrent_mode] != NULL) { + defeat_mode_change = pSpec->move_right_proc[gCurrent_mode](&gCurrent_choice, &gCurrent_mode); + } else { + defeat_mode_change = 0; + } + if (pSpec->move_right_new_mode[gCurrent_mode] >= 0 && !defeat_mode_change) { + gCurrent_mode = pSpec->move_right_new_mode[gCurrent_mode]; + } + } + if (PDKeyDown(72) || PDKeyDown(89)) { + if (pSpec->move_up_delta[gCurrent_mode] != 0) { + gCurrent_choice += pSpec->move_up_delta[gCurrent_mode]; + if (gCurrent_choice < pSpec->move_up_min[gCurrent_mode]) { + gCurrent_choice = pSpec->move_up_max[gCurrent_mode]; + } + if (gCurrent_choice > pSpec->move_up_max[gCurrent_mode]) { + gCurrent_choice = pSpec->move_up_min[gCurrent_mode]; + } + DRS3StartSound(gEffects_outlet, eSoundId_LeftButton); + } + if (pSpec->move_up_proc[gCurrent_mode] != NULL) { + defeat_mode_change = pSpec->move_up_proc[gCurrent_mode](&gCurrent_choice, &gCurrent_mode); + } else { + defeat_mode_change = 0; + } + if (pSpec->move_up_new_mode[gCurrent_mode] >= 0 && !defeat_mode_change) { + gCurrent_mode = pSpec->move_up_new_mode[gCurrent_mode]; + } + } + if (PDKeyDown(73) || PDKeyDown(83)) { + if (pSpec->move_down_delta[gCurrent_mode] != 0) { + gCurrent_choice += pSpec->move_down_delta[gCurrent_mode]; + if (gCurrent_choice < pSpec->move_down_min[gCurrent_mode]) { + gCurrent_choice = pSpec->move_down_max[gCurrent_mode]; + } + if (gCurrent_choice > pSpec->move_down_max[gCurrent_mode]) { + gCurrent_choice = pSpec->move_down_min[gCurrent_mode]; + } + DRS3StartSound(gEffects_outlet, eSoundId_LeftButton); + } + if (pSpec->move_down_proc[gCurrent_mode] != NULL) { + defeat_mode_change = pSpec->move_down_proc[gCurrent_mode](&gCurrent_choice, &gCurrent_mode); + } else { + defeat_mode_change = 0; + } + if (pSpec->move_down_new_mode[gCurrent_mode] >= 0 && !defeat_mode_change) { + gCurrent_mode = pSpec->move_down_new_mode[gCurrent_mode]; + } + } + if (gTyping_slot >= 0 && pSpec->typeable[gCurrent_mode] && gTyping_slot != gCurrent_choice && !gAlways_typing) { + gCurrent_choice = gTyping_slot; + } + if (last_choice != gCurrent_choice) { + ChangeSelection(pSpec, &last_choice, &gCurrent_choice, gCurrent_mode, 1); + } + timed_out = pSpec->time_out && (PDGetTotalTime() >= gStart_time + pSpec->time_out); + RemoveTransientBitmaps(1); + go_ahead = 1; + if (pSpec->go_ahead_proc[gCurrent_mode]) { + go_ahead = pSpec->go_ahead_proc[gCurrent_mode](&gCurrent_choice, &gCurrent_mode); + } + if (PDKeyDown(63)) { + DRS3StartSound(gEffects_outlet, eSoundId_EscEsc); + escaped = pSpec->escape_allowed[gCurrent_mode]; + if (pSpec->escape_proc[gCurrent_mode] != NULL) { + escaped = pSpec->escape_proc[gCurrent_mode](&gCurrent_choice, &gCurrent_mode); + } + } else { + escaped = 0; + } + if (escaped && gTyping_slot >= 0 && !gAlways_typing) { + escaped = 0; + pSpec->get_original_string(0, gTyping_slot, the_str, &the_max); + RevertTyping(gTyping_slot, the_str); + gTyping = 0; + gTyping_slot = -1; + } + if (last_choice != gCurrent_choice) { + ChangeSelection(pSpec, &last_choice, &gCurrent_choice, gCurrent_mode, 1); + } + if (entry_status != eProg_idling && gProgram_state.prog_status == eProg_idling) { + escaped = 1; + } + if (pSpec->exit_proc != NULL) { + if (pSpec->exit_proc(&gCurrent_choice, &gCurrent_mode)) { + break; + } + } + if (go_ahead || timed_out || escaped) { + break; + } + } + + gTyping = 0; + if (pSpec->font_needed) { + EndRollingLetters(); + DisposeFont(0); + } + RemoveTransientBitmaps(1); + FlushFlicQueue(); + for (i = 0; i < pSpec->number_of_button_flics; i++) { + UnlockFlic(pSpec->flicker_on_flics[i].flic_index); + UnlockFlic(pSpec->flicker_off_flics[i].flic_index); + UnlockFlic(pSpec->pushed_flics[i].flic_index); + } + + if (gCurrent_choice == pSpec->escape_code) { + escaped = 1; + go_ahead = 0; + } + if (escaped) { + gCurrent_choice = pSpec->escape_code; + } + if (pSpec->done_proc != NULL) { + result = (pSpec->done_proc)(gCurrent_choice, gCurrent_mode, go_ahead, escaped, timed_out); + } else { + result = gCurrent_choice; + } + gProgram_state.dont_save_or_load = 0; + EndMouseCursor(); + UnlockInterfaceStuff(); + EdgeTriggerModeOff(); + return result; +} + +// FUNCTION: CARMA2_HW 0x00484f40 +int C2_HOOK_FASTCALL WhichItemIsSelectedIn(tFrontend_spec* pFrontend, int pGroup) { + int i; + + for (i = 0; i < pFrontend->count_items; i++) { + tFrontend_item_spec* item = &pFrontend->items[i]; + + if (item->group == pGroup && item->radioButton_selected) { + return i; + } + } + return -1; +} -// WhichItemIsSelectedIn +// FUNCTION: CARMA2_HW 0x00484f70 +void C2_HOOK_FASTCALL SelectThisItemIn(tFrontend_spec* pFrontend, int pGroup, int pValue) { + int i; -// SelectThisItemIn + for (i = pFrontend->radios[pGroup - 1].indexFirstItem; i <= pFrontend->radios[pGroup - 1].indexLastItem; i++) { + pFrontend->items[i].radioButton_selected = i == pValue; + } +} diff --git a/src/carma2/newcommon/35-intrface.h b/src/carma2/newcommon/35-intrface.h index 7a57f0abe8..9744adec3b 100644 --- a/src/carma2/newcommon/35-intrface.h +++ b/src/carma2/newcommon/35-intrface.h @@ -1,22 +1,25 @@ #ifndef GUARD_35_INTRFACE_H #define GUARD_35_INTRFACE_H -// SetAlwaysTyping +#include "c2_hooks.h" +#include "rec2_types.h" -// ClearAlwaysTyping +extern void C2_HOOK_FASTCALL SetAlwaysTyping(void); -// ChoiceDisabled +extern void C2_HOOK_FASTCALL ClearAlwaysTyping(void); -// ResetInterfaceTimeout +extern int C2_HOOK_FASTCALL ChoiceDisabled(int pChoice); -// ChangeSelection +extern void C2_HOOK_FASTCALL ResetInterfaceTimeout__intrface(void); + +extern void C2_HOOK_FASTCALL ChangeSelection(const tInterface_spec* pSpec, int* pOld_selection, int* pNew_selection, int pMode, int pSkip_disabled); // RecopyAreas -// DoInterfaceScreen +extern int C2_HOOK_FASTCALL DoInterfaceScreen(const tInterface_spec* pSpec, int pOptions, int pCurrent_choice); -// WhichItemIsSelectedIn +extern int C2_HOOK_FASTCALL WhichItemIsSelectedIn(tFrontend_spec* pFrontend, int pGroup); -// SelectThisItemIn +extern void C2_HOOK_FASTCALL SelectThisItemIn(tFrontend_spec* pFrontend, int pGroup, int pValue); #endif // GUARD_35_INTRFACE_H diff --git a/src/carma2/newcommon/38-flicplay.c b/src/carma2/newcommon/38-flicplay.c index fe28492457..7d9f20e857 100644 --- a/src/carma2/newcommon/38-flicplay.c +++ b/src/carma2/newcommon/38-flicplay.c @@ -1,5 +1,7 @@ #include "38-flicplay.h" +#include "rec2_types.h" + // GLOBAL: CARMA2_HW 0x0068b8b4 float gFlic_sound_delay_pre_smack; @@ -15,6 +17,9 @@ float gFlic_sound_delay_post_demo; // GLOBAL: CARMA2_HW 0x006861dc int gTranslation_count; +// GLOBAL: CARMA2_HW 0x006861e8 +tFlic_descriptor* gFirst_flic; + // FUNCTION: CARMA2_HW 0x00461990 int C2_HOOK_FASTCALL TranslationMode(void) { @@ -75,19 +80,33 @@ void C2_HOOK_FASTCALL InitFlics(void) { NOT_IMPLEMENTED(); } -// LoadFlic +// FUNCTION: CARMA2_HW 0x00462a60 +int C2_HOOK_FASTCALL LoadFlic(int pIndex) { -// UnlockFlic + return 0; +} + +// STUB: CARMA2_HW 0x00462a70 +void C2_HOOK_FASTCALL UnlockFlic(int pIndex) { + NOT_IMPLEMENTED(); +} // LoadFlicData -// InitFlicQueue +// FUNCTION: CARMA2_HW 0x00462cc0 +void C2_HOOK_FASTCALL InitFlicQueue(void) { + + gFirst_flic = NULL; +} // FlicQueueFinished // ProcessFlicQueue -// FlushFlicQueue +// STUB: CARMA2_HW 0x00462dc0 +void C2_HOOK_FASTCALL FlushFlicQueue(void) { + NOT_IMPLEMENTED(); +} // STUB: CARMA2_HW 0x00463340 void C2_HOOK_FASTCALL LoadInterfaceStrings(void) { diff --git a/src/carma2/newcommon/38-flicplay.h b/src/carma2/newcommon/38-flicplay.h index f22471ed3f..800129fd29 100644 --- a/src/carma2/newcommon/38-flicplay.h +++ b/src/carma2/newcommon/38-flicplay.h @@ -58,19 +58,19 @@ extern void C2_HOOK_FASTCALL FlicPaletteAllocate(void); extern void C2_HOOK_FASTCALL InitFlics(void); -// LoadFlic +extern int C2_HOOK_FASTCALL LoadFlic(int pIndex); -// UnlockFlic +extern void C2_HOOK_FASTCALL UnlockFlic(int pIndex); // LoadFlicData -// InitFlicQueue +extern void C2_HOOK_FASTCALL InitFlicQueue(void); // FlicQueueFinished // ProcessFlicQueue -// FlushFlicQueue +extern void C2_HOOK_FASTCALL FlushFlicQueue(void); extern void C2_HOOK_FASTCALL LoadInterfaceStrings(void); diff --git a/src/carma2/newcommon/42-input.c b/src/carma2/newcommon/42-input.c index e9b9c6269f..e38b4d3311 100644 --- a/src/carma2/newcommon/42-input.c +++ b/src/carma2/newcommon/42-input.c @@ -3,9 +3,15 @@ // GLOBAL: CARMA2_HW 0x0074b5e0 int gKey_mapping[77]; +// GLOBAL: CARMA2_HW 0x0068c1c4 +int gEdge_trigger_mode; + // SetJoystickArrays -// PollKeys +// STUB: CARMA2_HW 0x00481eb0 +void C2_HOOK_FASTCALL PollKeys(void) { + NOT_IMPLEMENTED(); +} // CyclePollKeys @@ -27,7 +33,10 @@ int C2_HOOK_FASTCALL PDKeyDown(int pKey_index) { // PDKeyDown3 -// PDAnyKeyDown +// STUB: CARMA2_HW 0x00482a00 +int C2_HOOK_FASTCALL PDAnyKeyDown(void) { + NOT_IMPLEMENTED(); +} // STUB: CARMA2_HW 0x00482d70 int C2_HOOK_FASTCALL AnyKeyDown(void) { @@ -43,21 +52,42 @@ int C2_HOOK_FASTCALL KeyIsDown(int pKey_index) { // KeyIsDownNoMouldiness -// WaitForNoKeys +// STUB: CARMA2_HW 0x004833b0 +void C2_HOOK_FASTCALL WaitForNoKeys(void) { + NOT_IMPLEMENTED(); +} // GetMousePosition -// InitRollingLetters +// STUB: CARMA2_HW 0x00483c90 +void C2_HOOK_FASTCALL InitRollingLetters(void) { + NOT_IMPLEMENTED(); +} -// EndRollingLetters +// STUB: CARMA2_HW 0x00483ce0 +void C2_HOOK_FASTCALL EndRollingLetters(void) { + NOT_IMPLEMENTED(); +} // AddRollingLetter // ChangeCharTo -// RevertTyping +// STUB: CARMA2_HW 0x00484120 +void C2_HOOK_FASTCALL RevertTyping(int pSlot_index, char* pRevert_str) { + NOT_IMPLEMENTED(); +} -// EdgeTriggerModeOn +// FUNCTION: CARMA2_HW 0x00484600 +void C2_HOOK_FASTCALL EdgeTriggerModeOn(void) { -// EdgeTriggerModeOff + gEdge_trigger_mode = 1; +} + + +// FUNCTION: CARMA2_HW 0x00484610 +void C2_HOOK_FASTCALL EdgeTriggerModeOff(void) { + + gEdge_trigger_mode = 0; +} diff --git a/src/carma2/newcommon/42-input.h b/src/carma2/newcommon/42-input.h index 76238abe87..5f29517534 100644 --- a/src/carma2/newcommon/42-input.h +++ b/src/carma2/newcommon/42-input.h @@ -7,7 +7,7 @@ extern int gKey_mapping[77]; // SetJoystickArrays -// PollKeys +extern void C2_HOOK_FASTCALL PollKeys(void); // CyclePollKeys @@ -25,7 +25,7 @@ extern int C2_HOOK_FASTCALL PDKeyDown(int pKey_index); // PDKeyDown3 -// PDAnyKeyDown +extern int C2_HOOK_FASTCALL PDAnyKeyDown(void); extern int C2_HOOK_FASTCALL AnyKeyDown(void); @@ -35,22 +35,22 @@ extern int C2_HOOK_FASTCALL KeyIsDown(int pKey_index); // KeyIsDownNoMouldiness -// WaitForNoKeys +extern void C2_HOOK_FASTCALL WaitForNoKeys(void); // GetMousePosition -// InitRollingLetters +extern void C2_HOOK_FASTCALL InitRollingLetters(void); -// EndRollingLetters +extern void C2_HOOK_FASTCALL EndRollingLetters(void); // AddRollingLetter // ChangeCharTo -// RevertTyping +extern void C2_HOOK_FASTCALL RevertTyping(int pSlot_index, char* pRevert_str); -// EdgeTriggerModeOn +extern void C2_HOOK_FASTCALL EdgeTriggerModeOn(void); -// EdgeTriggerModeOff +extern void C2_HOOK_FASTCALL EdgeTriggerModeOff(void); #endif // GUARD_42_INPUT_H diff --git a/src/carma2/newcommon/50-fog.c b/src/carma2/newcommon/50-fog.c index d8e42f18f9..b79e51988b 100644 --- a/src/carma2/newcommon/50-fog.c +++ b/src/carma2/newcommon/50-fog.c @@ -22,5 +22,8 @@ void C2_HOOK_FASTCALL DisableAutoFogification(void) { NOT_IMPLEMENTED(); } -// RemoveMaterialFromFogification +// STUB: CARMA2_HW 0x004ea860 +void C2_HOOK_FASTCALL RemoveMaterialFromFogification(br_material* pMaterial) { + NOT_IMPLEMENTED(); +} diff --git a/src/carma2/newcommon/50-fog.h b/src/carma2/newcommon/50-fog.h index ba954d79ee..fbcaaba5ea 100644 --- a/src/carma2/newcommon/50-fog.h +++ b/src/carma2/newcommon/50-fog.h @@ -2,6 +2,7 @@ #define GUARD_50_FOG_H #include "c2_hooks.h" +#include extern void C2_HOOK_FASTCALL InitFogificateMaterials(void); @@ -15,6 +16,6 @@ extern void C2_HOOK_FASTCALL InitFogificateMaterials(void); extern void C2_HOOK_FASTCALL DisableAutoFogification(void); -// RemoveMaterialFromFogification +extern void C2_HOOK_FASTCALL RemoveMaterialFromFogification(br_material* pMaterial); #endif // GUARD_50_FOG_H diff --git a/src/carma2/newcommon/69-sound.c b/src/carma2/newcommon/69-sound.c index 854d4e60c6..3ab2709882 100644 --- a/src/carma2/newcommon/69-sound.c +++ b/src/carma2/newcommon/69-sound.c @@ -77,6 +77,9 @@ const char* gSound_periodicity_choices[3] = { // GLOBAL: CARMA2_HW 0x00595c48 int gSound_detail_level = 1; +// GLOBAL: CARMA2_HW 0x006845fc +tS3_outlet* gEffects_outlet; + // FUNCTION: CARMA2_HW 0x00500060 void C2_HOOK_FASTCALL SplungeSomeData(void* pData, br_size_t size) { @@ -119,7 +122,10 @@ void C2_HOOK_FASTCALL InitSound(void) { NOT_IMPLEMENTED(); } -// DRS3StartSound +// STUB: CARMA2_HW 0x00455690 +tS3_sound_tag C2_HOOK_FASTCALL DRS3StartSound(tS3_outlet* pOutlet, tS3_sound_id pSound) { + NOT_IMPLEMENTED(); +} int C2_HOOK_FASTCALL DRS3StartSoundNoPiping(tS3_outlet* pOutlet, tS3_sound_id pSound) { if (gSound_enabled) { diff --git a/src/carma2/newcommon/69-sound.h b/src/carma2/newcommon/69-sound.h index 48d3f11568..12f06f5f98 100644 --- a/src/carma2/newcommon/69-sound.h +++ b/src/carma2/newcommon/69-sound.h @@ -9,6 +9,8 @@ #include +extern tS3_outlet* gEffects_outlet; + extern int gCD_fully_installed; extern void C2_HOOK_FASTCALL SplungeSomeData(void* pData, br_size_t size); @@ -17,7 +19,7 @@ extern void C2_HOOK_FASTCALL UsePathFileToDetermineIfFullInstallation(void); extern void C2_HOOK_FASTCALL InitSound(void); -// DRS3StartSound +extern tS3_sound_tag C2_HOOK_FASTCALL DRS3StartSound(tS3_outlet* pOutlet, tS3_sound_id pSound); extern int C2_HOOK_FASTCALL DRS3StartSoundNoPiping(tS3_outlet* pOutlet, tS3_sound_id pSound);