From 806e7d25dddcc8b0e9c3f372ed956c63c6508381 Mon Sep 17 00:00:00 2001 From: Peter Nelson Date: Sun, 20 May 2018 09:58:36 +0100 Subject: Change: Use GUITimer class instead of bare int/uints. --- src/guitimer_func.h | 65 +++++++++++++++++++++++++++++++++++++++++++++++++++ src/main_gui.cpp | 13 ++++++----- src/misc_gui.cpp | 6 +++-- src/newgrf_gui.cpp | 8 +++---- src/news_gui.cpp | 7 ++++-- src/smallmap_gui.cpp | 9 +++---- src/smallmap_gui.h | 3 ++- src/statusbar_gui.cpp | 21 +++++++++-------- src/texteff.cpp | 6 ++--- src/toolbar_gui.cpp | 17 +++++++------- src/window.cpp | 29 ++++++++++++----------- src/window_func.h | 32 ------------------------- 12 files changed, 131 insertions(+), 85 deletions(-) create mode 100644 src/guitimer_func.h (limited to 'src') diff --git a/src/guitimer_func.h b/src/guitimer_func.h new file mode 100644 index 000000000..44ce04228 --- /dev/null +++ b/src/guitimer_func.h @@ -0,0 +1,65 @@ +/* $Id$ */ + +/* + * This file is part of OpenTTD. + * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2. + * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see . + */ + +/** @file guitimer_func.h GUI Timers. */ + +#ifndef GUITIMER_FUNC_H +#define GUITIMER_FUNC_H + +class GUITimer +{ +protected: + uint timer; + uint interval; + +public: + GUITimer() : timer(0), interval(0) { } + explicit GUITimer(uint interval) : timer(0), interval(interval) { } + + inline bool HasElapsed() const + { + return this->interval == 0; + } + + inline void SetInterval(uint interval) + { + this->timer = 0; + this->interval = interval; + } + + /** + * Count how many times the interval has elapsed. + * Use to ensure a specific amount of events happen within a timeframe, e.g. for animation. + * @param delta Time since last test. + * @return Number of times the interval has elapsed. + */ + inline uint CountElapsed(uint delta) + { + if (this->interval == 0) return 0; + uint count = delta / this->interval; + if (this->timer + (delta % this->interval) >= this->interval) count++; + this->timer = (this->timer + delta) % this->interval; + return count; + } + + /** + * Test if a timer has elapsed. + * Use to ensure an event happens only once within a timeframe, e.g. for window updates. + * @param delta Time since last test. + * @return True iff the timer has elapsed. + */ + inline bool Elapsed(uint delta) + { + if (this->CountElapsed(delta) == 0) return false; + this->SetInterval(0); + return true; + } +}; + +#endif /* GUITIMER_FUNC_H */ diff --git a/src/main_gui.cpp b/src/main_gui.cpp index 12ee574bb..2eb24c8dc 100644 --- a/src/main_gui.cpp +++ b/src/main_gui.cpp @@ -32,6 +32,7 @@ #include "linkgraph/linkgraph_gui.h" #include "tilehighlight_func.h" #include "hotkeys.h" +#include "guitimer_func.h" #include "saveload/saveload.h" @@ -235,7 +236,7 @@ enum { struct MainWindow : Window { - int refresh; + GUITimer refresh; /* Refresh times in milliseconds */ static const uint LINKGRAPH_REFRESH_PERIOD = 7650; @@ -251,14 +252,14 @@ struct MainWindow : Window nvp->InitializeViewport(this, TileXY(32, 32), ZOOM_LVL_VIEWPORT); this->viewport->overlay = new LinkGraphOverlay(this, WID_M_VIEWPORT, 0, 0, 3); - this->refresh = LINKGRAPH_DELAY; + this->refresh.SetInterval(LINKGRAPH_DELAY); } virtual void OnRealtimeTick(uint delta_ms) { - if (!TimerElapsed(this->refresh, delta_ms)) return; + if (!this->refresh.Elapsed(delta_ms)) return; - this->refresh = LINKGRAPH_REFRESH_PERIOD; + this->refresh.SetInterval(LINKGRAPH_REFRESH_PERIOD); if (this->viewport->overlay->GetCargoMask() == 0 || this->viewport->overlay->GetCompanyMask() == 0) { @@ -435,7 +436,7 @@ struct MainWindow : Window this->viewport->scrollpos_y += ScaleByZoom(delta.y, this->viewport->zoom); this->viewport->dest_scrollpos_x = this->viewport->scrollpos_x; this->viewport->dest_scrollpos_y = this->viewport->scrollpos_y; - this->refresh = LINKGRAPH_DELAY; + this->refresh.SetInterval(LINKGRAPH_DELAY); } virtual void OnMouseWheel(int wheel) @@ -450,7 +451,7 @@ struct MainWindow : Window if (this->viewport != NULL) { NWidgetViewport *nvp = this->GetWidget(WID_M_VIEWPORT); nvp->UpdateViewportCoordinates(this); - this->refresh = LINKGRAPH_DELAY; + this->refresh.SetInterval(LINKGRAPH_DELAY); } } diff --git a/src/misc_gui.cpp b/src/misc_gui.cpp index 31faae2d4..149ebe717 100644 --- a/src/misc_gui.cpp +++ b/src/misc_gui.cpp @@ -26,6 +26,7 @@ #include "core/geometry_func.hpp" #include "newgrf_debug.h" #include "zoom_func.h" +#include "guitimer_func.h" #include "widgets/misc_widget.h" @@ -458,13 +459,14 @@ struct AboutWindow : public Window { static const int num_visible_lines = 19; ///< The number of lines visible simultaneously static const uint TIMER_INTERVAL = 150; ///< Scrolling interval in ms - uint timer; + GUITimer timer; AboutWindow() : Window(&_about_desc) { this->InitNested(WN_GAME_OPTIONS_ABOUT); this->text_position = this->GetWidget(WID_A_SCROLLING_TEXT)->pos_y + this->GetWidget(WID_A_SCROLLING_TEXT)->current_y; + this->timer.SetInterval(TIMER_INTERVAL); } virtual void SetStringParameters(int widget) const @@ -505,7 +507,7 @@ struct AboutWindow : public Window { virtual void OnRealtimeTick(uint delta_ms) { - uint count = CountIntervalElapsed(this->timer, delta_ms, TIMER_INTERVAL); + uint count = this->timer.CountElapsed(delta_ms); if (count > 0) { this->text_position -= count; /* If the last text has scrolled start a new from the start */ diff --git a/src/newgrf_gui.cpp b/src/newgrf_gui.cpp index 0b0512544..6a4530483 100644 --- a/src/newgrf_gui.cpp +++ b/src/newgrf_gui.cpp @@ -30,6 +30,7 @@ #include "textfile_gui.h" #include "tilehighlight_func.h" #include "fios.h" +#include "guitimer_func.h" #include "widgets/newgrf_widget.h" #include "widgets/misc_widget.h" @@ -150,7 +151,7 @@ struct NewGRFParametersWindow : public Window { bool clicked_increase; ///< True if the increase button was clicked, false for the decrease button. bool clicked_dropdown; ///< Whether the dropdown is open. bool closing_dropdown; ///< True, if the dropdown list is currently closing. - int timeout; ///< How long before we unpress the last-pressed button? + GUITimer timeout; ///< How long before we unpress the last-pressed button? uint clicked_row; ///< The selected parameter int line_height; ///< Height of a row in the matrix widget. Scrollbar *vscroll; @@ -162,7 +163,6 @@ struct NewGRFParametersWindow : public Window { clicked_button(UINT_MAX), clicked_dropdown(false), closing_dropdown(false), - timeout(0), clicked_row(UINT_MAX), editable(editable) { @@ -403,7 +403,7 @@ struct NewGRFParametersWindow : public Window { par_info->SetValue(this->grf_config, val); this->clicked_button = num; - this->timeout = 150; + this->timeout.SetInterval(150); } } else if (par_info->type == PTYPE_UINT_ENUM && !par_info->complete_labels && click_count >= 2) { /* Display a query box so users can enter a custom value. */ @@ -485,7 +485,7 @@ struct NewGRFParametersWindow : public Window { virtual void OnRealtimeTick(uint delta_ms) { - if (TimerElapsed(this->timeout, delta_ms)) { + if (timeout.Elapsed(delta_ms)) { this->clicked_button = UINT_MAX; this->SetDirty(); } diff --git a/src/news_gui.cpp b/src/news_gui.cpp index 183b27b90..b79418c89 100644 --- a/src/news_gui.cpp +++ b/src/news_gui.cpp @@ -33,6 +33,7 @@ #include "command_func.h" #include "company_base.h" #include "settings_internal.h" +#include "guitimer_func.h" #include "widgets/news_widget.h" @@ -262,7 +263,7 @@ struct NewsWindow : Window { const NewsItem *ni; ///< News item to display. static int duration; ///< Remaining time for showing the current news message (may only be access while a news item is displayed). - uint timer; + GUITimer timer; NewsWindow(WindowDesc *desc, const NewsItem *ni) : Window(desc), ni(ni) { @@ -273,6 +274,8 @@ struct NewsWindow : Window { this->flags |= WF_DISABLE_VP_SCROLL; + this->timer.SetInterval(15); + this->CreateNestedTree(); /* For company news with a face we have a separate headline in param[0] */ @@ -489,7 +492,7 @@ struct NewsWindow : Window { virtual void OnRealtimeTick(uint delta_ms) { - int count = CountIntervalElapsed(this->timer, delta_ms, 15); + int count = this->timer.CountElapsed(delta_ms); if (count > 0) { /* Scroll up newsmessages from the bottom */ int newtop = max(this->top - 2 * count, _screen.height - this->height - this->status_height - this->chat_height); diff --git a/src/smallmap_gui.cpp b/src/smallmap_gui.cpp index 447d25e4a..df9fd2df2 100644 --- a/src/smallmap_gui.cpp +++ b/src/smallmap_gui.cpp @@ -23,6 +23,7 @@ #include "sound_func.h" #include "window_func.h" #include "company_base.h" +#include "guitimer_func.h" #include "smallmap_gui.h" @@ -1055,7 +1056,7 @@ void SmallMapWindow::SetupWidgetData() this->GetWidget(WID_SM_SELECT_BUTTONS)->SetDisplayedPlane(plane); } -SmallMapWindow::SmallMapWindow(WindowDesc *desc, int window_number) : Window(desc), refresh(FORCE_REFRESH_PERIOD) +SmallMapWindow::SmallMapWindow(WindowDesc *desc, int window_number) : Window(desc), refresh(GUITimer(FORCE_REFRESH_PERIOD)) { _smallmap_industry_highlight = INVALID_INDUSTRYTYPE; this->overlay = new LinkGraphOverlay(this, WID_SM_MAP, 0, this->GetOverlayCompanyMask(), 1); @@ -1390,7 +1391,7 @@ int SmallMapWindow::GetPositionOnLegend(Point pt) } if (new_highlight != _smallmap_industry_highlight) { _smallmap_industry_highlight = new_highlight; - this->refresh = _smallmap_industry_highlight != INVALID_INDUSTRYTYPE ? BLINK_PERIOD : FORCE_REFRESH_PERIOD; + this->refresh.SetInterval(_smallmap_industry_highlight != INVALID_INDUSTRYTYPE ? BLINK_PERIOD : FORCE_REFRESH_PERIOD); _smallmap_industry_highlight_state = true; this->SetDirty(); } @@ -1573,7 +1574,7 @@ int SmallMapWindow::GetPositionOnLegend(Point pt) /* virtual */ void SmallMapWindow::OnRealtimeTick(uint delta_ms) { /* Update the window every now and then */ - if (!TimerElapsed(this->refresh, delta_ms)) return; + if (!this->refresh.Elapsed(delta_ms)) return; if (this->map_type == SMT_LINKSTATS) { uint32 company_mask = this->GetOverlayCompanyMask(); @@ -1585,7 +1586,7 @@ int SmallMapWindow::GetPositionOnLegend(Point pt) } _smallmap_industry_highlight_state = !_smallmap_industry_highlight_state; - this->refresh = _smallmap_industry_highlight != INVALID_INDUSTRYTYPE ? BLINK_PERIOD : FORCE_REFRESH_PERIOD; + this->refresh.SetInterval(_smallmap_industry_highlight != INVALID_INDUSTRYTYPE ? BLINK_PERIOD : FORCE_REFRESH_PERIOD); this->SetDirty(); } diff --git a/src/smallmap_gui.h b/src/smallmap_gui.h index 60b39b7a3..486f2a652 100644 --- a/src/smallmap_gui.h +++ b/src/smallmap_gui.h @@ -19,6 +19,7 @@ #include "blitter/factory.hpp" #include "linkgraph/linkgraph_gui.h" #include "widgets/smallmap_widget.h" +#include "guitimer_func.h" /* set up the cargos to be displayed in the smallmap's route legend */ void BuildLinkStatsLegend(); @@ -79,7 +80,7 @@ protected: int32 subscroll; ///< Number of pixels (0..3) between the right end of the base tile and the pixel at the top-left corner of the smallmap display. int zoom; ///< Zoom level. Bigger number means more zoom-out (further away). - int refresh; ///< Refresh timer, in millseconds. + GUITimer refresh; ///< Refresh timer. LinkGraphOverlay *overlay; static void BreakIndustryChainLink(); diff --git a/src/statusbar_gui.cpp b/src/statusbar_gui.cpp index e45697130..88ba495f3 100644 --- a/src/statusbar_gui.cpp +++ b/src/statusbar_gui.cpp @@ -26,6 +26,7 @@ #include "statusbar_gui.h" #include "toolbar_gui.h" #include "core/geometry_func.hpp" +#include "guitimer_func.h" #include "widgets/statusbar_widget.h" @@ -79,8 +80,8 @@ static bool DrawScrollingStatusText(const NewsItem *ni, int scroll_pos, int left struct StatusBarWindow : Window { bool saving; int ticker_scroll; - uint ticker_timer; - int reminder_timeout; + GUITimer ticker_timer; + GUITimer reminder_timeout; static const int TICKER_STOP = 1640; ///< scrolling is finished when counter reaches this value static const int REMINDER_START = 1350; ///< time in ms for reminder notification (red dot on the right) to stay @@ -89,8 +90,9 @@ struct StatusBarWindow : Window { StatusBarWindow(WindowDesc *desc) : Window(desc) { - this->ticker_scroll = TICKER_STOP; - this->reminder_timeout = REMINDER_STOP; + this->ticker_scroll = TICKER_STOP; + this->ticker_timer.SetInterval(15); + this->reminder_timeout.SetInterval(REMINDER_STOP); this->InitNested(); CLRBITS(this->flags, WF_WHITE_BORDER); @@ -180,7 +182,7 @@ struct StatusBarWindow : Window { } } - if (this->reminder_timeout > 0) { + if (!this->reminder_timeout.HasElapsed()) { Dimension icon_size = GetSpriteSize(SPR_UNREAD_NEWS); DrawSprite(SPR_UNREAD_NEWS, PAL_NONE, r.right - WD_FRAMERECT_RIGHT - icon_size.width, r.top + WD_FRAMERECT_TOP + (int)(FONT_HEIGHT_NORMAL - icon_size.height) / 2); } @@ -201,11 +203,10 @@ struct StatusBarWindow : Window { case SBI_SAVELOAD_START: this->saving = true; break; case SBI_SAVELOAD_FINISH: this->saving = false; break; case SBI_SHOW_TICKER: this->ticker_scroll = 0; break; - case SBI_SHOW_REMINDER: this->reminder_timeout = REMINDER_START; break; + case SBI_SHOW_REMINDER: this->reminder_timeout.SetInterval(REMINDER_START); break; case SBI_NEWS_DELETED: this->ticker_scroll = TICKER_STOP; // reset ticker ... - this->ticker_timer = 0; - this->reminder_timeout = REMINDER_STOP; // ... and reminder + this->reminder_timeout.SetInterval(REMINDER_STOP); // ... and reminder break; } } @@ -224,7 +225,7 @@ struct StatusBarWindow : Window { if (_pause_mode != PM_UNPAUSED) return; if (this->ticker_scroll < TICKER_STOP) { // Scrolling text - uint count = CountIntervalElapsed(this->ticker_timer, delta_ms, 15); + uint count = this->ticker_timer.CountElapsed(delta_ms); if (count > 0) { this->ticker_scroll += count; this->SetWidgetDirty(WID_S_MIDDLE); @@ -232,7 +233,7 @@ struct StatusBarWindow : Window { } // Red blot to show there are new unread newsmessages - if (TimerElapsed(this->reminder_timeout, delta_ms)) { + if (this->reminder_timeout.Elapsed(delta_ms)) { this->SetWidgetDirty(WID_S_MIDDLE); } } diff --git a/src/texteff.cpp b/src/texteff.cpp index 0f79f51c1..ee5ce592b 100644 --- a/src/texteff.cpp +++ b/src/texteff.cpp @@ -16,7 +16,7 @@ #include "core/smallvec_type.hpp" #include "viewport_func.h" #include "settings_type.h" -#include "window_func.h" +#include "guitimer_func.h" #include "safeguards.h" @@ -85,8 +85,8 @@ void RemoveTextEffect(TextEffectID te_id) void MoveAllTextEffects(uint delta_ms) { - static uint texteffecttimer = 0; - uint count = CountIntervalElapsed(texteffecttimer, delta_ms, MILLISECONDS_PER_TICK); + static GUITimer texteffecttimer = GUITimer(MILLISECONDS_PER_TICK); + uint count = texteffecttimer.CountElapsed(delta_ms); if (count == 0) return; const TextEffect *end = _text_effects.End(); diff --git a/src/toolbar_gui.cpp b/src/toolbar_gui.cpp index 4f0f14011..cd0f518df 100644 --- a/src/toolbar_gui.cpp +++ b/src/toolbar_gui.cpp @@ -48,6 +48,7 @@ #include "story_base.h" #include "toolbar_gui.h" #include "framerate_type.h" +#include "guitimer_func.h" #include "widgets/toolbar_widget.h" @@ -1978,7 +1979,7 @@ enum MainToolbarHotkeys { /** Main toolbar. */ struct MainToolbarWindow : Window { - int timer; + GUITimer timer; MainToolbarWindow(WindowDesc *desc) : Window(desc) { @@ -1991,7 +1992,7 @@ struct MainToolbarWindow : Window { PositionMainToolbar(this); DoZoomInOutWindow(ZOOM_NONE, this); - this->timer = MILLISECONDS_PER_TICK; + this->timer.SetInterval(MILLISECONDS_PER_TICK); } virtual void FindWindowPlacementAndResize(int def_width, int def_height) @@ -2098,8 +2099,8 @@ struct MainToolbarWindow : Window { virtual void OnRealtimeTick(uint delta_ms) { - if (!TimerElapsed(this->timer, delta_ms)) return; - this->timer = MILLISECONDS_PER_TICK; + if (!this->timer.Elapsed(delta_ms)) return; + this->timer.SetInterval(MILLISECONDS_PER_TICK); if (this->IsWidgetLowered(WID_TN_PAUSE) != !!_pause_mode) { this->ToggleWidgetLoweredState(WID_TN_PAUSE); @@ -2317,7 +2318,7 @@ enum MainToolbarEditorHotkeys { }; struct ScenarioEditorToolbarWindow : Window { - int timer; + GUITimer timer; ScenarioEditorToolbarWindow(WindowDesc *desc) : Window(desc) { @@ -2328,7 +2329,7 @@ struct ScenarioEditorToolbarWindow : Window { PositionMainToolbar(this); DoZoomInOutWindow(ZOOM_NONE, this); - this->timer = MILLISECONDS_PER_TICK; + this->timer.SetInterval(MILLISECONDS_PER_TICK); } virtual void FindWindowPlacementAndResize(int def_width, int def_height) @@ -2458,8 +2459,8 @@ struct ScenarioEditorToolbarWindow : Window { virtual void OnRealtimeTick(uint delta_ms) { - if (!TimerElapsed(this->timer, delta_ms)) return; - this->timer = MILLISECONDS_PER_TICK; + if (!this->timer.Elapsed(delta_ms)) return; + this->timer.SetInterval(MILLISECONDS_PER_TICK); if (this->IsWidgetLowered(WID_TE_PAUSE) != !!_pause_mode) { this->ToggleWidgetLoweredState(WID_TE_PAUSE); diff --git a/src/window.cpp b/src/window.cpp index efa206d56..bbde131a4 100644 --- a/src/window.cpp +++ b/src/window.cpp @@ -38,6 +38,7 @@ #include "video/video_driver.hpp" #include "framerate_type.h" #include "network/network_func.h" +#include "guitimer_func.h" #include "safeguards.h" @@ -3099,17 +3100,17 @@ void UpdateWindows() CallWindowRealtimeTickEvent(delta_ms); - static int network_message_timer = 1; - if (TimerElapsed(network_message_timer, delta_ms)) { - network_message_timer = 1000; + static GUITimer network_message_timer = GUITimer(1); + if (network_message_timer.Elapsed(delta_ms)) { + network_message_timer.SetInterval(1000); NetworkChatMessageLoop(); } Window *w; - static int window_timer = 1; - if (TimerElapsed(window_timer, delta_ms)) { - window_timer = MILLISECONDS_PER_TICK; + static GUITimer window_timer = GUITimer(1); + if (window_timer.Elapsed(delta_ms)) { + if (_network_dedicated) window_timer.SetInterval(MILLISECONDS_PER_TICK); extern int _caret_timer; _caret_timer += 3; @@ -3120,9 +3121,9 @@ void UpdateWindows() DecreaseWindowCounters(); } - static int highlight_timer = 1; - if (TimerElapsed(highlight_timer, delta_ms)) { - highlight_timer = 450; + static GUITimer highlight_timer = GUITimer(1); + if (highlight_timer.Elapsed(delta_ms)) { + highlight_timer.SetInterval(450); _window_highlight_colour = !_window_highlight_colour; } @@ -3137,16 +3138,18 @@ void UpdateWindows() * But still empty the invalidation queues above. */ if (_network_dedicated) return; - static int hundredth_timer = 1; - if (TimerElapsed(hundredth_timer, delta_ms)) { - hundredth_timer = 3000; // Historical reason: 100 * MILLISECONDS_PER_TICK + static GUITimer hundredth_timer = GUITimer(1); + if (hundredth_timer.Elapsed(delta_ms)) { + hundredth_timer.SetInterval(3000); // Historical reason: 100 * MILLISECONDS_PER_TICK FOR_ALL_WINDOWS_FROM_FRONT(w) { w->OnHundredthTick(); } } - if (window_timer == MILLISECONDS_PER_TICK) { // window_timer has elapsed this call + if (window_timer.HasElapsed()) { + window_timer.SetInterval(MILLISECONDS_PER_TICK); + FOR_ALL_WINDOWS_FROM_FRONT(w) { if ((w->flags & WF_WHITE_BORDER) && --w->white_border_timer == 0) { CLRBITS(w->flags, WF_WHITE_BORDER); diff --git a/src/window_func.h b/src/window_func.h index f2ae638fe..453b88978 100644 --- a/src/window_func.h +++ b/src/window_func.h @@ -56,36 +56,4 @@ void DeleteWindowByClass(WindowClass cls); bool EditBoxInGlobalFocus(); Point GetCaretPosition(); -/** - * Count how many times the interval has elapsed, and update the timer. - * Use to ensure a specific amount of events happen within a timeframe, e.g. for animation. - * The timer value does not need to be initialised. - * @param timer Timer to test. Value will be increased. - * @param delta Time since last test. - * @param interval Timing interval. - * @return Number of times the interval has elapsed. - */ -static inline uint CountIntervalElapsed(uint &timer, uint delta, uint interval) -{ - uint count = delta / interval; - if (timer + (delta % interval) >= interval) count++; - timer = (timer + delta) % interval; - return count; -} - -/** - * Test if a timer has elapsed, and update the timer. - * Use to ensure an event happens only once within a timeframe, e.g. for window updates. - * The timer value must be initialised in order for the timer to elapsed. - * @param timer Timer to test. Value will be decreased. - * @param delta Time since last test. - * @return True iff the timer has elapsed. - */ -static inline bool TimerElapsed(int &timer, uint delta) -{ - if (timer <= 0) return false; - timer -= delta; - return timer <= 0; -} - #endif /* WINDOW_FUNC_H */ -- cgit v1.2.3-70-g09d2