OpenTTD
window_gui.h
Go to the documentation of this file.
1 /* $Id: window_gui.h 27085 2014-12-18 18:20:59Z alberth $ */
2 
3 /*
4  * This file is part of OpenTTD.
5  * 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.
6  * 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.
7  * 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/>.
8  */
9 
12 #ifndef WINDOW_GUI_H
13 #define WINDOW_GUI_H
14 
15 #include "vehicle_type.h"
16 #include "viewport_type.h"
17 #include "company_type.h"
18 #include "tile_type.h"
19 #include "widget_type.h"
20 #include "core/smallvec_type.hpp"
21 #include "core/smallmap_type.hpp"
22 #include "string_type.h"
23 
27 enum FrameFlags {
28  FR_NONE = 0,
29  FR_TRANSPARENT = 1 << 0,
30  FR_BORDERONLY = 1 << 4,
31  FR_LOWERED = 1 << 5,
32  FR_DARKENED = 1 << 6,
33 };
34 
36 
37 
39  /* WWT_IMGBTN(_2) */
44 
45  /* WWT_INSET */
49 
54 
55  /* Size of the pure frame bevel without any padding. */
60 
61  /* FrameRect widgets, all text buttons, panel, editbox */
66 
67  /* Extra space at top/bottom of text panels */
70 
71  /* WWT_FRAME */
76 
77  /* WWT_MATRIX */
82 
83  /* WWT_SHADEBOX */
89 
90  /* WWT_STICKYBOX */
96 
97  /* WWT_DEBUGBOX */
103 
104  /* WWT_DEFSIZEBOX */
110 
111  /* WWT_RESIZEBOX */
117 
118  /* WWT_CLOSEBOX */
124 
125  /* WWT_CAPTION */
131 
132  /* Dropdown widget. */
138 
141 };
142 
143 /* widget.cpp */
144 void DrawFrameRect(int left, int top, int right, int bottom, Colours colour, FrameFlags flags);
145 void DrawCaption(const Rect &r, Colours colour, Owner owner, StringID str);
146 
147 /* window.cpp */
148 extern Window *_z_front_window;
149 extern Window *_z_back_window;
150 extern Window *_focused_window;
151 
152 
159 };
160 
161 Point GetToolbarAlignedWindowPosition(int window_width);
162 
163 struct HotkeyList;
164 
169 
170  WindowDesc(WindowPosition default_pos, const char *ini_key, int16 def_width, int16 def_height,
171  WindowClass window_class, WindowClass parent_class, uint32 flags,
172  const NWidgetPart *nwid_parts, int16 nwid_length, HotkeyList *hotkeys = NULL);
173 
174  ~WindowDesc();
175 
181  const char *ini_key;
182  uint32 flags;
184  int16 nwid_length;
186 
187  bool pref_sticky;
188  int16 pref_width;
189  int16 pref_height;
190 
191  int16 GetDefaultWidth() const { return this->pref_width != 0 ? this->pref_width : this->default_width; }
192  int16 GetDefaultHeight() const { return this->pref_height != 0 ? this->pref_height : this->default_height; }
193 
194  static void LoadFromConfig();
195  static void SaveToConfig();
196 
197 private:
202  WindowDesc(const WindowDesc &other);
203 };
204 
209  WDF_CONSTRUCTION = 1 << 0,
210  WDF_MODAL = 1 << 1,
211  WDF_NO_FOCUS = 1 << 2,
212 };
213 
217 struct ResizeInfo {
218  uint step_width;
219  uint step_height;
220 };
221 
227 };
228 
233  WF_TIMEOUT = 1 << 0,
234 
235  WF_DRAGGING = 1 << 3,
236  WF_SIZING_RIGHT = 1 << 4,
237  WF_SIZING_LEFT = 1 << 5,
239  WF_STICKY = 1 << 6,
241  WF_WHITE_BORDER = 1 << 8,
242  WF_HIGHLIGHTED = 1 << 9,
243  WF_CENTERED = 1 << 10,
244 };
246 
247 static const int TIMEOUT_DURATION = 7;
248 static const int WHITE_BORDER_DURATION = 3;
249 
259  int32 scrollpos_x;
260  int32 scrollpos_y;
263 };
264 
265 struct QueryString;
266 
271 protected:
273  void InitializePositionSize(int x, int y, int min_width, int min_height);
274  void FindWindowPlacementAndResize(int def_width, int def_height);
275 
277 
278 public:
279  Window(WindowDesc *desc);
280 
281  virtual ~Window();
282 
289  inline void *operator new[](size_t size)
290  {
291  NOT_REACHED();
292  }
293 
299  inline void operator delete(void *ptr)
300  {
301  }
302 
307 
310 
311  int left;
312  int top;
313  int width;
314  int height;
315 
317 
319 
328 
330 
334 
335  template <class NWID>
336  inline const NWID *GetWidget(uint widnum) const;
337  template <class NWID>
338  inline NWID *GetWidget(uint widnum);
339 
340  const Scrollbar *GetScrollbar(uint widnum) const;
341  Scrollbar *GetScrollbar(uint widnum);
342 
343  const QueryString *GetQueryString(uint widnum) const;
344  QueryString *GetQueryString(uint widnum);
345 
346  virtual const char *GetFocusedText() const;
347  virtual const char *GetCaret() const;
348  virtual const char *GetMarkedText(size_t *length) const;
349  virtual Point GetCaretPosition() const;
350  virtual Rect GetTextBoundingRect(const char *from, const char *to) const;
351  virtual const char *GetTextCharacterAtPosition(const Point &pt) const;
352 
353  void InitNested(WindowNumber number = 0);
354  void CreateNestedTree(bool fill_nested = true);
355  void FinishInitNested(WindowNumber window_number = 0);
356 
360  inline void SetTimeout()
361  {
362  this->flags |= WF_TIMEOUT;
364  }
365 
369  inline void SetWhiteBorder()
370  {
371  this->flags |= WF_WHITE_BORDER;
373  }
374 
376  void SetWidgetHighlight(byte widget_index, TextColour highlighted_colour);
377  bool IsWidgetHighlighted(byte widget_index) const;
378 
386  inline void SetWidgetDisabledState(byte widget_index, bool disab_stat)
387  {
388  assert(widget_index < this->nested_array_size);
389  if (this->nested_array[widget_index] != NULL) this->GetWidget<NWidgetCore>(widget_index)->SetDisabled(disab_stat);
390  }
391 
396  inline void DisableWidget(byte widget_index)
397  {
398  SetWidgetDisabledState(widget_index, true);
399  }
400 
405  inline void EnableWidget(byte widget_index)
406  {
407  SetWidgetDisabledState(widget_index, false);
408  }
409 
415  inline bool IsWidgetDisabled(byte widget_index) const
416  {
417  assert(widget_index < this->nested_array_size);
418  return this->GetWidget<NWidgetCore>(widget_index)->IsDisabled();
419  }
420 
426  inline bool IsWidgetFocused(byte widget_index) const
427  {
428  return this->nested_focus != NULL && this->nested_focus->index == widget_index;
429  }
430 
437  inline bool IsWidgetGloballyFocused(byte widget_index) const
438  {
439  return _focused_window == this && IsWidgetFocused(widget_index);
440  }
441 
447  inline void SetWidgetLoweredState(byte widget_index, bool lowered_stat)
448  {
449  assert(widget_index < this->nested_array_size);
450  this->GetWidget<NWidgetCore>(widget_index)->SetLowered(lowered_stat);
451  }
452 
457  inline void ToggleWidgetLoweredState(byte widget_index)
458  {
459  assert(widget_index < this->nested_array_size);
460  bool lowered_state = this->GetWidget<NWidgetCore>(widget_index)->IsLowered();
461  this->GetWidget<NWidgetCore>(widget_index)->SetLowered(!lowered_state);
462  }
463 
468  inline void LowerWidget(byte widget_index)
469  {
470  SetWidgetLoweredState(widget_index, true);
471  }
472 
477  inline void RaiseWidget(byte widget_index)
478  {
479  SetWidgetLoweredState(widget_index, false);
480  }
481 
487  inline bool IsWidgetLowered(byte widget_index) const
488  {
489  assert(widget_index < this->nested_array_size);
490  return this->GetWidget<NWidgetCore>(widget_index)->IsLowered();
491  }
492 
493  void UnfocusFocusedWidget();
494  bool SetFocusedWidget(int widget_index);
495 
496  EventState HandleEditBoxKey(int wid, WChar key, uint16 keycode);
497  virtual void InsertTextString(int wid, const char *str, bool marked, const char *caret, const char *insert_location, const char *replacement_end);
498 
499  void HandleButtonClick(byte widget);
500  int GetRowFromWidget(int clickpos, int widget, int padding, int line_height = -1) const;
501 
502  void RaiseButtons(bool autoraise = false);
503  void CDECL SetWidgetsDisabledState(bool disab_stat, int widgets, ...);
504  void CDECL SetWidgetsLoweredState(bool lowered_stat, int widgets, ...);
505  void SetWidgetDirty(byte widget_index) const;
506 
507  void DrawWidgets() const;
508  void DrawViewport() const;
509  void DrawSortButtonState(int widget, SortButtonState state) const;
510  static int SortButtonWidth();
511 
512  void DeleteChildWindows(WindowClass wc = WC_INVALID) const;
513 
514  void SetDirty() const;
515  void ReInit(int rx = 0, int ry = 0);
516 
518  inline bool IsShaded() const
519  {
520  return this->shade_select != NULL && this->shade_select->shown_plane == SZSP_HORIZONTAL;
521  }
522 
523  void SetShaded(bool make_shaded);
524 
525  void InvalidateData(int data = 0, bool gui_scope = true);
528 
529  /*** Event handling ***/
530 
535  virtual void OnInit() { }
536 
537  virtual void ApplyDefaults();
538 
546  virtual Point OnInitialPosition(int16 sm_width, int16 sm_height, int window_number);
547 
552  virtual void OnPaint()
553  {
554  this->DrawWidgets();
555  }
556 
563  virtual void DrawWidget(const Rect &r, int widget) const {}
564 
577  virtual void UpdateWidgetSize(int widget, Dimension *size, const Dimension &padding, Dimension *fill, Dimension *resize) {}
578 
585  virtual void SetStringParameters(int widget) const {}
586 
590  virtual void OnFocus() {}
591 
592  virtual void OnFocusLost();
593 
601  virtual EventState OnKeyPress(WChar key, uint16 keycode) { return ES_NOT_HANDLED; }
602 
603  virtual EventState OnHotkey(int hotkey);
604 
611 
612 
619  virtual void OnClick(Point pt, int widget, int click_count) {}
620 
628  virtual bool OnRightClick(Point pt, int widget) { return false; }
629 
635  virtual void OnHover(Point pt, int widget) {}
636 
642  virtual void OnMouseDrag(Point pt, int widget) {}
643 
649  virtual void OnDragDrop(Point pt, int widget) {}
650 
655  virtual void OnScroll(Point delta) {}
656 
663  virtual void OnMouseOver(Point pt, int widget) {}
664 
669  virtual void OnMouseWheel(int wheel) {}
670 
671 
675  virtual void OnMouseLoop() {}
676 
680  virtual void OnTick() {}
681 
685  virtual void OnHundredthTick() {}
686 
690  virtual void OnTimeout() {}
691 
692 
697  virtual void OnResize() {}
698 
704  virtual void OnDropdownSelect(int widget, int index) {}
705 
706  virtual void OnDropdownClose(Point pt, int widget, int index, bool instant_close);
707 
712  virtual void OnEditboxChanged(int widget) {}
713 
720  virtual void OnQueryTextFinished(char *str) {}
721 
727  virtual void OnInvalidateData(int data = 0, bool gui_scope = true) {}
728 
735  virtual void OnPlaceObject(Point pt, TileIndex tile) {}
736 
742  virtual bool OnVehicleSelect(const struct Vehicle *v) { return false; }
743 
747  virtual void OnPlaceObjectAbort() {}
748 
749 
757  virtual void OnPlaceDrag(ViewportPlaceMethod select_method, ViewportDragDropSelectionProcess select_proc, Point pt) {}
758 
768  virtual void OnPlaceMouseUp(ViewportPlaceMethod select_method, ViewportDragDropSelectionProcess select_proc, Point pt, TileIndex start_tile, TileIndex end_tile) {}
769 
777  virtual void OnPlacePresize(Point pt, TileIndex tile) {}
778 
779  /*** End of the event handling ***/
780 
785  virtual bool IsNewGRFInspectable() const { return false; }
786 
793  virtual void ShowNewGRFInspectWindow() const { NOT_REACHED(); }
794 };
795 
802 template <class NWID>
803 inline NWID *Window::GetWidget(uint widnum)
804 {
805  if (widnum >= this->nested_array_size || this->nested_array[widnum] == NULL) return NULL;
806  NWID *nwid = dynamic_cast<NWID *>(this->nested_array[widnum]);
807  assert(nwid != NULL);
808  return nwid;
809 }
810 
812 template <>
813 inline const NWidgetBase *Window::GetWidget<NWidgetBase>(uint widnum) const
814 {
815  if (widnum >= this->nested_array_size) return NULL;
816  return this->nested_array[widnum];
817 }
818 
825 template <class NWID>
826 inline const NWID *Window::GetWidget(uint widnum) const
827 {
828  return const_cast<Window *>(this)->GetWidget<NWID>(widnum);
829 }
830 
831 
835 class PickerWindowBase : public Window {
836 
837 public:
839  {
840  this->parent = parent;
841  }
842 
843  virtual ~PickerWindowBase();
844 };
845 
847 Window *FindWindowFromPt(int x, int y);
848 
857 template <typename Wcls>
858 Wcls *AllocateWindowDescFront(WindowDesc *desc, int window_number, bool return_existing = false)
859 {
860  Wcls *w = static_cast<Wcls *>(BringWindowToFrontById(desc->cls, window_number));
861  if (w != NULL) return return_existing ? w : NULL;
862  return new Wcls(desc, window_number);
863 }
864 
865 void RelocateAllWindows(int neww, int newh);
866 
867 /* misc_gui.cpp */
868 enum TooltipCloseCondition {
869  TCC_RIGHT_CLICK,
870  TCC_LEFT_CLICK,
871  TCC_HOVER,
872 };
873 
874 void GuiShowTooltips(Window *parent, StringID str, uint paramcount = 0, const uint64 params[] = NULL, TooltipCloseCondition close_tooltip = TCC_HOVER);
875 
876 /* widget.cpp */
877 int GetWidgetFromPos(const Window *w, int x, int y);
878 
880 #define FOR_ALL_WINDOWS_FROM_BACK_FROM(w, start) for (w = start; w != NULL; w = w->z_front) if (w->window_class != WC_INVALID)
881 #define FOR_ALL_WINDOWS_FROM_FRONT_FROM(w, start) for (w = start; w != NULL; w = w->z_back) if (w->window_class != WC_INVALID)
882 #define FOR_ALL_WINDOWS_FROM_BACK(w) FOR_ALL_WINDOWS_FROM_BACK_FROM(w, _z_back_window)
883 #define FOR_ALL_WINDOWS_FROM_FRONT(w) FOR_ALL_WINDOWS_FROM_FRONT_FROM(w, _z_front_window)
884 
885 extern Point _cursorpos_drag_start;
886 
887 extern int _scrollbar_start_pos;
888 extern int _scrollbar_size;
889 extern byte _scroller_click_timeout;
890 
891 extern bool _scrolling_viewport;
892 extern bool _mouse_hovering;
893 
900 };
902 
903 void SetFocusedWindow(Window *w);
904 
905 void ScrollbarClickHandler(Window *w, NWidgetCore *nw, int x, int y);
906 
907 #endif /* WINDOW_GUI_H */