diff --git a/source/game_sa/Radar.cpp b/source/game_sa/Radar.cpp index 0ea3ae7cb9..45a2de6e19 100644 --- a/source/game_sa/Radar.cpp +++ b/source/game_sa/Radar.cpp @@ -147,7 +147,7 @@ void CRadar::InjectHooks() { RH_ScopedInstall(ShowRadarTraceWithHeight, 0x584070); RH_ScopedInstall(DrawCoordBlip, 0x586D60); - RH_ScopedInstall(SetupAirstripBlips, 0x587D20, {.reversed = false}); // TEST + RH_ScopedInstall(SetupAirstripBlips, 0x587D20); // TEST RH_ScopedInstall(DrawBlips, 0x588050); // RH_ScopedInstall(ClipRadarPoly, 0x585040); // RH_ScopedInstall(DrawAreaOnRadar, 0x5853D0); @@ -239,10 +239,6 @@ int32 CRadar::GetActualBlipArrayIndex(tBlipHandle blip) { // 0x5828A0 void CRadar::DrawLegend(int32 x, int32 y, eRadarSprite blipType) { - if (blipType == RADAR_SPRITE_NONE) { // None => Player position - blipType = RADAR_SPRITE_MAP_HERE; - } - CFont::PrintString( (float)x + SCREEN_STRETCH_X(20.0f), (float)y + SCREEN_STRETCH_Y(3.0f), @@ -253,13 +249,18 @@ void CRadar::DrawLegend(int32 x, int32 y, eRadarSprite blipType) { RadarBlipSprites[blipType].Draw( { (float)x, (float)y, - (float)x + SCREEN_STRETCH_X(16.0f), (float)y + SCREEN_STRETCH_Y(16.0f) + (float)x + SCREEN_STRETCH_X(16.0f), (float)y + SCREEN_STRETCH_X(16.0f) }, + // NOTE: `y + SCREEN_STRETCH_X(16.0f)` is correct. It is here to make sprites + // square instead of dependent on the aspect ratio. { 255, 255, 255, 255 } ); return; } + static auto& legendTraceHeight = StaticRef(); // = eRadarTraceHeight::RADAR_TRACE_LOW; + static auto& legendTraceTimer = StaticRef(); // = CTimer::GetTimeInMS(); + if (CTimer::GetTimeInMSPauseMode() - legendTraceTimer > 600) { legendTraceTimer = CTimer::GetTimeInMSPauseMode(); @@ -425,13 +426,7 @@ void CRadar::TransformRadarPointToScreenSpace(CVector2D& out, const CVector2D& i * @addr 0x583530 */ void CRadar::TransformRealWorldPointToRadarSpace(CVector2D& out, const CVector2D& in) { - const auto xOffset = (in.x - vec2DRadarOrigin.x) / m_radarRange; - const auto yOffset = (in.y - vec2DRadarOrigin.y) / m_radarRange; - - out = { - cachedSin * yOffset + cachedCos * xOffset, - cachedCos * yOffset - cachedSin * xOffset - }; + out = CachedRotateClockwise((in - vec2DRadarOrigin) / m_radarRange); } /*! @@ -439,10 +434,7 @@ void CRadar::TransformRealWorldPointToRadarSpace(CVector2D& out, const CVector2D * @addr 0x5835A0 */ void CRadar::TransformRadarPointToRealWorldSpace(CVector2D& out, const CVector2D& in) { - out = CVector2D{ - cachedCos * in.x - cachedSin * in.y, - cachedCos * in.y + cachedSin * in.x - } * m_radarRange + vec2DRadarOrigin; + out = CachedRotateCounterclockwise(in) * m_radarRange + vec2DRadarOrigin; } /*! @@ -495,7 +487,7 @@ void CRadar::CalculateCachedSinCos() { * @brief Creates a new coordinate blip (i.e. tracing blip with no sprite) * @param type Type * @param posn Position - * @param color Color + * @param color Color (Unused) * @param blipDisplay Display option * @param scriptName Script name (Unused) (from Android) * @addr 0x583820 @@ -511,7 +503,7 @@ tBlipHandle CRadar::SetCoordBlip(eBlipType type, CVector posn, eBlipColour color t.m_vPosition = posn; t.m_nBlipDisplayFlag = blipDisplay; t.m_nBlipType = type; - t.m_nColour = color; + t.m_nColour = BLIP_COLOUR_DESTINATION; t.m_fSphereRadius = 1.f; t.m_nEntityHandle = 0; t.m_nBlipSize = 1; @@ -851,10 +843,15 @@ void CRadar::ShowRadarTrace(float x, float y, uint32 size, CRGBA color) { * @brief Draws a coordinate blip to the map with height information. * @addr 0x584070 */ -void CRadar::ShowRadarTraceWithHeight(float x, float y, uint32 size, CRGBA color, eRadarTraceHeight height) { +void CRadar::ShowRadarTraceWithHeight(float x, float y, uint32 size, uint32 R, uint32 G, uint32 B, uint32 A, eRadarTraceHeight height) { Limit(x, y); RwRenderStateSet(rwRENDERSTATETEXTURERASTER, RWRSTATE(NULL)); + // NOTE: Those RGBA parameters are 4-bytes per channel. + // then we construct 1-byte per channel CRGBA. It's stupid isn't it? + // NOTE: {R,G,B,A} > 255 is possible, so we can't assert for x <= UCHAR_MAX. + const auto r = static_cast(R), g = static_cast(G), b = static_cast(B), a = static_cast(A); + const auto size0 = float(size + 0), size1 = float(size + 1); const auto size2 = float(size + 2), size3 = float(size + 3); @@ -865,23 +862,23 @@ void CRadar::ShowRadarTraceWithHeight(float x, float y, uint32 size, CRGBA color x, y + SCREEN_STRETCH_Y(size3), x + SCREEN_STRETCH_X(size3), y - SCREEN_STRETCH_Y(size2), x - SCREEN_STRETCH_X(size3), y - SCREEN_STRETCH_Y(size2), - { 0, 0, 0, color.a } + { 0, 0, 0, a } ); CSprite2d::Draw2DPolygon( // draw triangle x, y + SCREEN_STRETCH_Y(size1), x, y + SCREEN_STRETCH_Y(size1), x + SCREEN_STRETCH_X(size1), y - SCREEN_STRETCH_Y(size1), x - SCREEN_STRETCH_X(size1), y - SCREEN_STRETCH_Y(size1), - color + { r, g, b, a } ); break; case RADAR_TRACE_NORMAL: CSprite2d::DrawRect( // draw black border - CRect( + { x - SCREEN_STRETCH_X(size1), y - SCREEN_STRETCH_Y(size1), x + SCREEN_STRETCH_X(size1), y + SCREEN_STRETCH_Y(size1) - ), - { 0, 0, 0, color.a } + }, + { 0, 0, 0, a } ); CSprite2d::DrawRect( // draw box @@ -889,7 +886,7 @@ void CRadar::ShowRadarTraceWithHeight(float x, float y, uint32 size, CRGBA color x - SCREEN_STRETCH_X(size0), y - SCREEN_STRETCH_Y(size0), x + SCREEN_STRETCH_X(size0), y + SCREEN_STRETCH_Y(size0) }, - color + { r, g, b, a } ); break; case RADAR_TRACE_LOW: @@ -898,7 +895,7 @@ void CRadar::ShowRadarTraceWithHeight(float x, float y, uint32 size, CRGBA color x - SCREEN_STRETCH_X(size3), y + SCREEN_STRETCH_Y(size2), x, y - SCREEN_STRETCH_Y(size3), x, y - SCREEN_STRETCH_Y(size3), - { 0, 0, 0, color.a } + { 0, 0, 0, a } ); CSprite2d::Draw2DPolygon( // draw triangle @@ -906,7 +903,7 @@ void CRadar::ShowRadarTraceWithHeight(float x, float y, uint32 size, CRGBA color x - SCREEN_STRETCH_X(size1), y + SCREEN_STRETCH_Y(size1), x, y - SCREEN_STRETCH_Y(size1), x, y - SCREEN_STRETCH_Y(size1), - color + { r, g, b, a } ); break; } @@ -998,7 +995,7 @@ void CRadar::DrawYouAreHereSprite(float x, float y) { ); } - MapLegendList[++MapLegendCounter] = RADAR_SPRITE_MAP_HERE; + MapLegendList[MapLegendCounter++] = RADAR_SPRITE_MAP_HERE; } // 0x584A80 @@ -1181,7 +1178,7 @@ void CRadar::InitFrontEndMap() { rng::fill(MapLegendList, RADAR_SPRITE_NONE); vec2DRadarOrigin.Set(0.0f, 0.0f); - m_radarRange = 2990.0f; // todo: world const - 1.0f + m_radarRange = WORLD_BOUND_RANGE - 10.0f; MapLegendCounter = 0; rng::fill(ArrowBlipColour, CRGBA(0, 0, 0, 0)); @@ -1532,7 +1529,7 @@ void CRadar::DrawRadarMap() { const auto vehicle = FindPlayerVehicle(); // Draw green rectangle when in plane - if (vehicle && vehicle->IsSubPlane() && ModelIndices::IsVortex(vehicle->m_nModelIndex)) { + if (vehicle && vehicle->IsSubPlane() && !ModelIndices::IsVortex(vehicle->m_nModelIndex)) { CVector playerPos = FindPlayerCentreOfWorld_NoInteriorShift(0); const auto cSin = cachedSin; @@ -1562,7 +1559,6 @@ void CRadar::DrawRadarMap() { } // 0x586B00 -// TODO: Fix me - Zoom incorrect void CRadar::DrawMap() { const auto player = FindPlayerPed(); const auto mapShouldDrawn = !CGame::currArea && player->m_nAreaCode == 0 && FrontEndMenuManager.m_nRadarMode != 1; @@ -1578,7 +1574,7 @@ void CRadar::DrawMap() { else m_radarRange = RADAR_MIN_RANGE; } else { - if (vehicle && vehicle->IsSubPlane() && ModelIndices::IsVortex(vehicle->m_nModelIndex)) { + if (vehicle && vehicle->IsSubPlane() && !ModelIndices::IsVortex(vehicle->m_nModelIndex)) { const auto speedZ = vehicle->GetPosition().z * 1.0f / 200.0f; if (speedZ < RADAR_MIN_SPEED) @@ -1652,17 +1648,17 @@ void CRadar::DrawCoordBlip(int32 blipIndex, bool isSprite) { } const auto GetHeight = [&] { - const auto zDiff = trace.GetWorldPos().z - FindPlayerCentreOfWorld_NoInteriorShift().z; + const auto zDiff = trace.GetWorldPos().z - FindPlayerCentreOfWorld_NoInteriorShift(PED_TYPE_PLAYER1).z; - if (zDiff < 2.0f) { + if (zDiff > 2.0f) { // trace is higher return RADAR_TRACE_LOW; - } else if (zDiff < -4.0f) { - // player is higher - return RADAR_TRACE_HIGH; - } else { + } else if (zDiff >= -4.0f) { // they are at the around the same elevation. return RADAR_TRACE_NORMAL; + } else { + // player is higher + return RADAR_TRACE_HIGH; } }; @@ -1671,12 +1667,10 @@ void CRadar::DrawCoordBlip(int32 blipIndex, bool isSprite) { screenPos.x, screenPos.y, trace.m_nBlipSize, - { - color.r, - color.g, - color.b, - trace.m_bBlipFade ? color.a : CalculateBlipAlpha(realDist) - }, + color.r, + color.g, + color.b, + trace.m_bBlipFade ? color.a : CalculateBlipAlpha(realDist), GetHeight() ); @@ -1754,7 +1748,11 @@ CVector GetAirStripLocation(eAirstripLocation location) { // 0x587D20 void CRadar::SetupAirstripBlips() { if (const auto veh = FindPlayerVehicle(); veh && veh->IsSubPlane() && !ModelIndices::IsVortex(veh->m_nModelIndex)) { - if ((CTimer::GetFrameCounter() & 4) == 0) { + // FIX_BUGS: FPS independent counter. SA: (CTimer::GetFrameCounter() & 4) == 0 + static auto airstripBlipCounter = CTimer::GetTimeInMS() + 200; + if (CTimer::GetTimeInMS() >= airstripBlipCounter) { + airstripBlipCounter = CTimer::GetTimeInMS() + 200; + if (airstrip_blip) return; diff --git a/source/game_sa/Radar.h b/source/game_sa/Radar.h index 447728d4ce..50e18519c6 100644 --- a/source/game_sa/Radar.h +++ b/source/game_sa/Radar.h @@ -203,10 +203,6 @@ class CRadar { static inline float& cachedCos = *(float*)0xBA8308; static inline float& cachedSin = *(float*)0xBA830C; - // original name unknown - static inline eRadarTraceHeight& legendTraceHeight = *(eRadarTraceHeight*)0xBAA350; - static inline uint32& legendTraceTimer = *(uint32*)0xBAA354; - static SpriteFileName RadarBlipFileNames[]; static inline float& m_radarRange = *(float*)0xBA8314; // 2990.0 by default @@ -257,7 +253,7 @@ class CRadar { static void SetBlipFriendly(tBlipHandle blip, bool friendly); static void SetBlipEntryExit(tBlipHandle blip, CEntryExit* enex); static void ShowRadarTrace(float x, float y, uint32 size, CRGBA color); - static void ShowRadarTraceWithHeight(float x, float y, uint32 size, CRGBA color, eRadarTraceHeight height); + static void ShowRadarTraceWithHeight(float x, float y, uint32 size, uint32 r, uint32 g, uint32 b, uint32 a, eRadarTraceHeight height); static void ShowRadarMarker(CVector posn, uint32 color, float radius); static uint32 GetRadarTraceColour(eBlipColour color, bool bright, bool friendly); static void DrawRotatingRadarSprite(CSprite2d& sprite, float x, float y, float angle, uint32 width, uint32 height, CRGBA color); @@ -313,7 +309,7 @@ class CRadar { static auto CachedRotateClockwise(const CVector2D& point) { return CVector2D{ - cachedCos * point.x + cachedSin * point.y, + +cachedCos * point.x + cachedSin * point.y, -cachedSin * point.x + cachedCos * point.y }; } diff --git a/source/game_sa/Scripts/Commands/Player.cpp b/source/game_sa/Scripts/Commands/Player.cpp index 54ab8d4fb2..15eba72be6 100644 --- a/source/game_sa/Scripts/Commands/Player.cpp +++ b/source/game_sa/Scripts/Commands/Player.cpp @@ -234,7 +234,6 @@ void notsa::script::commands::player::RegisterHandlers() { REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_PLAYER_MOOD); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_IS_PLAYER_WEARING); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_PLAYER_CAN_DO_DRIVE_BY); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_PLAYER_DRUNKENNESS); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_GET_PLAYER_DRUNKENNESS); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_PLAYER_DRUG_LEVEL); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_GET_PLAYER_DRUG_LEVEL); @@ -243,19 +242,11 @@ void notsa::script::commands::player::RegisterHandlers() { REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_CHECK_FOR_PED_MODEL_AROUND_PLAYER); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_PLAYER_HAS_MET_DEBBIE_HARRY); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_MAKE_PLAYER_FIRE_PROOF); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_INCREASE_PLAYER_MAX_HEALTH); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_INCREASE_PLAYER_MAX_ARMOUR); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_ENSURE_PLAYER_HAS_DRIVE_BY_WEAPON); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_GET_BUS_FARES_COLLECTED_BY_PLAYER); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_IS_PLAYER_IN_INFO_ZONE); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_GANG_ATTACK_PLAYER_WITH_COPS); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_IS_PLAYER_IN_SHORTCUT_TAXI); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_TASK_PLAYER_ON_FOOT); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_TASK_PLAYER_IN_CAR); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_IS_PLAYER_TARGETTING_ANYTHING); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_GET_CLOSEST_BUYABLE_OBJECT_TO_PLAYER); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_DISABLE_PLAYER_SPRINT); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_DELETE_PLAYER); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_TWO_PLAYER_CAMERA_MODE); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_LIMIT_TWO_PLAYER_DISTANCE); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_RELEASE_TWO_PLAYER_DISTANCE); @@ -271,7 +262,6 @@ void notsa::script::commands::player::RegisterHandlers() { REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_TWO_PLAYER_CAM_MODE_SAME_CAR_SHOOTING); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_TWO_PLAYER_CAM_MODE_SAME_CAR_NO_SHOOTING); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_TWO_PLAYER_CAM_MODE_NOT_BOTH_IN_CAR); - REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_ENABLE_ENTRY_EXIT_PLAYER_GROUP_WARPING); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_OBJECT_ONLY_DAMAGED_BY_PLAYER); REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_SET_PLAYER_FIRE_BUTTON); //REGISTER_COMMAND_UNIMPLEMENTED(COMMAND_IS_PLAYER_IN_POSITION_FOR_CONVERSATION); diff --git a/source/game_sa/World.h b/source/game_sa/World.h index af585d62d0..c933549f25 100644 --- a/source/game_sa/World.h +++ b/source/game_sa/World.h @@ -30,6 +30,7 @@ constexpr int32 MAX_LOD_PTR_LISTS_X = 30; constexpr int32 MAX_LOD_PTR_LISTS_Y = 30; constexpr int32 MAX_LOD_PTR_LISTS = MAX_LOD_PTR_LISTS_X * MAX_LOD_PTR_LISTS_Y; +constexpr inline float WORLD_BOUND_RANGE = 3000.0f; constexpr inline CRect WORLD_BOUNDS{-3000.0F, -3000.0F, 3000.0F, 3000.0F}; constexpr float MAP_Z_LOW_LIMIT = -100.0f;