From 4e770c258b9ad9f0239e2a7a91201b29b4b3e5f8 Mon Sep 17 00:00:00 2001 From: Alexis Murzeau Date: Mon, 8 Aug 2022 21:54:06 +0200 Subject: [PATCH] Fix flipper animation and angle calculation Checked with a slowed down flipper (reduced retractTime and extendTime) to ensure the flipper position is correct even when not finished while pressing the flipper control. --- SpaceCadetPinball/TFlipper.cpp | 4 ++-- SpaceCadetPinball/TFlipperEdge.cpp | 21 +++++++++------------ 2 files changed, 11 insertions(+), 14 deletions(-) diff --git a/SpaceCadetPinball/TFlipper.cpp b/SpaceCadetPinball/TFlipper.cpp index 4fece3b..bd40e5a 100644 --- a/SpaceCadetPinball/TFlipper.cpp +++ b/SpaceCadetPinball/TFlipper.cpp @@ -137,7 +137,7 @@ void TFlipper::TimerExpired(int timerId, void* caller) auto flip = static_cast(caller); int bmpCountSub1 = flip->ListBitmap->size() - 1; - auto newBmpIndex = static_cast(floor((pb::time_now - flip->InputTime) / flip->TimerTime)); + auto newBmpIndex = static_cast(floor(flip->FlipperEdge->flipper_angle(pb::time_now) / flip->FlipperEdge->AngleMax * bmpCountSub1 + 0.5)); if (newBmpIndex > bmpCountSub1) newBmpIndex = bmpCountSub1; if (newBmpIndex < 0) @@ -155,7 +155,7 @@ void TFlipper::TimerExpired(int timerId, void* caller) } if (flip->MessageField == 2) { - flip->BmpIndex = bmpCountSub1 - newBmpIndex; + flip->BmpIndex = newBmpIndex; if (flip->BmpIndex <= 0) { flip->BmpIndex = 0; diff --git a/SpaceCadetPinball/TFlipperEdge.cpp b/SpaceCadetPinball/TFlipperEdge.cpp index aa8c63b..7d17567 100644 --- a/SpaceCadetPinball/TFlipperEdge.cpp +++ b/SpaceCadetPinball/TFlipperEdge.cpp @@ -418,19 +418,17 @@ float TFlipperEdge::flipper_angle(float timeNow) { if (!FlipperFlag) return Angle1; - float angle = (Angle1 - Angle2) / AngleMax * AngleMult; - if (angle < 0.0f) - angle = -angle; - if (angle >= 0.0000001f) - angle = (timeNow - InputTime) / angle; + float currentAngleDuration = fabsf((Angle1 - Angle2) / AngleMax * AngleMult); + float currentAngleRatio; + + if (currentAngleDuration >= 0.0000001f) + currentAngleRatio = (timeNow - InputTime) / currentAngleDuration; else - angle = 1.0; + currentAngleRatio = 1.0; - angle = std::min(1.0f, std::max(angle, 0.0f)); - if (FlipperFlag == 2) - angle = 1.0f - angle; - return angle * AngleMax; + currentAngleRatio = std::min(1.0f, std::max(currentAngleRatio, 0.0f)); + return currentAngleRatio * (Angle1 - Angle2) + Angle2; } int TFlipperEdge::is_ball_inside(float x, float y) @@ -482,8 +480,7 @@ void TFlipperEdge::SetMotion(int code, float value) default: break; } - if (!FlipperFlag) - InputTime = value; + InputTime = value; FlipperFlag = code; AngleStopTime = AngleMult + InputTime; }