2009-08-21 22:21:05 +02:00
/*
* 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 < http : //www.gnu.org/licenses/>.
*/
2007-12-19 20:44:29 +01:00
/** @file window_gui.h Functions, definitions and such used only by the GUI. */
2007-02-23 02:48:53 +01:00
2007-12-19 20:44:29 +01:00
# ifndef WINDOW_GUI_H
# define WINDOW_GUI_H
2004-08-09 19:04:08 +02:00
2022-11-26 18:03:21 +01:00
# include "vehiclelist.h"
2007-12-26 12:45:43 +01:00
# include "vehicle_type.h"
2008-01-09 10:45:45 +01:00
# include "viewport_type.h"
2008-09-30 22:51:04 +02:00
# include "company_type.h"
2008-05-07 15:10:15 +02:00
# include "tile_type.h"
2009-02-09 02:06:23 +01:00
# include "widget_type.h"
2013-08-05 22:36:24 +02:00
# include "string_type.h"
2004-08-09 19:04:08 +02:00
2008-04-07 22:28:58 +02:00
/**
* Flags to describe the look of the frame
*/
2007-03-07 13:11:48 +01:00
enum FrameFlags {
2007-12-04 18:51:50 +01:00
FR_NONE = 0 ,
FR_TRANSPARENT = 1 < < 0 , ///< Makes the background transparent if set
FR_BORDERONLY = 1 < < 4 , ///< Draw border only, no background
2009-02-09 03:57:15 +01:00
FR_LOWERED = 1 < < 5 , ///< If set the frame is lowered and the background colour brighter (ie. buttons when pressed)
FR_DARKENED = 1 < < 6 , ///< If set the background is darker, allows for lowered frames with normal background colour when used with FR_LOWERED (ie. dropdown boxes)
2007-03-07 13:11:48 +01:00
} ;
2006-08-29 08:07:57 +02:00
2010-03-23 23:25:43 +01:00
DECLARE_ENUM_AS_BIT_SET ( FrameFlags )
2007-01-10 19:56:51 +01:00
2024-01-15 23:49:59 +01:00
class WidgetDimensions {
public :
2024-01-21 19:10:49 +01:00
RectPadding imgbtn ; ///< Padding around image button image.
RectPadding inset ; ///< Padding inside inset container.
RectPadding vscrollbar ; ///< Padding inside vertical scrollbar buttons.
RectPadding hscrollbar ; ///< Padding inside horizontal scrollbar buttons.
RectPadding bevel ; ///< Bevel thickness, affected by "scaled bevels" game option.
RectPadding fullbevel ; ///< Always-scaled bevel thickness.
RectPadding framerect ; ///< Standard padding inside many panels.
RectPadding frametext ; ///< Padding inside frame with text.
RectPadding matrix ; ///< Padding of WWT_MATRIX items.
RectPadding shadebox ; ///< Padding around image in shadebox widget.
RectPadding stickybox ; ///< Padding around image in stickybox widget.
RectPadding debugbox ; ///< Padding around image in debugbox widget.
RectPadding defsizebox ; ///< Padding around image in defsizebox widget.
RectPadding resizebox ; ///< Padding around image in resizebox widget.
RectPadding closebox ; ///< Padding around image in closebox widget.
RectPadding captiontext ; ///< Padding for text within caption widget.
RectPadding dropdowntext ; ///< Padding of drop down list item.
RectPadding dropdownlist ; ///< Padding of complete drop down list.
RectPadding modalpopup ; ///< Spacing for popup warning/information windows.
RectPadding picker ; ///< Padding for a picker (dock, station, etc) window.
RectPadding sparse ; ///< Padding used for 'sparse' widget window, usually containing multiple frames.
2023-10-25 02:04:42 +02:00
RectPadding sparse_resize ; ///< Padding used for a resizeable 'sparse' widget window, usually containing multiple frames.
2022-09-28 19:02:14 +02:00
2023-11-03 03:25:05 +01:00
int vsep_picker ; ///< Vertical spacing of picker-window widgets.
2022-09-28 19:02:14 +02:00
int vsep_normal ; ///< Normal vertical spacing.
2023-10-25 02:04:42 +02:00
int vsep_sparse ; ///< Normal vertical spacing for 'sparse' widget window.
2022-09-28 19:02:14 +02:00
int vsep_wide ; ///< Wide vertical spacing.
int hsep_normal ; ///< Normal horizontal spacing.
int hsep_wide ; ///< Wide horizontal spacing.
int hsep_indent ; ///< Width of identation for tree layouts.
static const WidgetDimensions unscaled ; ///< Unscaled widget dimensions.
static WidgetDimensions scaled ; ///< Widget dimensions scaled for current zoom level.
2024-01-15 23:49:59 +01:00
2024-03-27 10:02:41 +01:00
static constexpr float ASPECT_LOCATION = 12.f / 14.f ;
static constexpr float ASPECT_RENAME = 12.f / 14.f ;
static constexpr float ASPECT_SETTINGS_BUTTON = 21.f / 12.f ;
static constexpr float ASPECT_TOGGLE_SIZE = 12.f / 14.f ;
static constexpr float ASPECT_UP_DOWN_BUTTON = 11.f / 12.f ;
static constexpr float ASPECT_VEHICLE_ICON = 15.f / 12.f ;
static constexpr float ASPECT_VEHICLE_FLAG = 11.f / 12.f ;
2024-01-15 23:49:59 +01:00
private :
/**
* Distances used in drawing widgets .
* These constants should not be used elsewhere , use scaled / unscaled WidgetDimensions instead .
*/
enum WidgetDrawDistances {
2024-01-21 19:10:49 +01:00
WD_SHADEBOX_WIDTH = 12 , ///< Minimum width of a standard shade box widget.
WD_STICKYBOX_WIDTH = 12 , ///< Minimum width of a standard sticky box widget.
WD_DEBUGBOX_WIDTH = 12 , ///< Minimum width of a standard debug box widget.
WD_DEFSIZEBOX_WIDTH = 12 , ///< Minimum width of a standard defsize box widget.
WD_RESIZEBOX_WIDTH = 12 , ///< Minimum width of a resize box widget.
WD_CLOSEBOX_WIDTH = 11 , ///< Minimum width of a close box widget.
WD_CAPTION_HEIGHT = 14 , ///< Minimum height of a title bar.
WD_DROPDOWN_HEIGHT = 12 , ///< Minimum height of a drop down widget.
2024-01-15 23:49:59 +01:00
} ;
friend NWidgetLeaf ;
} ;
inline constexpr WidgetDimensions WidgetDimensions : : unscaled = {
2024-01-21 19:10:49 +01:00
. imgbtn = { . left = 1 , . top = 1 , . right = 1 , . bottom = 1 } ,
. inset = { . left = 2 , . top = 1 , . right = 2 , . bottom = 1 } ,
. vscrollbar = { . left = 2 , . top = 3 , . right = 2 , . bottom = 3 } ,
. hscrollbar = { . left = 3 , . top = 2 , . right = 3 , . bottom = 2 } ,
. bevel = { . left = 1 , . top = 1 , . right = 1 , . bottom = 1 } ,
. fullbevel = { . left = 1 , . top = 1 , . right = 1 , . bottom = 1 } ,
. framerect = { . left = 2 , . top = 1 , . right = 2 , . bottom = 1 } ,
. frametext = { . left = 6 , . top = 6 , . right = 6 , . bottom = 6 } ,
. matrix = { . left = 2 , . top = 3 , . right = 2 , . bottom = 1 } ,
. shadebox = { . left = 2 , . top = 3 , . right = 2 , . bottom = 3 } ,
. stickybox = { . left = 2 , . top = 3 , . right = 2 , . bottom = 3 } ,
. debugbox = { . left = 2 , . top = 3 , . right = 2 , . bottom = 3 } ,
. defsizebox = { . left = 2 , . top = 3 , . right = 2 , . bottom = 3 } ,
. resizebox = { . left = 2 , . top = 2 , . right = 2 , . bottom = 2 } ,
. closebox = { . left = 2 , . top = 2 , . right = 1 , . bottom = 2 } ,
. captiontext = { . left = 2 , . top = 2 , . right = 2 , . bottom = 2 } ,
. dropdowntext = { . left = 2 , . top = 1 , . right = 2 , . bottom = 1 } ,
. dropdownlist = { . left = 1 , . top = 2 , . right = 1 , . bottom = 2 } ,
. modalpopup = { . left = 20 , . top = 10 , . right = 20 , . bottom = 10 } ,
. picker = { . left = 3 , . top = 3 , . right = 3 , . bottom = 3 } ,
. sparse = { . left = 10 , . top = 8 , . right = 10 , . bottom = 8 } ,
. sparse_resize = { . left = 10 , . top = 8 , . right = 10 , . bottom = 0 } ,
. vsep_picker = 1 ,
. vsep_normal = 2 ,
. vsep_sparse = 4 ,
. vsep_wide = 8 ,
. hsep_normal = 2 ,
. hsep_wide = 6 ,
. hsep_indent = 10 ,
2022-09-28 19:02:14 +02:00
} ;
2010-06-07 21:56:32 +02:00
/* widget.cpp */
2009-02-09 03:57:15 +01:00
void DrawFrameRect ( int left , int top , int right , int bottom , Colours colour , FrameFlags flags ) ;
2022-09-28 18:16:46 +02:00
2024-01-06 12:19:27 +01:00
inline void DrawFrameRect ( const Rect & r , Colours colour , FrameFlags flags )
2022-09-28 18:16:46 +02:00
{
DrawFrameRect ( r . left , r . top , r . right , r . bottom , colour , flags ) ;
}
2023-04-28 18:59:14 +02:00
void DrawCaption ( const Rect & r , Colours colour , Owner owner , TextColour text_colour , StringID str , StringAlignment align , FontSize fs ) ;
2005-06-15 19:27:14 +02:00
2009-02-17 13:41:29 +01:00
/* window.cpp */
2021-05-09 17:12:34 +02:00
using WindowList = std : : list < Window * > ;
extern WindowList _z_windows ;
2009-02-17 13:41:29 +01:00
extern Window * _focused_window ;
2009-11-28 15:42:35 +01:00
/** How do we the window to be placed? */
enum WindowPosition {
WDP_MANUAL , ///< Manually align the window (so no automatic location finding)
WDP_AUTO , ///< Find a place automatically
WDP_CENTER , ///< Center the window
WDP_ALIGN_TOOLBAR , ///< Align toward the toolbar
} ;
Point GetToolbarAlignedWindowPosition ( int window_width ) ;
2013-06-15 17:30:16 +02:00
struct HotkeyList ;
2008-04-07 22:28:58 +02:00
/**
* High level window description
*/
2009-03-15 16:12:06 +01:00
struct WindowDesc : ZeroedMemoryAllocator {
2024-01-17 04:17:02 +01:00
WindowDesc ( WindowPosition default_pos , const char * ini_key , int16_t def_width_trad , int16_t def_height_trad ,
2023-05-08 19:01:06 +02:00
WindowClass window_class , WindowClass parent_class , uint32_t flags ,
2024-01-17 04:17:02 +01:00
const NWidgetPart * nwid_begin , const NWidgetPart * nwid_end , HotkeyList * hotkeys = nullptr ,
const std : : source_location location = std : : source_location : : current ( ) ) ;
2009-03-15 16:12:06 +01:00
2009-03-22 22:15:45 +01:00
~ WindowDesc ( ) ;
2024-01-17 04:17:02 +01:00
const std : : source_location source_location ; ///< Source location of this definition
2013-01-08 23:46:42 +01:00
WindowPosition default_pos ; ///< Preferred position of the window. @see WindowPosition()
2009-03-22 22:15:45 +01:00
WindowClass cls ; ///< Class of the window, @see WindowClass.
WindowClass parent_cls ; ///< Class of the parent window. @see WindowClass
2019-04-10 23:07:06 +02:00
const char * ini_key ; ///< Key to store window defaults in openttd.cfg. \c nullptr if nothing shall be stored.
2023-05-08 19:01:06 +02:00
uint32_t flags ; ///< Flags. @see WindowDefaultFlag
2023-09-03 22:54:13 +02:00
const NWidgetPart * nwid_begin ; ///< Beginning of nested widget parts describing the window.
const NWidgetPart * nwid_end ; ///< Ending of nested widget parts describing the window.
2013-06-15 17:30:16 +02:00
HotkeyList * hotkeys ; ///< Hotkeys for the window.
2013-05-26 21:27:22 +02:00
2013-05-26 21:27:44 +02:00
bool pref_sticky ; ///< Preferred stickyness.
2023-05-08 19:01:06 +02:00
int16_t pref_width ; ///< User-preferred width of the window. Zero if unset.
int16_t pref_height ; ///< User-preferred height of the window. Zero if unset.
2013-05-26 21:30:31 +02:00
2023-05-08 19:01:06 +02:00
int16_t GetDefaultWidth ( ) const ;
int16_t GetDefaultHeight ( ) const ;
2013-05-26 21:27:44 +02:00
2013-05-26 21:27:22 +02:00
static void LoadFromConfig ( ) ;
static void SaveToConfig ( ) ;
2013-06-15 17:06:22 +02:00
private :
2023-05-08 19:01:06 +02:00
int16_t default_width_trad ; ///< Preferred initial width of the window (pixels at 1x zoom).
int16_t default_height_trad ; ///< Preferred initial height of the window (pixels at 1x zoom).
2015-02-13 22:25:48 +01:00
2013-06-15 17:06:22 +02:00
/**
2024-01-17 04:17:02 +01:00
* Delete copy constructor to prevent compilers from
2013-06-15 17:06:22 +02:00
* copying the structure , which fails due to _window_descs .
*/
2024-01-17 04:17:02 +01:00
WindowDesc ( const WindowDesc & ) = delete ;
WindowDesc & operator = ( const WindowDesc & ) = delete ;
2007-03-07 13:11:48 +01:00
} ;
2004-08-09 19:04:08 +02:00
2008-04-07 22:28:58 +02:00
/**
* Window default widget / window handling flags
*/
2006-12-29 14:59:48 +01:00
enum WindowDefaultFlag {
2009-11-24 18:28:29 +01:00
WDF_CONSTRUCTION = 1 < < 0 , ///< This window is used for construction; close it whenever changing company.
2012-11-11 17:10:43 +01:00
WDF_MODAL = 1 < < 1 , ///< The window is a modal child of some other window, meaning the parent is 'inactive'
WDF_NO_FOCUS = 1 < < 2 , ///< This window won't get focus/make any other window lose focus when click
2023-06-14 18:24:14 +02:00
WDF_NO_CLOSE = 1 < < 3 , ///< This window can't be interactively closed
2004-08-09 19:04:08 +02:00
} ;
2008-04-07 22:28:58 +02:00
/**
* Data structure for resizing a window
*/
2007-03-07 13:11:48 +01:00
struct ResizeInfo {
2008-04-07 22:28:58 +02:00
uint step_width ; ///< Step-size of width resize changes
uint step_height ; ///< Step-size of height resize changes
2007-03-07 13:11:48 +01:00
} ;
2005-01-03 20:45:18 +01:00
2009-08-14 20:41:03 +02:00
/** State of a sort direction button. */
2008-05-17 14:48:06 +02:00
enum SortButtonState {
2009-08-14 20:41:03 +02:00
SBS_OFF , ///< Do not sort (with this button).
SBS_DOWN , ///< Sort ascending.
SBS_UP , ///< Sort descending.
2008-05-17 14:48:06 +02:00
} ;
2011-12-15 20:54:23 +01:00
/**
* Window flags .
*/
enum WindowFlags {
WF_TIMEOUT = 1 < < 0 , ///< Window timeout counter.
WF_DRAGGING = 1 < < 3 , ///< Window is being dragged.
WF_SIZING_RIGHT = 1 < < 4 , ///< Window is being resized towards the right.
WF_SIZING_LEFT = 1 < < 5 , ///< Window is being resized towards the left.
WF_SIZING = WF_SIZING_RIGHT | WF_SIZING_LEFT , ///< Window is being resized.
WF_STICKY = 1 < < 6 , ///< Window is made sticky by user
WF_DISABLE_VP_SCROLL = 1 < < 7 , ///< Window does not do autoscroll, @see HandleAutoscroll().
WF_WHITE_BORDER = 1 < < 8 , ///< Window white border counter bit mask.
2011-12-19 22:05:14 +01:00
WF_HIGHLIGHTED = 1 < < 9 , ///< Window has a widget that has a highlight.
2011-12-15 20:54:23 +01:00
WF_CENTERED = 1 < < 10 , ///< Window is centered and shall stay centered after ReInit.
} ;
DECLARE_ENUM_AS_BIT_SET ( WindowFlags )
static const int TIMEOUT_DURATION = 7 ; ///< The initial timeout value for WF_TIMEOUT.
static const int WHITE_BORDER_DURATION = 3 ; ///< The initial timeout value for WF_WHITE_BORDER.
2008-04-07 22:28:58 +02:00
/**
2009-07-26 14:49:26 +02:00
* Data structure for a window viewport .
* A viewport is either following a vehicle ( its id in then in # follow_vehicle ) , or it aims to display a specific
* location # dest_scrollpos_x , # dest_scrollpos_y ( # follow_vehicle is then # INVALID_VEHICLE ) .
* The actual location being shown is # scrollpos_x , # scrollpos_y .
2009-07-26 19:29:01 +02:00
* @ see InitializeViewport ( ) , UpdateViewportPosition ( ) , UpdateViewportCoordinates ( ) .
2008-05-11 17:08:44 +02:00
*/
2020-06-29 03:38:29 +02:00
struct ViewportData : Viewport {
2009-07-26 14:49:26 +02:00
VehicleID follow_vehicle ; ///< VehicleID to follow if following a vehicle, #INVALID_VEHICLE otherwise.
2023-05-08 19:01:06 +02:00
int32_t scrollpos_x ; ///< Currently shown x coordinate (virtual screen coordinate of topleft corner of the viewport).
int32_t scrollpos_y ; ///< Currently shown y coordinate (virtual screen coordinate of topleft corner of the viewport).
int32_t dest_scrollpos_x ; ///< Current destination x coordinate to display (virtual screen coordinate of topleft corner of the viewport).
int32_t dest_scrollpos_y ; ///< Current destination y coordinate to display (virtual screen coordinate of topleft corner of the viewport).
2008-05-11 17:08:44 +02:00
} ;
2012-11-14 23:50:35 +01:00
struct QueryString ;
2019-03-20 03:13:36 +01:00
/* misc_gui.cpp */
enum TooltipCloseCondition {
TCC_RIGHT_CLICK ,
TCC_HOVER ,
TCC_NONE ,
2021-04-05 13:30:58 +02:00
TCC_EXIT_VIEWPORT ,
2019-03-20 03:13:36 +01:00
} ;
2008-05-17 05:29:16 +02:00
/**
2008-04-07 22:28:58 +02:00
* Data structure for an opened window
*/
2008-04-13 21:25:14 +02:00
struct Window : ZeroedMemoryAllocator {
2021-05-15 23:12:25 +02:00
private :
static std : : vector < Window * > closed_windows ;
2008-05-08 13:31:41 +02:00
protected :
2013-05-26 21:23:42 +02:00
void InitializeData ( WindowNumber window_number ) ;
2009-07-09 21:52:47 +02:00
void InitializePositionSize ( int x , int y , int min_width , int min_height ) ;
2015-02-13 22:13:45 +01:00
virtual void FindWindowPlacementAndResize ( int def_width , int def_height ) ;
2008-05-08 13:31:41 +02:00
2019-03-03 18:30:09 +01:00
std : : vector < int > scheduled_invalidation_data ; ///< Data of scheduled OnInvalidateData() calls.
2024-01-27 19:44:27 +01:00
bool scheduled_resize ; ///< Set if window has been resized.
2011-02-23 21:54:55 +01:00
2021-05-15 23:12:25 +02:00
/* Protected to prevent deletion anywhere outside Window::DeleteClosedWindows(). */
virtual ~ Window ( ) ;
2008-05-04 12:05:50 +02:00
public :
2013-05-26 21:23:42 +02:00
Window ( WindowDesc * desc ) ;
2008-05-08 13:31:41 +02:00
2009-11-11 22:15:58 +01:00
/**
* Helper allocation function to disallow something .
* Don ' t allow arrays ; arrays of Windows are pointless as you need
* to destruct them all at the same time too , which is kinda hard .
* @ param size the amount of space not to allocate
*/
2021-05-09 17:12:34 +02:00
inline void * operator new [ ] ( size_t size ) = delete ;
2008-05-04 12:05:50 +02:00
2013-05-26 21:23:42 +02:00
WindowDesc * window_desc ; ///< Window description
2011-12-15 20:54:23 +01:00
WindowFlags flags ; ///< Window flags
2008-04-07 22:28:58 +02:00
WindowClass window_class ; ///< Window class
WindowNumber window_number ; ///< Window number within the window class
2004-08-09 19:04:08 +02:00
2023-11-29 13:35:02 +01:00
int scale ; ///< Scale of this window -- used to determine how to resize.
2023-05-08 19:01:06 +02:00
uint8_t timeout_timer ; ///< Timer value of the WF_TIMEOUT for flags.
uint8_t white_border_timer ; ///< Timer value of the WF_WHITE_BORDER for flags.
2011-12-15 20:54:23 +01:00
2008-04-07 22:28:58 +02:00
int left ; ///< x position of left edge of the window
int top ; ///< y position of top edge of the window
int width ; ///< width of the window (number of pixels to the right in x direction)
int height ; ///< Height of the window (number of pixels down in y direction)
2004-08-09 19:04:08 +02:00
2008-04-07 22:28:58 +02:00
ResizeInfo resize ; ///< Resize information
2004-08-09 19:04:08 +02:00
2009-02-09 03:33:10 +01:00
Owner owner ; ///< The owner of the content shown in this window. Company colour is acquired from this variable.
2004-08-09 19:04:08 +02:00
2009-06-04 16:07:05 +02:00
ViewportData * viewport ; ///< Pointer to viewport data, if present.
2019-04-10 23:07:06 +02:00
const NWidgetCore * nested_focus ; ///< Currently focused nested widget, or \c nullptr if no nested widget has focus.
2024-01-14 17:47:10 +01:00
std : : map < WidgetID , QueryString * > querystrings ; ///< QueryString associated to WWT_EDITBOX widgets.
2023-12-30 08:36:22 +01:00
std : : unique_ptr < NWidgetBase > nested_root ; ///< Root of the nested tree.
2023-10-16 12:13:36 +02:00
WidgetLookup widget_lookup ; ///< Indexed access to the nested widget tree. Do not access directly, use #Window::GetWidget() instead.
2019-04-10 23:07:06 +02:00
NWidgetStacked * shade_select ; ///< Selection widget (#NWID_SELECTION) to use for shading the window. If \c nullptr, window cannot shade.
2009-12-21 17:06:20 +01:00
Dimension unshaded_size ; ///< Last known unshaded size (only valid while shaded).
2004-08-09 19:04:08 +02:00
2023-12-29 20:11:59 +01:00
WidgetID mouse_capture_widget ; ///< ID of current mouse capture widget (e.g. dragged scrollbar). -1 if no widget has mouse capture.
2010-08-12 11:09:24 +02:00
2009-06-04 16:07:05 +02:00
Window * parent ; ///< Parent window.
2021-05-09 17:12:34 +02:00
WindowList : : iterator z_position ;
2007-12-02 01:59:48 +01:00
2009-09-19 16:41:43 +02:00
template < class NWID >
2023-12-29 20:11:59 +01:00
inline const NWID * GetWidget ( WidgetID widnum ) const ;
2009-10-30 08:51:33 +01:00
template < class NWID >
2023-12-29 20:11:59 +01:00
inline NWID * GetWidget ( WidgetID widnum ) ;
2009-09-19 13:31:12 +02:00
2023-12-29 20:11:59 +01:00
const Scrollbar * GetScrollbar ( WidgetID widnum ) const ;
Scrollbar * GetScrollbar ( WidgetID widnum ) ;
2009-09-19 13:31:12 +02:00
2023-12-29 20:11:59 +01:00
const QueryString * GetQueryString ( WidgetID widnum ) const ;
QueryString * GetQueryString ( WidgetID widnum ) ;
2022-12-25 01:40:55 +01:00
void UpdateQueryStringSize ( ) ;
2012-11-14 23:50:35 +01:00
2023-07-01 22:05:07 +02:00
virtual const struct Textbuf * GetFocusedTextbuf ( ) const ;
2013-08-05 22:37:14 +02:00
virtual Point GetCaretPosition ( ) const ;
2013-08-05 22:37:48 +02:00
virtual Rect GetTextBoundingRect ( const char * from , const char * to ) const ;
2023-05-06 19:53:02 +02:00
virtual ptrdiff_t GetTextCharacterAtPosition ( const Point & pt ) const ;
2013-08-05 22:37:14 +02:00
2013-05-26 21:23:42 +02:00
void InitNested ( WindowNumber number = 0 ) ;
2023-12-29 15:27:04 +01:00
void CreateNestedTree ( ) ;
2013-05-26 21:23:42 +02:00
void FinishInitNested ( WindowNumber window_number = 0 ) ;
2009-06-04 16:34:38 +02:00
2023-08-15 18:12:05 +02:00
template < typename T , std : : enable_if_t < std : : is_base_of < StrongTypedefBase , T > : : value , int > = 0 >
void FinishInitNested ( T number )
{
2023-11-06 21:29:35 +01:00
this - > FinishInitNested ( number . base ( ) ) ;
2023-08-15 18:12:05 +02:00
}
2011-12-15 20:54:23 +01:00
/**
* Set the timeout flag of the window and initiate the timer .
*/
inline void SetTimeout ( )
{
this - > flags | = WF_TIMEOUT ;
this - > timeout_timer = TIMEOUT_DURATION ;
}
/**
* Set the timeout flag of the window and initiate the timer .
*/
inline void SetWhiteBorder ( )
{
this - > flags | = WF_WHITE_BORDER ;
this - > white_border_timer = WHITE_BORDER_DURATION ;
}
2011-12-19 22:05:14 +01:00
void DisableAllWidgetHighlight ( ) ;
2023-12-29 20:11:59 +01:00
void SetWidgetHighlight ( WidgetID widget_index , TextColour highlighted_colour ) ;
bool IsWidgetHighlighted ( WidgetID widget_index ) const ;
2011-12-19 22:05:14 +01:00
2009-02-17 13:41:29 +01:00
/**
* Sets the enabled / disabled status of a widget .
* By default , widgets are enabled .
* On certain conditions , they have to be disabled .
* @ param widget_index index of this widget in the window
* @ param disab_stat status to use ie : disabled = true , enabled = false
*/
2023-12-29 20:11:59 +01:00
inline void SetWidgetDisabledState ( WidgetID widget_index , bool disab_stat )
2009-02-17 13:41:29 +01:00
{
2023-12-30 14:29:31 +01:00
NWidgetCore * nwid = this - > GetWidget < NWidgetCore > ( widget_index ) ;
if ( nwid ! = nullptr ) nwid - > SetDisabled ( disab_stat ) ;
2009-02-17 13:41:29 +01:00
}
/**
* Sets a widget to disabled .
* @ param widget_index index of this widget in the window
*/
2023-12-29 20:11:59 +01:00
inline void DisableWidget ( WidgetID widget_index )
2009-02-17 13:41:29 +01:00
{
SetWidgetDisabledState ( widget_index , true ) ;
}
/**
* Sets a widget to Enabled .
* @ param widget_index index of this widget in the window
*/
2023-12-29 20:11:59 +01:00
inline void EnableWidget ( WidgetID widget_index )
2009-02-17 13:41:29 +01:00
{
SetWidgetDisabledState ( widget_index , false ) ;
}
/**
* Gets the enabled / disabled status of a widget .
* @ param widget_index index of this widget in the window
* @ return status of the widget ie : disabled = true , enabled = false
*/
2023-12-29 20:11:59 +01:00
inline bool IsWidgetDisabled ( WidgetID widget_index ) const
2009-02-17 13:41:29 +01:00
{
2009-11-15 14:36:30 +01:00
return this - > GetWidget < NWidgetCore > ( widget_index ) - > IsDisabled ( ) ;
2009-02-17 13:41:29 +01:00
}
/**
* Check if given widget is focused within this window
* @ param widget_index : index of the widget in the window to check
* @ return true if given widget is the focused window in this window
*/
2023-12-29 20:11:59 +01:00
inline bool IsWidgetFocused ( WidgetID widget_index ) const
2009-02-17 13:41:29 +01:00
{
2019-04-10 23:07:06 +02:00
return this - > nested_focus ! = nullptr & & this - > nested_focus - > index = = widget_index ;
2009-02-17 13:41:29 +01:00
}
/**
* Check if given widget has user input focus . This means that both the window
* has focus and that the given widget has focus within the window .
* @ param widget_index : index of the widget in the window to check
* @ return true if given widget is the focused window in this window and this window has focus
*/
2023-12-29 20:11:59 +01:00
inline bool IsWidgetGloballyFocused ( WidgetID widget_index ) const
2009-02-17 13:41:29 +01:00
{
return _focused_window = = this & & IsWidgetFocused ( widget_index ) ;
}
/**
* Sets the lowered / raised status of a widget .
* @ param widget_index index of this widget in the window
* @ param lowered_stat status to use ie : lowered = true , raised = false
*/
2023-12-29 20:11:59 +01:00
inline void SetWidgetLoweredState ( WidgetID widget_index , bool lowered_stat )
2009-02-17 13:41:29 +01:00
{
2009-11-15 14:36:30 +01:00
this - > GetWidget < NWidgetCore > ( widget_index ) - > SetLowered ( lowered_stat ) ;
2009-02-17 13:41:29 +01:00
}
/**
* Invert the lowered / raised status of a widget .
* @ param widget_index index of this widget in the window
*/
2023-12-29 20:11:59 +01:00
inline void ToggleWidgetLoweredState ( WidgetID widget_index )
2009-02-17 13:41:29 +01:00
{
2009-11-15 14:36:30 +01:00
bool lowered_state = this - > GetWidget < NWidgetCore > ( widget_index ) - > IsLowered ( ) ;
this - > GetWidget < NWidgetCore > ( widget_index ) - > SetLowered ( ! lowered_state ) ;
2009-02-17 13:41:29 +01:00
}
/**
* Marks a widget as lowered .
* @ param widget_index index of this widget in the window
*/
2023-12-29 20:11:59 +01:00
inline void LowerWidget ( WidgetID widget_index )
2009-02-17 13:41:29 +01:00
{
SetWidgetLoweredState ( widget_index , true ) ;
}
/**
* Marks a widget as raised .
* @ param widget_index index of this widget in the window
*/
2023-12-29 20:11:59 +01:00
inline void RaiseWidget ( WidgetID widget_index )
2009-02-17 13:41:29 +01:00
{
SetWidgetLoweredState ( widget_index , false ) ;
}
2023-09-17 06:40:28 +02:00
/**
* Marks a widget as raised and dirty ( redraw ) , when it is marked as lowered .
* @ param widget_index index of this widget in the window
*/
2024-03-18 21:32:38 +01:00
inline void RaiseWidgetWhenLowered ( WidgetID widget_index )
2023-09-17 06:40:28 +02:00
{
if ( this - > IsWidgetLowered ( widget_index ) ) {
this - > RaiseWidget ( widget_index ) ;
this - > SetWidgetDirty ( widget_index ) ;
}
}
2009-02-17 13:41:29 +01:00
/**
* Gets the lowered state of a widget .
* @ param widget_index index of this widget in the window
* @ return status of the widget ie : lowered = true , raised = false
*/
2023-12-29 20:11:59 +01:00
inline bool IsWidgetLowered ( WidgetID widget_index ) const
2009-02-17 13:41:29 +01:00
{
2009-11-15 14:36:30 +01:00
return this - > GetWidget < NWidgetCore > ( widget_index ) - > IsLowered ( ) ;
2009-02-17 13:41:29 +01:00
}
2009-12-31 19:11:03 +01:00
void UnfocusFocusedWidget ( ) ;
2023-12-29 20:11:59 +01:00
bool SetFocusedWidget ( WidgetID widget_index ) ;
2009-09-11 21:12:05 +02:00
2023-12-29 20:11:59 +01:00
EventState HandleEditBoxKey ( WidgetID wid , char32_t key , uint16_t keycode ) ;
virtual void InsertTextString ( WidgetID wid , const char * str , bool marked , const char * caret , const char * insert_location , const char * replacement_end ) ;
2012-11-13 22:47:13 +01:00
2023-12-29 20:11:59 +01:00
void HandleButtonClick ( WidgetID widget ) ;
int GetRowFromWidget ( int clickpos , WidgetID widget , int padding , int line_height = - 1 ) const ;
2007-12-02 01:59:48 +01:00
2009-08-14 23:27:08 +02:00
void RaiseButtons ( bool autoraise = false ) ;
2023-09-16 21:56:09 +02:00
/**
* Sets the enabled / disabled status of a list of widgets .
* By default , widgets are enabled .
* On certain conditions , they have to be disabled .
* @ param disab_stat status to use ie : disabled = true , enabled = false
* @ param widgets list of widgets
*/
template < typename . . . Args >
void SetWidgetsDisabledState ( bool disab_stat , Args . . . widgets )
{
( SetWidgetDisabledState ( widgets , disab_stat ) , . . . ) ;
}
/**
* Sets the lowered / raised status of a list of widgets .
* @ param lowered_stat status to use ie : lowered = true , raised = false
* @ param widgets list of widgets
*/
template < typename . . . Args >
void SetWidgetsLoweredState ( bool lowered_stat , Args . . . widgets )
{
( SetWidgetLoweredState ( widgets , lowered_stat ) , . . . ) ;
}
2023-09-17 06:40:28 +02:00
/**
* Raises the widgets and sets widgets dirty that are lowered .
* @ param widgets list of widgets
*/
template < typename . . . Args >
2023-11-09 20:20:41 +01:00
void RaiseWidgetsWhenLowered ( Args . . . widgets )
{
2023-09-17 06:40:28 +02:00
( this - > RaiseWidgetWhenLowered ( widgets ) , . . . ) ;
}
2023-12-29 20:11:59 +01:00
void SetWidgetDirty ( WidgetID widget_index ) const ;
2008-05-04 12:05:50 +02:00
2008-05-17 14:48:06 +02:00
void DrawWidgets ( ) const ;
void DrawViewport ( ) const ;
2023-12-29 20:11:59 +01:00
void DrawSortButtonState ( WidgetID widget , SortButtonState state ) const ;
2014-10-05 13:20:02 +02:00
static int SortButtonWidth ( ) ;
2008-05-17 14:48:06 +02:00
2023-11-11 22:51:39 +01:00
Window * FindChildWindow ( WindowClass wc = WC_INVALID ) const ;
2021-05-17 15:46:38 +02:00
void CloseChildWindows ( WindowClass wc = WC_INVALID ) const ;
2023-10-13 13:59:15 +02:00
virtual void Close ( int data = 0 ) ;
2021-05-15 23:12:25 +02:00
static void DeleteClosedWindows ( ) ;
2008-09-24 18:40:06 +02:00
2008-05-06 23:28:30 +02:00
void SetDirty ( ) const ;
2023-04-25 10:13:33 +02:00
void ReInit ( int rx = 0 , int ry = 0 , bool reposition = false ) ;
2008-05-06 23:28:30 +02:00
2009-12-21 17:06:20 +01:00
/** Is window shaded currently? */
inline bool IsShaded ( ) const
{
2019-04-10 23:07:06 +02:00
return this - > shade_select ! = nullptr & & this - > shade_select - > shown_plane = = SZSP_HORIZONTAL ;
2009-12-21 17:06:20 +01:00
}
void SetShaded ( bool make_shaded ) ;
2024-01-27 19:44:27 +01:00
void ScheduleResize ( ) ;
void ProcessScheduledResize ( ) ;
2011-12-15 20:54:23 +01:00
void InvalidateData ( int data = 0 , bool gui_scope = true ) ;
void ProcessScheduledInvalidations ( ) ;
2011-12-19 22:05:14 +01:00
void ProcessHighlightedInvalidations ( ) ;
2011-02-23 21:54:55 +01:00
2008-05-10 15:46:36 +02:00
/*** Event handling ***/
2009-11-29 22:14:34 +01:00
/**
* Notification that the nested widget tree gets initialized . The event can be used to perform general computations .
2023-12-29 15:52:42 +01:00
* @ note # nested_root and / or # widget_lookup ( normally accessed via # GetWidget ( ) ) may not exist during this call .
2009-11-29 22:14:34 +01:00
*/
virtual void OnInit ( ) { }
2013-05-26 21:27:44 +02:00
virtual void ApplyDefaults ( ) ;
2009-10-31 12:34:43 +01:00
/**
* Compute the initial position of the window .
* @ param sm_width Smallest width of the window .
* @ param sm_height Smallest height of the window .
* @ param window_number The window number of the new window .
* @ return Initial position of the top - left corner of the window .
*/
2023-05-08 19:01:06 +02:00
virtual Point OnInitialPosition ( int16_t sm_width , int16_t sm_height , int window_number ) ;
2009-10-31 12:34:43 +01:00
2008-05-10 15:46:36 +02:00
/**
2009-06-29 00:23:26 +02:00
* The window must be repainted .
* @ note This method should not change any state , it should only use drawing functions .
2008-05-10 15:46:36 +02:00
*/
2010-11-26 16:22:18 +01:00
virtual void OnPaint ( )
{
this - > DrawWidgets ( ) ;
}
2008-05-10 15:46:36 +02:00
2009-06-29 00:23:26 +02:00
/**
* Draw the contents of a nested widget .
* @ param r Rectangle occupied by the widget .
* @ param widget Number of the widget to draw .
* @ note This method may not change any state , it may only use drawing functions .
*/
2023-12-29 20:11:59 +01:00
virtual void DrawWidget ( [ [ maybe_unused ] ] const Rect & r , [ [ maybe_unused ] ] WidgetID widget ) const { }
2009-06-29 00:23:26 +02:00
2009-07-04 17:35:36 +02:00
/**
2009-07-18 12:46:55 +02:00
* Update size and resize step of a widget in the window .
* After retrieval of the minimal size and the resize - steps of a widget , this function is called to allow further refinement ,
* typically by computing the real maximal size of the content . Afterwards , \ a size is taken to be the minimal size of the widget
* and \ a resize is taken to contain the resize steps . For the convenience of the callee , \ a padding contains the amount of
* padding between the content and the edge of the widget . This should be added to the returned size .
* @ param widget Widget number .
2024-04-09 09:34:45 +02:00
* @ param [ in , out ] size Size of the widget .
2009-07-18 12:46:55 +02:00
* @ param padding Recommended amount of space between the widget content and the widget edge .
2024-04-09 09:34:45 +02:00
* @ param [ in , out ] fill Fill step of the widget .
* @ param [ in , out ] resize Resize step of the widget .
2009-07-04 17:35:36 +02:00
*/
2024-04-09 09:34:45 +02:00
virtual void UpdateWidgetSize ( [ [ maybe_unused ] ] WidgetID widget , [ [ maybe_unused ] ] Dimension & size , [ [ maybe_unused ] ] const Dimension & padding , [ [ maybe_unused ] ] Dimension & fill , [ [ maybe_unused ] ] Dimension & resize ) { }
2009-07-04 17:35:36 +02:00
2009-07-25 13:54:53 +02:00
/**
* Initialize string parameters for a widget .
* Calls to this function are made during initialization to measure the size ( that is as part of # InitNested ( ) ) , during drawing ,
* and while re - initializing the window . Only for widgets that render text initializing is requested .
* @ param widget Widget number .
*/
2023-12-29 20:11:59 +01:00
virtual void SetStringParameters ( [ [ maybe_unused ] ] WidgetID widget ) const { }
2009-07-25 13:54:53 +02:00
2023-06-12 09:42:02 +02:00
/**
* The window has gained focus .
*/
2019-11-04 19:09:24 +01:00
virtual void OnFocus ( ) ;
2009-02-09 02:22:29 +01:00
2023-06-12 09:42:02 +02:00
/**
* The window has lost focus .
* @ param closing True iff the window has lost focus in the process of closing .
*/
virtual void OnFocusLost ( bool closing ) ;
2008-05-10 15:46:36 +02:00
/**
* A key has been pressed .
* @ param key the Unicode value of the key .
* @ param keycode the untranslated key code including shift state .
2009-11-29 22:27:12 +01:00
* @ return # ES_HANDLED if the key press has been handled and no other
2008-05-10 15:46:36 +02:00
* window should receive the event .
*/
2023-09-16 22:20:53 +02:00
virtual EventState OnKeyPress ( [ [ maybe_unused ] ] char32_t key , [ [ maybe_unused ] ] uint16_t keycode ) { return ES_NOT_HANDLED ; }
2008-05-10 15:46:36 +02:00
2013-06-15 17:30:16 +02:00
virtual EventState OnHotkey ( int hotkey ) ;
2008-05-10 15:46:36 +02:00
/**
* The state of the control key has changed
2009-11-29 22:27:12 +01:00
* @ return # ES_HANDLED if the change has been handled and no other
2008-05-10 15:46:36 +02:00
* window should receive the event .
*/
2008-05-19 11:48:47 +02:00
virtual EventState OnCTRLStateChange ( ) { return ES_NOT_HANDLED ; }
2008-05-10 15:46:36 +02:00
/**
* A click with the left mouse button has been made on the window .
* @ param pt the point inside the window that has been clicked .
* @ param widget the clicked widget .
2010-01-30 19:34:48 +01:00
* @ param click_count Number of fast consecutive clicks at same position
2008-05-10 15:46:36 +02:00
*/
2023-12-29 20:11:59 +01:00
virtual void OnClick ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] WidgetID widget , [ [ maybe_unused ] ] int click_count ) { }
2008-05-10 15:46:36 +02:00
/**
* A click with the right mouse button has been made on the window .
* @ param pt the point inside the window that has been clicked .
* @ param widget the clicked widget .
2010-07-14 19:36:27 +02:00
* @ return true if the click was actually handled , i . e . do not show a
* tooltip if tooltip - on - right - click is enabled .
2008-05-10 15:46:36 +02:00
*/
2023-12-29 20:11:59 +01:00
virtual bool OnRightClick ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] WidgetID widget ) { return false ; }
2008-05-10 15:46:36 +02:00
2010-07-11 13:00:09 +02:00
/**
2019-03-20 03:13:36 +01:00
* The mouse is hovering over a widget in the window , perform an action for it .
2010-07-11 13:00:09 +02:00
* @ param pt The point where the mouse is hovering .
* @ param widget The widget where the mouse is hovering .
*/
2023-12-29 20:11:59 +01:00
virtual void OnHover ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] WidgetID widget ) { }
2010-07-11 13:00:09 +02:00
2019-03-20 03:13:36 +01:00
/**
* Event to display a custom tooltip .
* @ param pt The point where the mouse is located .
* @ param widget The widget where the mouse is located .
* @ return True if the event is handled , false if it is ignored .
*/
2023-12-29 20:11:59 +01:00
virtual bool OnTooltip ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] WidgetID widget , [ [ maybe_unused ] ] TooltipCloseCondition close_cond ) { return false ; }
2019-03-20 03:13:36 +01:00
2010-05-23 16:53:39 +02:00
/**
* An ' object ' is being dragged at the provided position , highlight the target if possible .
* @ param pt The point inside the window that the mouse hovers over .
* @ param widget The widget the mouse hovers over .
*/
2023-12-29 20:11:59 +01:00
virtual void OnMouseDrag ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] WidgetID widget ) { }
2010-05-23 16:53:39 +02:00
2008-05-10 15:46:36 +02:00
/**
* A dragged ' object ' has been released .
* @ param pt the point inside the window where the release took place .
* @ param widget the widget where the release took place .
*/
2023-12-29 20:11:59 +01:00
virtual void OnDragDrop ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] WidgetID widget ) { }
2008-05-10 15:46:36 +02:00
/**
* Handle the request for ( viewport ) scrolling .
* @ param delta the amount the viewport must be scrolled .
*/
2023-09-16 22:20:53 +02:00
virtual void OnScroll ( [ [ maybe_unused ] ] Point delta ) { }
2008-05-10 15:46:36 +02:00
/**
* The mouse is currently moving over the window or has just moved outside
* of the window . In the latter case pt is ( - 1 , - 1 ) .
* @ param pt the point inside the window that the mouse hovers over .
* @ param widget the widget the mouse hovers over .
*/
2023-12-29 20:11:59 +01:00
virtual void OnMouseOver ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] WidgetID widget ) { }
2008-05-10 15:46:36 +02:00
/**
* The mouse wheel has been turned .
* @ param wheel the amount of movement of the mouse wheel .
*/
2023-09-16 22:20:53 +02:00
virtual void OnMouseWheel ( [ [ maybe_unused ] ] int wheel ) { }
2008-05-10 15:46:36 +02:00
/**
* Called for every mouse loop run , which is at least once per ( game ) tick .
*/
2008-05-19 11:48:47 +02:00
virtual void OnMouseLoop ( ) { }
2008-05-10 15:46:36 +02:00
/**
* Called once per ( game ) tick .
*/
2018-05-04 22:29:22 +02:00
virtual void OnGameTick ( ) { }
2008-05-10 15:46:36 +02:00
2018-05-04 22:29:22 +02:00
/**
* Called periodically .
*/
2023-09-16 22:20:53 +02:00
virtual void OnRealtimeTick ( [ [ maybe_unused ] ] uint delta_ms ) { }
2018-05-04 22:29:22 +02:00
2008-05-10 15:46:36 +02:00
/**
* Called when this window ' s timeout has been reached .
*/
2008-05-19 11:48:47 +02:00
virtual void OnTimeout ( ) { }
2008-05-10 15:46:36 +02:00
/**
2009-03-29 11:49:11 +02:00
* Called after the window got resized .
2009-07-26 19:29:01 +02:00
* For nested windows with a viewport , call NWidgetViewport : : UpdateViewportCoordinates .
2008-05-10 15:46:36 +02:00
*/
2009-10-24 16:53:55 +02:00
virtual void OnResize ( ) { }
2008-05-10 15:46:36 +02:00
/**
* A dropdown option associated to this window has been selected .
* @ param widget the widget ( button ) that the dropdown is associated with .
* @ param index the element in the dropdown that is selected .
*/
2023-12-29 20:11:59 +01:00
virtual void OnDropdownSelect ( [ [ maybe_unused ] ] WidgetID widget , [ [ maybe_unused ] ] int index ) { }
2008-05-10 15:46:36 +02:00
2023-12-29 20:11:59 +01:00
virtual void OnDropdownClose ( Point pt , WidgetID widget , int index , bool instant_close ) ;
2012-06-01 12:42:46 +02:00
2012-11-13 22:47:07 +01:00
/**
* The text in an editbox has been edited .
* @ param widget The widget of the editbox .
*/
2023-12-29 20:11:59 +01:00
virtual void OnEditboxChanged ( [ [ maybe_unused ] ] WidgetID widget ) { }
2012-11-13 22:47:07 +01:00
2008-05-10 15:46:36 +02:00
/**
* The query window opened from this window has closed .
2019-04-10 23:07:06 +02:00
* @ param str the new value of the string , nullptr if the window
2010-01-23 20:30:53 +01:00
* was cancelled or an empty string when the default
* button was pressed , i . e . StrEmpty ( str ) .
2008-05-10 15:46:36 +02:00
*/
2023-09-16 22:20:53 +02:00
virtual void OnQueryTextFinished ( [ [ maybe_unused ] ] char * str ) { }
2008-05-10 15:46:36 +02:00
/**
* Some data on this window has become invalid .
* @ param data information about the changed data .
2011-03-13 22:31:29 +01:00
* @ param gui_scope Whether the call is done from GUI scope . You may not do everything when not in GUI scope . See # InvalidateWindowData ( ) for details .
2008-05-10 15:46:36 +02:00
*/
2023-09-16 22:20:53 +02:00
virtual void OnInvalidateData ( [ [ maybe_unused ] ] int data = 0 , [ [ maybe_unused ] ] bool gui_scope = true ) { }
2008-05-10 15:46:36 +02:00
/**
* The user clicked some place on the map when a tile highlight mode
* has been set .
* @ param pt the exact point on the map that has been clicked .
* @ param tile the tile on the map that has been clicked .
*/
2023-09-16 22:20:53 +02:00
virtual void OnPlaceObject ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] TileIndex tile ) { }
2008-05-10 15:46:36 +02:00
2010-09-06 16:14:09 +02:00
/**
* The user clicked on a vehicle while HT_VEHICLE has been set .
2022-11-26 18:03:21 +01:00
* @ param v clicked vehicle
* @ return true if the click is handled , false if it is ignored
* @ pre v - > IsPrimaryVehicle ( ) = = true
2010-09-06 16:14:09 +02:00
*/
2023-09-16 22:20:53 +02:00
virtual bool OnVehicleSelect ( [ [ maybe_unused ] ] const struct Vehicle * v ) { return false ; }
2010-09-06 16:14:09 +02:00
2022-11-26 18:03:21 +01:00
/**
* The user clicked on a vehicle while HT_VEHICLE has been set .
* @ param v clicked vehicle
* @ return True if the click is handled , false if it is ignored
* @ pre v - > IsPrimaryVehicle ( ) = = true
*/
2023-09-16 22:20:53 +02:00
virtual bool OnVehicleSelect ( [ [ maybe_unused ] ] VehicleList : : const_iterator begin , [ [ maybe_unused ] ] VehicleList : : const_iterator end ) { return false ; }
2022-11-26 18:03:21 +01:00
2008-05-10 15:46:36 +02:00
/**
* The user cancelled a tile highlight mode that has been set .
*/
2008-05-19 11:48:47 +02:00
virtual void OnPlaceObjectAbort ( ) { }
2008-05-10 15:46:36 +02:00
/**
* The user is dragging over the map when the tile highlight mode
* has been set .
* @ param select_method the method of selection ( allowed directions )
* @ param select_proc what will be created when the drag is over .
* @ param pt the exact point on the map where the mouse is .
*/
2023-09-16 22:20:53 +02:00
virtual void OnPlaceDrag ( [ [ maybe_unused ] ] ViewportPlaceMethod select_method , [ [ maybe_unused ] ] ViewportDragDropSelectionProcess select_proc , [ [ maybe_unused ] ] Point pt ) { }
2008-05-10 15:46:36 +02:00
/**
* The user has dragged over the map when the tile highlight mode
* has been set .
* @ param select_method the method of selection ( allowed directions )
* @ param select_proc what should be created .
* @ param pt the exact point on the map where the mouse was released .
* @ param start_tile the begin tile of the drag .
* @ param end_tile the end tile of the drag .
*/
2023-09-16 22:20:53 +02:00
virtual void OnPlaceMouseUp ( [ [ maybe_unused ] ] ViewportPlaceMethod select_method , [ [ maybe_unused ] ] ViewportDragDropSelectionProcess select_proc , [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] TileIndex start_tile , [ [ maybe_unused ] ] TileIndex end_tile ) { }
2008-05-10 15:46:36 +02:00
/**
* The user moves over the map when a tile highlight mode has been set
* when the special mouse mode has been set to ' PRESIZE ' mode . An
* example of this is the tile highlight for dock building .
* @ param pt the exact point on the map where the mouse is .
* @ param tile the tile on the map where the mouse is .
*/
2023-09-16 22:20:53 +02:00
virtual void OnPlacePresize ( [ [ maybe_unused ] ] Point pt , [ [ maybe_unused ] ] TileIndex tile ) { }
2008-05-10 15:46:36 +02:00
/*** End of the event handling ***/
2010-04-24 15:27:22 +02:00
/**
* Is the data related to this window NewGRF inspectable ?
* @ return true iff it is inspectable .
*/
virtual bool IsNewGRFInspectable ( ) const { return false ; }
/**
* Show the NewGRF inspection window . When this function is called it is
* up to the window to call and pass the right parameters to the
* ShowInspectWindow function .
* @ pre this - > IsNewGRFInspectable ( )
*/
virtual void ShowNewGRFInspectWindow ( ) const { NOT_REACHED ( ) ; }
2021-04-28 21:24:24 +02:00
/**
* Iterator to iterate all valid Windows
2021-05-09 17:12:34 +02:00
* @ tparam TtoBack whether we iterate towards the back .
2021-04-28 21:24:24 +02:00
*/
2021-05-09 17:12:34 +02:00
template < bool TtoBack >
2021-04-28 21:24:24 +02:00
struct WindowIterator {
2021-05-09 18:35:49 +02:00
typedef Window * value_type ;
typedef value_type * pointer ;
typedef value_type & reference ;
2021-04-28 21:24:24 +02:00
typedef size_t difference_type ;
typedef std : : forward_iterator_tag iterator_category ;
2021-05-09 17:12:34 +02:00
explicit WindowIterator ( WindowList : : iterator start ) : it ( start )
2021-04-28 21:24:24 +02:00
{
this - > Validate ( ) ;
}
2021-05-09 17:12:34 +02:00
explicit WindowIterator ( const Window * w ) : it ( w - > z_position ) { }
2021-04-28 21:24:24 +02:00
2021-05-09 17:12:34 +02:00
bool operator = = ( const WindowIterator & other ) const { return this - > it = = other . it ; }
2021-04-28 21:24:24 +02:00
bool operator ! = ( const WindowIterator & other ) const { return ! ( * this = = other ) ; }
2021-05-09 17:12:34 +02:00
Window * operator * ( ) const { return * this - > it ; }
2021-04-28 21:24:24 +02:00
WindowIterator & operator + + ( ) { this - > Next ( ) ; this - > Validate ( ) ; return * this ; }
2021-05-09 17:12:34 +02:00
bool IsEnd ( ) const { return this - > it = = _z_windows . end ( ) ; }
2021-05-09 16:42:36 +02:00
2021-04-28 21:24:24 +02:00
private :
2021-05-09 17:12:34 +02:00
WindowList : : iterator it ;
void Validate ( )
{
while ( ! this - > IsEnd ( ) & & * this - > it = = nullptr ) this - > Next ( ) ;
}
void Next ( )
{
if constexpr ( ! TtoBack ) {
+ + this - > it ;
} else if ( this - > it = = _z_windows . begin ( ) ) {
this - > it = _z_windows . end ( ) ;
} else {
- - this - > it ;
}
}
2021-04-28 21:24:24 +02:00
} ;
2021-05-09 16:42:36 +02:00
using IteratorToFront = WindowIterator < false > ; //!< Iterate in Z order towards front.
using IteratorToBack = WindowIterator < true > ; //!< Iterate in Z order towards back.
2021-04-28 21:24:24 +02:00
/**
* Iterable ensemble of all valid Windows
* @ tparam Tfront Wether we iterate from front
*/
2021-05-09 18:35:49 +02:00
template < bool Tfront >
2021-05-09 16:42:36 +02:00
struct AllWindows {
AllWindows ( ) { }
2021-05-09 17:12:34 +02:00
WindowIterator < Tfront > begin ( )
{
if constexpr ( Tfront ) {
auto back = _z_windows . end ( ) ;
if ( back ! = _z_windows . begin ( ) ) - - back ;
return WindowIterator < Tfront > ( back ) ;
} else {
return WindowIterator < Tfront > ( _z_windows . begin ( ) ) ;
}
}
WindowIterator < Tfront > end ( ) { return WindowIterator < Tfront > ( _z_windows . end ( ) ) ; }
2021-04-28 21:24:24 +02:00
} ;
2021-05-09 17:10:07 +02:00
using Iterate = AllWindows < false > ; //!< Iterate all windows in whatever order is easiest.
2021-05-09 16:42:36 +02:00
using IterateFromBack = AllWindows < false > ; //!< Iterate all windows in Z order from back to front.
using IterateFromFront = AllWindows < true > ; //!< Iterate all windows in Z order from front to back.
2004-08-09 19:04:08 +02:00
} ;
2022-11-26 18:03:21 +01:00
/**
* Generic helper function that checks if all elements of the range are equal with respect to the given predicate .
* @ param begin The start of the range .
* @ param end The end of the range .
* @ param pred The predicate to use .
* @ return True if all elements are equal , false otherwise .
*/
template < class It , class Pred >
inline bool AllEqual ( It begin , It end , Pred pred )
{
return std : : adjacent_find ( begin , end , std : : not_fn ( pred ) ) = = end ;
}
2010-08-01 21:22:34 +02:00
/**
* Get the nested widget with number \ a widnum from the nested widget tree .
2009-09-19 13:31:12 +02:00
* @ tparam NWID Type of the nested widget .
* @ param widnum Widget number of the widget to retrieve .
2019-04-10 23:07:06 +02:00
* @ return The requested widget if it is instantiated , \ c nullptr otherwise .
2009-09-19 13:31:12 +02:00
*/
template < class NWID >
2023-12-29 20:11:59 +01:00
inline NWID * Window : : GetWidget ( WidgetID widnum )
2009-09-19 13:31:12 +02:00
{
2023-10-16 12:13:36 +02:00
auto it = this - > widget_lookup . find ( widnum ) ;
if ( it = = std : : end ( this - > widget_lookup ) ) return nullptr ;
NWID * nwid = dynamic_cast < NWID * > ( it - > second ) ;
2019-04-10 23:07:06 +02:00
assert ( nwid ! = nullptr ) ;
2009-09-19 13:31:12 +02:00
return nwid ;
}
/** Specialized case of #Window::GetWidget for the nested widget base class. */
template < >
2023-12-29 20:11:59 +01:00
inline const NWidgetBase * Window : : GetWidget < NWidgetBase > ( WidgetID widnum ) const
2009-09-19 13:31:12 +02:00
{
2023-10-16 12:13:36 +02:00
auto it = this - > widget_lookup . find ( widnum ) ;
if ( it = = std : : end ( this - > widget_lookup ) ) return nullptr ;
return it - > second ;
2009-09-19 13:31:12 +02:00
}
2010-08-01 21:22:34 +02:00
/**
* Get the nested widget with number \ a widnum from the nested widget tree .
2009-10-30 08:51:33 +01:00
* @ tparam NWID Type of the nested widget .
* @ param widnum Widget number of the widget to retrieve .
2019-04-10 23:07:06 +02:00
* @ return The requested widget if it is instantiated , \ c nullptr otherwise .
2009-10-30 08:51:33 +01:00
*/
template < class NWID >
2023-12-29 20:11:59 +01:00
inline const NWID * Window : : GetWidget ( WidgetID widnum ) const
2009-10-30 08:51:33 +01:00
{
return const_cast < Window * > ( this ) - > GetWidget < NWID > ( widnum ) ;
}
2009-09-19 13:31:12 +02:00
2008-05-17 05:29:16 +02:00
/**
2009-07-20 21:44:28 +02:00
* Base class for windows opened from a toolbar .
2008-05-17 05:29:16 +02:00
*/
class PickerWindowBase : public Window {
public :
2013-05-26 21:23:42 +02:00
PickerWindowBase ( WindowDesc * desc , Window * parent ) : Window ( desc )
2009-07-20 21:44:28 +02:00
{
this - > parent = parent ;
2011-01-15 16:36:58 +01:00
}
2009-07-20 21:44:28 +02:00
2023-10-13 13:59:15 +02:00
void Close ( [ [ maybe_unused ] ] int data = 0 ) override ;
2008-05-17 05:29:16 +02:00
} ;
2004-08-09 19:04:08 +02:00
Window * BringWindowToFrontById ( WindowClass cls , WindowNumber number ) ;
Window * FindWindowFromPt ( int x , int y ) ;
2023-08-15 18:12:05 +02:00
template < typename T , std : : enable_if_t < std : : is_base_of < StrongTypedefBase , T > : : value , int > = 0 >
Window * BringWindowToFrontById ( WindowClass cls , T number )
{
2023-11-06 21:29:35 +01:00
return BringWindowToFrontById ( cls , number . base ( ) ) ;
2023-08-15 18:12:05 +02:00
}
2008-05-08 13:50:34 +02:00
/**
* Open a new window .
2014-12-18 17:50:11 +01:00
* @ tparam Wcls % Window class to use if the window does not exist .
2008-10-14 21:27:08 +02:00
* @ param desc The pointer to the WindowDesc to be created
2008-05-08 13:50:34 +02:00
* @ param window_number the window number of the new window
2014-12-18 19:20:59 +01:00
* @ param return_existing If set , also return the window if it already existed .
2019-04-10 23:07:06 +02:00
* @ return % Window pointer of the newly created window , or the existing one if \ a return_existing is set , or \ c nullptr .
2008-05-08 13:50:34 +02:00
*/
template < typename Wcls >
2014-12-18 19:20:59 +01:00
Wcls * AllocateWindowDescFront ( WindowDesc * desc , int window_number , bool return_existing = false )
2008-05-08 13:50:34 +02:00
{
2014-12-18 19:20:59 +01:00
Wcls * w = static_cast < Wcls * > ( BringWindowToFrontById ( desc - > cls , window_number ) ) ;
2019-04-10 23:07:06 +02:00
if ( w ! = nullptr ) return return_existing ? w : nullptr ;
2008-05-13 16:43:33 +02:00
return new Wcls ( desc , window_number ) ;
2008-05-08 13:50:34 +02:00
}
2004-08-09 19:04:08 +02:00
void RelocateAllWindows ( int neww , int newh ) ;
2023-06-17 08:46:59 +02:00
void GuiShowTooltips ( Window * parent , StringID str , TooltipCloseCondition close_tooltip , uint paramcount = 0 ) ;
2006-10-03 22:16:20 +02:00
2007-02-23 02:48:53 +01:00
/* widget.cpp */
2023-12-29 20:11:59 +01:00
WidgetID GetWidgetFromPos ( const Window * w , int x , int y ) ;
2004-08-09 19:04:08 +02:00
2008-01-13 14:36:01 +01:00
extern Point _cursorpos_drag_start ;
2004-08-09 19:04:08 +02:00
2008-01-13 14:36:01 +01:00
extern int _scrollbar_start_pos ;
extern int _scrollbar_size ;
2024-03-16 23:59:32 +01:00
extern uint8_t _scroller_click_timeout ;
2004-08-09 19:04:08 +02:00
2008-01-13 14:36:01 +01:00
extern bool _scrolling_viewport ;
2010-07-11 12:53:07 +02:00
extern bool _mouse_hovering ;
2004-08-09 19:04:08 +02:00
2010-05-30 12:36:32 +02:00
/** Mouse modes. */
2004-08-09 19:04:08 +02:00
enum SpecialMouseMode {
2010-05-30 12:36:32 +02:00
WSM_NONE , ///< No special mouse mode.
2020-06-26 21:30:18 +02:00
WSM_DRAGDROP , ///< Drag&drop an object.
2010-05-30 12:36:32 +02:00
WSM_SIZING , ///< Sizing mode.
WSM_PRESIZE , ///< Presizing mode (docks, tunnels).
2020-06-26 21:30:18 +02:00
WSM_DRAGGING , ///< Dragging mode (trees).
2004-08-09 19:04:08 +02:00
} ;
2010-05-30 12:36:32 +02:00
extern SpecialMouseMode _special_mouse_mode ;
2004-08-09 19:04:08 +02:00
2009-02-09 02:22:29 +01:00
void SetFocusedWindow ( Window * w ) ;
2010-08-12 11:09:24 +02:00
void ScrollbarClickHandler ( Window * w , NWidgetCore * nw , int x , int y ) ;
2004-08-09 19:04:08 +02:00
2007-12-19 20:44:29 +01:00
# endif /* WINDOW_GUI_H */