FINAL CUT
fmessagebox.h
1 /***********************************************************************
2 * fmessagebox.h - Widget FMessageBox (a text message window) *
3 * *
4 * This file is part of the FINAL CUT widget toolkit *
5 * *
6 * Copyright 2014-2026 Markus Gans *
7 * *
8 * FINAL CUT is free software; you can redistribute it and/or modify *
9 * it under the terms of the GNU Lesser General Public License as *
10 * published by the Free Software Foundation; either version 3 of *
11 * the License, or (at your option) any later version. *
12 * *
13 * FINAL CUT is distributed in the hope that it will be useful, but *
14 * WITHOUT ANY WARRANTY; without even the implied warranty of *
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
16 * GNU Lesser General Public License for more details. *
17 * *
18 * You should have received a copy of the GNU Lesser General Public *
19 * License along with this program. If not, see *
20 * <http://www.gnu.org/licenses/>. *
21 ***********************************************************************/
22 
23 /* Inheritance diagram
24  * ═══════════════════
25  *
26  * ▕▔▔▔▔▔▔▔▔▔▏ ▕▔▔▔▔▔▔▔▔▔▏
27  * ▕ FVTerm ▏ ▕ FObject ▏
28  * ▕▁▁▁▁▁▁▁▁▁▏ ▕▁▁▁▁▁▁▁▁▁▏
29  * ▲ ▲
30  * │ │
31  * └─────┬─────┘
32  * │
33  * ▕▔▔▔▔▔▔▔▔▔▏
34  * ▕ FWidget ▏
35  * ▕▁▁▁▁▁▁▁▁▁▏
36  * ▲
37  * │
38  * ▕▔▔▔▔▔▔▔▔▔▏
39  * ▕ FWindow ▏
40  * ▕▁▁▁▁▁▁▁▁▁▏
41  * ▲
42  * │
43  * ▕▔▔▔▔▔▔▔▔▔▏
44  * ▕ FDialog ▏
45  * ▕▁▁▁▁▁▁▁▁▁▏
46  * ▲
47  * │
48  * ▕▔▔▔▔▔▔▔▔▔▔▔▔▔▏
49  * ▕ FMessageBox ▏
50  * ▕▁▁▁▁▁▁▁▁▁▁▁▁▁▏
51  */
52 
53 #ifndef FMESSAGEBOX_H
54 #define FMESSAGEBOX_H
55 
56 #if !defined (USE_FINAL_H) && !defined (COMPILE_FINAL_CUT)
57  #error "Only <final/final.h> can be included directly."
58 #endif
59 
60 #include <array>
61 #include <cstring>
62 #include <memory>
63 #include <utility>
64 
65 #include "final/dialog/fdialog.h"
66 #include "final/fwidgetcolors.h"
67 #include "final/widget/fbutton.h"
68 
69 namespace finalcut
70 {
71 
72 // class forward declaration
73 class FButton;
74 
75 //----------------------------------------------------------------------
76 // class FMessageBox
77 //----------------------------------------------------------------------
78 
79 class FMessageBox : public FDialog
80 {
81  public:
82  // Enumeration
83  enum class ButtonType : uInt8
84  {
85  Reject = 0,
86  Ok = 1,
87  Cancel = 2,
88  Yes = 3,
89  No = 4,
90  Abort = 5,
91  Retry = 6,
92  Ignore = 7
93  };
94 
95  // Constructors
96  explicit FMessageBox (FWidget* = nullptr);
97 
98  FMessageBox ( const FString&, FString&&
99  , ButtonType, ButtonType, ButtonType
100  , FWidget* = nullptr );
101 
102  // Destructor
103  ~FMessageBox() noexcept override;
104 
105  // Accessor
106  auto getClassName() const -> FString override;
107  auto getTitleBarText() const -> FString;
108  auto getHeadline() const -> FString;
109  auto getText() const -> FString override;
110 
111  // Mutator
112  void setTitleBarText (const FString&);
113  void setHeadline (const FString&);
114  void setCenterText (bool = true);
115  void unsetCenterText();
116  void setText (const FString&) override;
117 
118  // Methods
119  auto exec() -> ButtonType;
120  template <typename messageType>
121  static auto info ( FWidget*
122  , const FString&
123  , const messageType&
124  , ButtonType = ButtonType::Ok
125  , ButtonType = ButtonType::Reject
126  , ButtonType = ButtonType::Reject ) -> ButtonType;
127 
128  template <typename messageType>
129  static auto error ( FWidget*
130  , const messageType&
131  , ButtonType = ButtonType::Ok
132  , ButtonType = ButtonType::Reject
133  , ButtonType = ButtonType::Reject ) -> ButtonType;
134  protected:
135  // Method
136  void initLayout() override;
137  void adjustSize() override;
138  void done (ButtonType);
139 
140  // Callback method
141  void cb_processClick (ButtonType);
142 
143  private:
144  // Constants
145  static constexpr std::size_t GAP = 4;
146  static constexpr std::size_t MAX_BUTTONS = 3;
147  static constexpr std::size_t PADDING = 5;
148 
149  // Using-declaration
150  using FButtons = std::array<std::unique_ptr<FButton>, MAX_BUTTONS>;
151  using FButtonsDigit = std::array<ButtonType, MAX_BUTTONS>;
152 
153  // Methods
154  void init();
155  void allocation();
156  void initCallbacks();
157  void calculateDimensions();
158  void draw() override;
159  auto getButtonLengthArray() const -> std::array<std::size_t, MAX_BUTTONS>;
160  auto calculateMaxButtonSize() const -> std::size_t;
161  void resizeButtons() const;
162  void adjustButtons();
163  auto calculateTotalButtonWidth() const -> std::size_t;
164  void adjustWindowSize (std::size_t);
165  void setButtonPositions (std::size_t);
166 
167  // Data members
168  FString headline_text{};
169  FString text{};
170  FStringList text_components{};
171  FButtons button{};
172  std::size_t max_line_width{0};
173  FColor emphasis_color{getColorTheme()->dialog.emphasis_fg};
174  ButtonType result_code{ButtonType::Reject};
175  FButtonsDigit button_digit{};
176  std::size_t num_buttons{0};
177  std::size_t text_num_lines{0};
178  bool center_text{false};
179 };
180 
181 
182 // FMessageBox inline functions
183 //----------------------------------------------------------------------
184 inline auto FMessageBox::getClassName() const -> FString
185 { return "FMessageBox"; }
186 
187 //----------------------------------------------------------------------
188 inline auto FMessageBox::getTitleBarText() const -> FString
189 {
190  const FString& title = FDialog::getText(); // initialize text
191  return title;
192 }
193 
194 //----------------------------------------------------------------------
195 inline auto FMessageBox::getHeadline() const -> FString
196 { return headline_text; }
197 
198 //----------------------------------------------------------------------
199 inline auto FMessageBox::getText() const -> FString
200 { return text; }
201 
202 //----------------------------------------------------------------------
203 inline void FMessageBox::setTitleBarText (const FString& txt)
204 { return FDialog::setText(txt); }
205 
206 //----------------------------------------------------------------------
207 inline void FMessageBox::setCenterText (bool enable)
208 { center_text = enable; }
209 
210 //----------------------------------------------------------------------
211 inline void FMessageBox::unsetCenterText()
212 { setCenterText(false); }
213 
214 //----------------------------------------------------------------------
215 template <typename messageType>
216 auto FMessageBox::info ( FWidget* parent
217  , const FString& caption
218  , const messageType& message
219  , ButtonType button0
220  , ButtonType button1
221  , ButtonType button2 ) -> ButtonType
222 {
223  FMessageBox mbox ( caption
224  , std::move(FString() << message)
225  , button0, button1, button2
226  , parent );
227  const ButtonType reply = mbox.exec();
228  return reply;
229 }
230 
231 //----------------------------------------------------------------------
232 template <typename messageType>
233 auto FMessageBox::error ( FWidget* parent
234  , const messageType& message
235  , ButtonType button0
236  , ButtonType button1
237  , ButtonType button2 ) -> ButtonType
238 {
239  const FString caption{"Error message"};
240 
241  FMessageBox mbox ( caption
242  , std::move(FString() << message)
243  , button0, button1, button2
244  , parent );
245  FVTerm::getFOutput()->beep();
246  mbox.setHeadline("Warning:");
247  mbox.setCenterText();
248  const auto& wc_error_box = getColorTheme()->error_box;
249  mbox.setForegroundColor(wc_error_box.fg);
250  mbox.setBackgroundColor(wc_error_box.bg);
251  mbox.emphasis_color = wc_error_box.emphasis_fg;
252  const ButtonType reply = mbox.exec();
253  return reply;
254 }
255 
256 } // namespace finalcut
257 
258 #endif // FMESSAGEBOX_H
Definition: class_template.cpp:25
Definition: fstring.h:82
Definition: fdialog.h:69
Definition: fwidget.h:129
Definition: fmessagebox.h:79