OpenTTD Source 20250312-master-gcdcc6b491d
texteff.cpp
Go to the documentation of this file.
1/*
2 * This file is part of OpenTTD.
3 * 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.
4 * 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.
5 * 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 <http://www.gnu.org/licenses/>.
6 */
7
10#include "stdafx.h"
11#include "texteff.hpp"
12#include "transparency.h"
13#include "strings_func.h"
14#include "viewport_func.h"
15#include "settings_type.h"
16#include "command_type.h"
17#include "timer/timer.h"
18#include "timer/timer_window.h"
19
20#include "safeguards.h"
21
23struct TextEffect : public ViewportSign {
25 uint8_t duration;
27
29 void Reset()
30 {
31 this->MarkDirty();
32 this->width_normal = 0;
33 this->mode = TE_INVALID;
34 }
35
36 inline bool IsValid() const { return this->mode != TE_INVALID; }
37};
38
39static std::vector<TextEffect> _text_effects;
40
41/* Text Effects */
42TextEffectID AddTextEffect(EncodedString &&msg, int center, int y, uint8_t duration, TextEffectMode mode)
43{
44 if (_game_mode == GM_MENU) return INVALID_TE_ID;
45
46 auto it = std::ranges::find_if(_text_effects, [](const TextEffect &te) { return !te.IsValid(); });
47 if (it == std::end(_text_effects)) {
48 /* _text_effects.size() is the maximum ID + 1 that has been allocated. We should not allocate INVALID_TE_ID or beyond. */
49 if (_text_effects.size() >= INVALID_TE_ID) return INVALID_TE_ID;
50 it = _text_effects.emplace(std::end(_text_effects));
51 }
52
53 TextEffect &te = *it;
54
55 /* Start defining this object */
56 te.msg = std::move(msg);
57 te.duration = duration;
58 te.mode = mode;
59
60 /* Make sure we only dirty the new area */
61 te.width_normal = 0;
62 te.UpdatePosition(center, y, te.msg.GetDecodedString());
63
64 return static_cast<TextEffectID>(it - std::begin(_text_effects));
65}
66
67void UpdateTextEffect(TextEffectID te_id, EncodedString &&msg)
68{
69 /* Update details */
70 TextEffect &te = _text_effects[te_id];
71 if (msg == te.msg) return;
72 te.msg = std::move(msg);
73
75}
76
77void UpdateAllTextEffectVirtCoords()
78{
79 for (auto &te : _text_effects) {
80 if (!te.IsValid()) continue;
81
83 }
84}
85
86void RemoveTextEffect(TextEffectID te_id)
87{
88 _text_effects[te_id].Reset();
89}
90
92IntervalTimer<TimerWindow> move_all_text_effects_interval = {std::chrono::milliseconds(30), [](uint count) {
93 if (_pause_mode.Any() && _game_mode != GM_EDITOR && _settings_game.construction.command_pause_level <= CMDPL_NO_CONSTRUCTION) return;
94
95 for (TextEffect &te : _text_effects) {
96 if (!te.IsValid()) continue;
97 if (te.mode != TE_RISING) continue;
98
99 if (te.duration < count) {
100 te.Reset();
101 continue;
102 }
103
105 te.duration -= count;
106 te.top -= count * ZOOM_BASE;
108 }
109}};
110
111void InitTextEffects()
112{
113 _text_effects.clear();
114 _text_effects.shrink_to_fit();
115}
116
117void DrawTextEffects(DrawPixelInfo *dpi)
118{
119 /* Don't draw the text effects when zoomed out a lot */
120 if (dpi->zoom > ZOOM_LVL_TEXT_EFFECT) return;
121 if (IsTransparencySet(TO_TEXT)) return;
122
123 ViewportStringFlags flags{};
124 if (dpi->zoom >= ZOOM_LVL_TEXT_EFFECT) flags.Set(ViewportStringFlag::Small);
125
126 for (const TextEffect &te : _text_effects) {
127 if (!te.IsValid()) continue;
128
130 std::string *str = ViewportAddString(dpi, &te, flags, INVALID_COLOUR);
131 if (str == nullptr) continue;
132
133 *str = te.msg.GetDecodedString();
134 }
135 }
136}
constexpr Timpl & Set()
Set all bits.
constexpr bool Any(const Timpl &other) const
Test if any of the given values are set.
Container for an encoded string, created by GetEncodedString.
std::string GetDecodedString() const
Decode the encoded string.
Definition strings.cpp:219
An interval timer will fire every interval, and will continue to fire until it is deleted.
Definition timer.h:76
Types related to commands.
@ CMDPL_NO_CONSTRUCTION
No construction actions may be executed.
PauseModes _pause_mode
The current pause mode.
Definition gfx.cpp:50
void MarkDirty(ZoomLevel maxzoom=ZOOM_LVL_MAX) const
Mark the sign dirty in all viewports.
A number of safeguards to prevent using unsafe methods.
GameSettings _settings_game
Game settings of a running game or the scenario editor.
Definition settings.cpp:58
ClientSettings _settings_client
The current settings for this game.
Definition settings.cpp:57
Types related to global configuration settings.
Definition of base types and functions in a cross-platform compatible way.
Functions related to OTTD's strings.
GUISettings gui
settings related to the GUI
uint8_t command_pause_level
level/amount of commands that can't be executed while paused
Data about how and where to blit pixels.
Definition gfx_type.h:156
uint8_t loading_indicators
show loading indicators
ConstructionSettings construction
construction of things in-game
Container for all information about a text effect.
Definition texteff.cpp:23
TextEffectMode mode
Type of text effect.
Definition texteff.cpp:24
uint8_t duration
How long the text effect should stay, in ticks (applies only when mode == TE_RISING)
Definition texteff.cpp:25
void Reset()
Reset the text effect.
Definition texteff.cpp:29
EncodedString msg
Encoded message for text effect.
Definition texteff.cpp:26
Location information about a sign as seen on the viewport.
int32_t center
The center position of the sign.
uint16_t width_normal
The width when not zoomed out (normal font)
void UpdatePosition(int center, int top, std::string_view str, std::string_view str_small={})
Update the position of the viewport sign.
int32_t top
The top of the sign.
IntervalTimer< TimerWindow > move_all_text_effects_interval
Slowly move text effects upwards.
Definition texteff.cpp:92
static std::vector< TextEffect > _text_effects
Text effects are stored there.
Definition texteff.cpp:39
Functions related to text effects.
TextEffectMode
Text effect modes.
Definition texteff.hpp:20
@ TE_RISING
Make the text effect slowly go upwards.
Definition texteff.hpp:22
@ TE_INVALID
Text effect is invalid.
Definition texteff.hpp:21
Definition of Interval and OneShot timers.
Definition of the Window system.
Functions related to transparency.
bool IsTransparencySet(TransparencyOption to)
Check if the transparency option bit is set and if we aren't in the game menu (there's never transpar...
@ TO_TEXT
loading and cost/income text
std::string * ViewportAddString(const DrawPixelInfo *dpi, const ViewportSign *sign, ViewportStringFlags flags, Colours colour)
Add a string to draw in the current viewport.
Functions related to (drawing on) viewports.
@ Small
Draw using the small font.
@ ZOOM_LVL_TEXT_EFFECT
All zoom levels above this will not show text effects.
Definition zoom_type.h:39