aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/crepe/api/LoopManager.cpp2
-rw-r--r--src/crepe/manager/LoopTimerManager.cpp7
-rw-r--r--src/crepe/manager/LoopTimerManager.h42
-rw-r--r--src/test/LoopManagerTest.cpp22
4 files changed, 60 insertions, 13 deletions
diff --git a/src/crepe/api/LoopManager.cpp b/src/crepe/api/LoopManager.cpp
index 4d97e16..d17aee1 100644
--- a/src/crepe/api/LoopManager.cpp
+++ b/src/crepe/api/LoopManager.cpp
@@ -48,7 +48,7 @@ void LoopManager::loop() {
while (game_running) {
this->loop_timer.update();
- while (this->loop_timer.get_lag() >= this->loop_timer.get_fixed_delta_time()) {
+ while (this->loop_timer.get_lag() >= this->loop_timer.get_scaled_fixed_delta_time()) {
this->process_input();
this->fixed_update();
this->loop_timer.advance_fixed_update();
diff --git a/src/crepe/manager/LoopTimerManager.cpp b/src/crepe/manager/LoopTimerManager.cpp
index e30b90d..5d4545f 100644
--- a/src/crepe/manager/LoopTimerManager.cpp
+++ b/src/crepe/manager/LoopTimerManager.cpp
@@ -82,3 +82,10 @@ void LoopTimerManager::enforce_frame_rate() {
double LoopTimerManager::get_lag() const {
return (this->elapsed_time - this->elapsed_fixed_time).count();
}
+double LoopTimerManager::get_scaled_fixed_delta_time() const{
+ return this->fixed_delta_time.count() * this->time_scale;
+}
+void LoopTimerManager::set_fixed_delta_time(int seconds) {
+ this->fixed_delta_time = std::chrono::duration<double>(seconds);
+}
+
diff --git a/src/crepe/manager/LoopTimerManager.h b/src/crepe/manager/LoopTimerManager.h
index cd05bf2..8fb4461 100644
--- a/src/crepe/manager/LoopTimerManager.h
+++ b/src/crepe/manager/LoopTimerManager.h
@@ -65,6 +65,35 @@ public:
*/
void set_time_scale(double time_scale);
+ /**
+ * \brief Get the scaled fixed delta time om seconds.
+ *
+ * The fixed delta time is used for operations that require uniform time steps,
+ * such as physics calculations, and is scaled by the current time scale.
+ *
+ * \return The fixed delta time, scaled by time scale, in seconds.
+ */
+ double get_scaled_fixed_delta_time() const;
+
+ /**
+ * \brief Get the fixed delta time in seconds without scaling by the time scale.
+ *
+ * This value is used in the LoopManager to determine how many times
+ * the fixed_update should be called within a given interval.
+ *
+ * \return The unscaled fixed delta time in seconds.
+ */
+ double get_fixed_delta_time() const;
+
+ /**
+ * \brief Set the fixed_delta_time in seconds.
+ *
+ * \param ms fixed_delta_time in seconds.
+ *
+ * The fixed_delta_time value is used to determine how many times per second the fixed_update and process_input functions are called.
+ */
+ void set_fixed_delta_time(int seconds);
+
private:
friend class LoopManager;
@@ -81,17 +110,6 @@ private:
* necessary.
*/
void enforce_frame_rate();
-
- /**
- * \brief Get the fixed delta time for consistent updates.
- *
- * Fixed delta time is used for operations that require uniform time steps, such as physics
- * calculations.
- *
- * \return Fixed delta time in seconds.
- */
- double get_fixed_delta_time() const;
-
/**
* \brief Get the accumulated lag in the game loop.
*
@@ -123,7 +141,7 @@ private:
int target_fps = 50;
//! Actual frames per second
int actual_fps = 0;
- //! time scale for speeding up or slowing down the game (0 = pause, < 1 = slow down, 1 = normal speed, > 1 = speed up)
+ //! Time scale for speeding up or slowing down the game (0 = pause, < 1 = slow down, 1 = normal speed, > 1 = speed up)
double time_scale = 1;
//! Maximum delta time in seconds to avoid large jumps
std::chrono::duration<double> maximum_delta_time{0.25};
diff --git a/src/test/LoopManagerTest.cpp b/src/test/LoopManagerTest.cpp
index f73605e..55ccbb3 100644
--- a/src/test/LoopManagerTest.cpp
+++ b/src/test/LoopManagerTest.cpp
@@ -45,6 +45,28 @@ TEST_F(LoopManagerTest, FixedUpdate) {
// Test finished
}
+TEST_F(LoopManagerTest, ScaledFixedUpdate) {
+ // Arrange
+ test_loop.loop_timer.set_target_fps(60);
+
+ // Set expectations for the mock calls
+ EXPECT_CALL(test_loop, render).Times(::testing::Exactly(60));
+ EXPECT_CALL(test_loop, update).Times(::testing::Exactly(60));
+ EXPECT_CALL(test_loop, fixed_update).Times(::testing::Exactly(50));
+
+ // Start the loop in a separate thread
+ std::thread loop_thread([&]() { test_loop.start(); });
+
+ // Let the loop run for exactly 1 second
+ std::this_thread::sleep_for(std::chrono::seconds(1));
+
+ // Stop the game loop
+ test_loop.game_running = false;
+ // Wait for the loop thread to finish
+ loop_thread.join();
+
+ // Test finished
+}
TEST_F(LoopManagerTest, ShutDown) {
// Arrange
test_loop.loop_timer.set_target_fps(60);