The Battle for Wesnoth  1.15.2+dev
size_lock.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2016 - 2018 Jyrki Vesterinen <sandgtx@gmail.com>
3  Part of the Battle for Wesnoth Project https://www.wesnoth.org/
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2 of the License, or
8  (at your option) any later version.
9  This program is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY.
11 
12  See the COPYING file for more details.
13 */
14 
15 #define GETTEXT_DOMAIN "wesnoth-lib"
16 
17 #include "size_lock.hpp"
18 
19 #include <gettext.hpp>
22 #include <gui/widgets/helper.hpp>
23 #include <gui/widgets/settings.hpp>
24 #include <wml_exception.hpp>
25 
26 namespace gui2
27 {
28 REGISTER_WIDGET(size_lock)
29 
30 size_lock::size_lock(const implementation::builder_size_lock& builder)
31  : container_base(builder, type())
32  , width_(builder.width_)
33  , height_(builder.height_)
34  , widget_(nullptr)
35 {
36 }
37 
38 void size_lock::place(const point& origin, const point& size)
39 {
40  point content_size = widget_->get_best_size();
41 
42  if(content_size.x > size.x) {
43  reduce_width(size.x);
44  content_size = widget_->get_best_size();
45  }
46 
47  if(content_size.y > size.y) {
48  try {
49  reduce_height(size.y);
50  } catch(const layout_exception_width_modified&) {
51  }
52 
53  content_size = widget_->get_best_size();
54  }
55 
56  if(content_size.x > size.x) {
57  reduce_width(size.x);
58  content_size = widget_->get_best_size();
59  }
60 
61  container_base::place(origin, size);
62 }
63 
65 {
66  assert(widget_ != nullptr);
67 
69 }
70 
72 {
73  set_rows_cols(1u, 1u);
74 
75  widget_ = widget_builder->build();
77 }
78 
80 {
82 
83  unsigned width = width_(size);
84  unsigned height = height_(size);
85 
86  VALIDATE(width > 0 || height > 0, _("Invalid size."));
87 
88  return point(width, height);
89 }
90 
93 {
94  DBG_GUI_P << "Parsing fixed size widget " << id << '\n';
95 
96  load_resolutions<resolution>(cfg);
97 }
98 
99 /*WIKI
100  * @page = GUIWidgetDefinitionWML
101  * @order = 1_size_lock
102  *
103  * == Size lock ==
104  *
105  * A size lock contains one child widget and forces it to have the specified size.
106  * This can be used, for example, when there are two list boxes in different rows of
107  * the same grid and it's desired that only one list box changes size when its
108  * contents change.
109  *
110  * A size lock has no states.
111  * @begin{parent}{name="gui/"}
112  * @begin{tag}{name="size_lock_definition"}{min=0}{max=-1}{super="generic/widget_definition"}
113  * @end{tag}{name="size_lock_definition"}
114  * @end{tag}{name="gui/"}
115  */
117  : resolution_definition(cfg)
118  , grid(nullptr)
119 {
120  // Add a dummy state since every widget needs a state.
121  static config dummy("draw");
122  state.emplace_back(dummy);
123 
124  const config& child = cfg.child("grid");
125  VALIDATE(child, _("No grid defined."));
126 
127  grid = std::make_shared<builder_grid>(child);
128 }
129 
130 /*WIKI
131  * @page = GUIWidgetInstanceWML
132  * @order = 2_size_lock
133  * @begin{parent}{name="gui/window/resolution/grid/row/column/"}
134  * @begin{tag}{name="size_lock"}{min=0}{max=-1}{super="generic/widget_instance"}
135  * == Size lock ==
136  *
137  * A size lock contains one child widget and forces it to have the specified size.
138  * This can be used, for example, when there are two list boxes in different rows of
139  * the same grid and it's desired that only one list box changes size when its
140  * contents change.
141  *
142  * @begin{table}{config}
143  * widget & section & mandatory & The widget. $
144  * width & f_unsigned & mandatory & The width of the widget. $
145  * height & f_unsigned & mandatory & The height of the widget. $
146  * @end{table}
147  *
148  * The variables available are the same as for window resolution, see
149  * [[GuiToolkitWML#Resolution_2]] for the list of items.
150  * @end{tag}{name="size_lock"}
151  * @end{parent}{name="gui/window/resolution/grid/row/column/"}
152  */
153 
154 namespace implementation
155 {
156 builder_size_lock::builder_size_lock(const config& cfg)
157  : builder_styled_widget(cfg)
158  , width_(cfg["width"])
159  , height_(cfg["height"])
160  , content_(nullptr)
161 {
162  VALIDATE(cfg.has_child("widget"), _("No widget defined."));
163  content_ = create_widget_builder(cfg.child("widget"));
164 }
165 
167 {
168  size_lock* widget = new size_lock(*this);
169 
170  DBG_GUI_G << "Window builder: placed fixed size widget '" << id << "' with definition '" << definition << "'.\n";
171 
172  const auto conf = widget->cast_config_to<size_lock_definition>();
173  assert(conf != nullptr);
174 
175  widget->init_grid(conf->grid);
176  widget->finalize(content_);
177 
178  return widget;
179 }
180 }
181 }
Base class of a resolution, contains the common keys for a resolution.
#define DBG_GUI_P
Definition: log.hpp:68
Defines the exception classes for the layout algorithm.
config & child(config_key_type key, int n=0)
Returns the nth child with the given key, or a reference to an invalid config if there is none...
Definition: config.cpp:420
void reduce_width(const unsigned maximum_width)
Tries to reduce the width of a container.
std::vector< state_definition > state
size_lock_definition(const config &cfg)
Definition: size_lock.cpp:91
int dummy
Definition: lstrlib.cpp:1125
virtual void place(const point &origin, const point &size) override
See widget::place.
Add a special kind of assert to validate whether the input from WML doesn&#39;t contain any problems that...
bool has_child(config_key_type key) const
Determine whether a config has a child or not.
Definition: config.cpp:412
Base class for all widgets.
Definition: widget.hpp:47
typed_formula< unsigned > height_
Definition: size_lock.hpp:64
void get_screen_size_variables(wfl::map_formula_callable &variable)
Gets a formula object with the screen size.
Definition: helper.cpp:99
int x
x coordinate.
Definition: point.hpp:44
Generic file dialog.
Definition: field-fwd.hpp:22
void set_child(widget *widget, const unsigned row, const unsigned col, const unsigned flags, const unsigned border_size)
Base container class.
Definition: grid.hpp:30
static UNUSEDNOWARN std::string _(const char *str)
Definition: gettext.hpp:91
std::string definition
Parameters for the styled_widget.
std::shared_ptr< const builder_widget > builder_widget_const_ptr
void reduce_height(const unsigned maximum_height)
Tries to reduce the height of a container.
std::size_t size(const std::string &str)
Length in characters of a UTF-8 string.
Definition: unicode.cpp:86
Exception thrown when the width has been modified during resizing.
point get_best_size() const
Gets the best size for the widget.
Definition: widget.cpp:190
#define VALIDATE(cond, message)
The macro to use for the validation of WML.
This file contains the settings handling of the widget library.
typed_formula< unsigned > width_
Definition: size_lock.hpp:63
void init_grid(const std::shared_ptr< builder_grid > &grid_builder)
Initializes and builds the grid.
#define REGISTER_WIDGET(id)
Wrapper for REGISTER_WIDGET3.
std::shared_ptr< const typename T::resolution > cast_config_to() const
Casts the current resolution definition config to the respective type of a derived widget...
void layout_children() override
See widget::layout_children.
Definition: size_lock.cpp:64
Holds a 2D point.
Definition: point.hpp:23
virtual void layout_children()
Allows a widget to update its children.
Definition: widget.cpp:292
static const unsigned HORIZONTAL_GROW_SEND_TO_CLIENT
Definition: grid.hpp:55
static const unsigned VERTICAL_GROW_SEND_TO_CLIENT
Definition: grid.hpp:48
point calculate_best_size() const override
See widget::calculate_best_size.
Definition: size_lock.cpp:79
A generic container base class.
builder_widget_const_ptr content_
Definition: size_lock.hpp:123
void finalize(builder_widget_const_ptr widget_builder)
Finishes the building initialization of the widget.
Definition: size_lock.cpp:71
void set_rows_cols(const unsigned rows, const unsigned cols)
void place(const point &origin, const point &size) override
See widget::place.
Definition: size_lock.cpp:38
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:68
int y
y coordinate.
Definition: point.hpp:47
#define DBG_GUI_G
Definition: log.hpp:40
Contains the implementation details for lexical_cast and shouldn&#39;t be used directly.
widget * widget_
Points to the actual widget.
Definition: size_lock.hpp:71
builder_widget_ptr create_widget_builder(const config &cfg)
Create a widget builder.