-
-
Notifications
You must be signed in to change notification settings - Fork 517
/
button.h
199 lines (167 loc) · 7.1 KB
/
button.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
/*
This file is part of Warzone 2100.
Copyright (C) 1999-2004 Eidos Interactive
Copyright (C) 2005-2020 Warzone 2100 Project
Warzone 2100 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; either version 2 of the License, or
(at your option) any later version.
Warzone 2100 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 Warzone 2100; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
/** @file
* Definitions for edit box functions.
*/
#ifndef __INCLUDED_LIB_WIDGET_BUTTON_H__
#define __INCLUDED_LIB_WIDGET_BUTTON_H__
#include "lib/ivis_opengl/ivisdef.h"
#include "widget.h"
#include "widgbase.h"
#include <map>
#include <functional>
#include <string>
class W_BUTTON : public WIDGET
{
public:
struct Images
{
Images() {}
Images(AtlasImage normal, AtlasImage down, AtlasImage highlighted, AtlasImage disabled = AtlasImage()) : normal(normal), down(down), highlighted(highlighted), disabled(disabled) {}
AtlasImage normal; ///< The image for the button.
AtlasImage down; ///< The image for the button, when down. Is overlaid over image.
AtlasImage highlighted; ///< The image for the button, when highlighted. Is overlaid over image.
AtlasImage disabled; ///< The image for the button, when disabled. Is overlaid over image.
};
public:
W_BUTTON(W_BUTINIT const *init);
W_BUTTON();
void clicked(W_CONTEXT *psContext, WIDGET_KEY key) override;
virtual bool clickHeld(W_CONTEXT *psContext, WIDGET_KEY key);
void released(W_CONTEXT *psContext, WIDGET_KEY key) override;
void highlight(W_CONTEXT *psContext) override;
void highlightLost() override;
void run(W_CONTEXT *psContext) override;
void display(int xOffset, int yOffset) override;
void displayRecursive(WidgetGraphicsContext const &context) override; // for handling progress border overlay
unsigned getState() override;
void setState(unsigned state) override;
void setFlash(bool enable) override;
WzString getString() const override;
void setString(WzString string) override;
void setTip(std::string string) override;
void setHelp(optional<WidgetHelp> help) override;
void unlock();
void setImages(Images const &images);
void setImages(AtlasImage image, AtlasImage imageDown, AtlasImage imageHighlight, AtlasImage imageDisabled = AtlasImage());
using WIDGET::setString;
using WIDGET::setTip;
std::string getTip() override
{
return pTip;
}
WidgetHelp const * getHelp() const override
{
if (!help.has_value()) { return nullptr; }
return &(help.value());
}
/* The optional "onClick" callback function */
typedef std::function<void (W_BUTTON& button)> W_BUTTON_ONCLICK_FUNC;
void addOnClickHandler(const W_BUTTON_ONCLICK_FUNC& onClickFunc);
struct ProgressBorder
{
public:
struct BorderInset
{
BorderInset() { }
BorderInset(int left, int top, int right, int bottom)
: left(left), top(top), right(right), bottom(bottom)
{ }
int left = 0;
int top = 0;
int right = 0;
int bottom = 0;
};
private:
ProgressBorder(UDWORD interval, optional<float> factor, bool repeated, BorderInset inset = BorderInset()): m_inset(inset), m_interval(interval), m_factor(factor), m_repeated(repeated) { resetStartingTime(); }
public:
// Create an indeterminate ProgressBorder
static ProgressBorder indeterminate(BorderInset inset = BorderInset()) { return ProgressBorder(0, nullopt, true, inset); }
// Create a timed ProgressBorder which proceeds from 0 to 100% over the interval
static ProgressBorder timed(UDWORD interval, bool repeated = false, BorderInset inset = BorderInset()) { return ProgressBorder(interval, nullopt, repeated, inset); }
// Create a fixed factor ProgressBorder, where `factor` is expected to be a float from 0.0 to 1.0 (which corresponds to the percentage progress)
static ProgressBorder fixedFactor(float factor, BorderInset inset = BorderInset()) { return ProgressBorder(0, factor, false, inset); }
public:
void setInset(const BorderInset& newInset) { m_inset = newInset; }
void resetStartingTime();
const BorderInset& inset() const { return m_inset; }
UDWORD interval() const { return m_interval; }
UDWORD startingTime() const { return m_startingTime; }
optional<float> factor() const { return m_factor; }
bool repeated() const { return m_repeated; }
bool isIndeterminate() const { return !m_factor.has_value() && m_interval == 0; }
private:
BorderInset m_inset;
UDWORD m_interval = 0;
UDWORD m_startingTime = 0;
optional<float> m_factor = 0.0f;
bool m_repeated = false;
};
// Set the current ProgressBorder on the button, optionally specifying a color
// To disable a ProgressBorder, use `setProgressBorder(nullopt)`
void setProgressBorder(optional<ProgressBorder> progressBorder, optional<PIELIGHT> borderColour = nullopt);
// May be called from within W_BUTTON_ONCLICK_FUNC (onclick handler) to retrieve the button pressed
WIDGET_KEY getOnClickButtonPressed() const;
public:
bool isHighlighted() const;
private:
void drawProgressBorder(int xOffset, int yOffset);
public:
unsigned state; // The current button state
WzString pText; // The text for the button
Images images; ///< The images for the button.
std::string pTip; // The tool tip for the button
SWORD HilightAudioID; // Audio ID for form clicked sound
SWORD ClickedAudioID; // Audio ID for form hilighted sound
WIDGET_AUDIOCALLBACK AudioCallback; // Pointer to audio callback function
iV_fonts FontID;
UDWORD minClickInterval = 0;
private:
UDWORD lastClickTime = 0;
std::vector<W_BUTTON_ONCLICK_FUNC> onClickHandlers;
optional<ProgressBorder> progressBorder;
PIELIGHT progressBorderColour;
WIDGET_KEY lastClickButton = WKEY_NONE;
optional<WidgetHelp> help;
optional<std::chrono::steady_clock::time_point> clickDownStart; // the start time of click down on this button
optional<WIDGET_KEY> clickDownKey;
};
class MultipleChoiceButton : public W_BUTTON
{
public:
MultipleChoiceButton() : W_BUTTON(), choice(0) {}
void setChoice(unsigned newChoice);
void setTip(unsigned stateValue, std::string const &string);
void setTip(unsigned stateValue, char const *stringUtf8);
void setImages(unsigned stateValue, Images const &stateImages);
unsigned getChoice()
{
return choice;
}
using WIDGET::setTip;
private:
unsigned choice;
std::map<int, std::string> tips;
std::map<int, Images> imageSets;
};
std::shared_ptr<W_BUTTON> makeFormTransparentCornerButton(const char* text, int buttonPadding /* = TAB_BUTTONS_PADDING */, PIELIGHT buttonBackgroundFill /* = WZCOL_DEBUG_FILL_COLOR */);
struct PopoverMenuButtonDisplayCache
{
WzText text;
};
void PopoverMenuButtonDisplayFunc(WIDGET *psWidget, UDWORD xOffset, UDWORD yOffset);
#endif // __INCLUDED_LIB_WIDGET_BUTTON_H__