14 frame_update_queued( false ),
15 frame_clients_iterator( frame_clients.end() )
25 this->frame_length_ms += delta_ms;
30 this->frame_update_queued =
true;
32 for( TimeData & time : this->time_data )
34 double add = double( this->frame_time_ms ) * time.speed_current + time.frame_start_time_remainder;
35 int add_int = int( add );
37 time.frame_start_time_remainder = add - double( add_int );
38 time.frame_start_time_ms += add_int;
39 time.speed_current = time.speed_target;
42 this->frame_length_ms -= this->frame_time_ms;
43 this->frame_time_ms = 0;
48 this->frame_clients.insert( client );
53 if( *this->frame_clients_iterator == client )
54 ++this->frame_clients_iterator;
56 this->frame_clients.erase( client );
61 TimeData & time = this->time_data[ time_type.
runtime_value() ];
62 return time.frame_start_time_ms + int( time.speed_current *
double( this->frame_time_ms ) );
67 TimeData & time = this->time_data[ time_type.
runtime_value() ];
68 return int( time.speed_current *
double( this->frame_length_ms - this->frame_time_ms ) );
73 TimeData & time = this->time_data[ time_type.
runtime_value() ];
74 time.speed_target =
speed;
79 TimeData & time = this->time_data[ time_type.
runtime_value() ];
80 return time.speed_target;
86 TimeData & time = this->time_data[ time_type.
runtime_value() ];
87 time.game_update_period_ms = period_ms;
92 TimeData & time = this->time_data[ time_type.
runtime_value() ];
93 return time.game_update_period_ms;
108 this->timeout_queues[ time_type.
runtime_value() ].erase( it );
118 this->fixed[ time_type.
runtime_value() ].clients.insert( client );
125 if( *data.iterator == client )
128 data.clients.erase( client );
133 bool something_was_called =
false;
136 if( this->frame_update_queued )
138 something_was_called =
true;
139 this->frame_update_queued =
false;
142 this->frame_clients_iterator = this->frame_clients.begin();
143 while( this->frame_clients_iterator != this->frame_clients.end() )
146 ++this->frame_clients_iterator;
152 static const constexpr
int FixedStepMs = 16;
154 for(
size_t i = 0; i < this->time_data.size(); i++ )
156 FixedData & data = this->fixed[ i ];
157 int time_ms = this->time_data[ i ].frame_start_time_ms;
159 if( data.last_update == 0 )
161 data.last_update = time_ms;
165 int steps = ( time_ms - data.last_update ) / FixedStepMs;
169 something_was_called =
true;
171 data.last_update += steps * FixedStepMs;
173 data.iterator = data.clients.begin();
174 while( data.iterator != data.clients.end() )
183 std::vector< double > real_frame_times_for_next_update;
184 real_frame_times_for_next_update.resize( this->time_data.size() );
185 for(
size_t i=0; i < this->time_data.size(); i++ )
187 if( this->timeout_queues[ i ].empty() )
189 real_frame_times_for_next_update[ i ] = std::numeric_limits< double >::infinity();
193 TimeData & time_data = this->time_data[ i ];
194 int const & first_item_time = this->timeout_queues[ i ].begin()->first;
196 real_frame_times_for_next_update[ i ] = double( first_item_time - time_data.frame_start_time_ms ) / time_data.speed_current;
202 int nearest_clock = -1;
203 double nearest_clock_value = std::numeric_limits< double >::infinity();
206 double frame_proximity = real_frame_times_for_next_update[ i ];
207 if( frame_proximity < nearest_clock_value )
209 nearest_clock_value = frame_proximity;
215 if( nearest_clock == -1 )
217 this->frame_time_ms = this->frame_length_ms;
222 if(
int( nearest_clock_value ) >= this->frame_length_ms )
224 this->frame_time_ms = this->frame_length_ms;
229 something_was_called =
true;
232 this->frame_time_ms = int( nearest_clock_value );
235 std::multimap< int, UpdateItem > & queue = this->timeout_queues[ nearest_clock ];
236 UpdateItem & update_item = queue.begin()->second;
237 std::function< void() > update_fun;
238 if( update_item.
watch )
239 update_fun = update_item.
fun;
240 queue.erase( queue.begin() );
243 if( this->timeout_queues[ nearest_clock ].empty() )
245 real_frame_times_for_next_update[ nearest_clock ] = std::numeric_limits< double >::infinity();
249 TimeData & time_data = this->time_data[ nearest_clock ];
250 int const & first_item_time = this->timeout_queues[ nearest_clock ].begin()->first;
251 real_frame_times_for_next_update[ nearest_clock ] = double( first_item_time - time_data.frame_start_time_ms ) / time_data.speed_current;
260 if( !this->delayed.empty() )
261 something_was_called =
true;
263 while( !this->delayed.empty() )
266 std::function< void() > fun;
275 return something_was_called;