From d7b564e2a71bf473a666f184302273ec23be2856 Mon Sep 17 00:00:00 2001 From: Charles Dang Date: Sat, 8 Apr 2017 14:32:27 +1100 Subject: [PATCH] GUI2/Widget: added ability to set widget alignment on the fly --- src/gui/widgets/grid.cpp | 33 +++++++++++++++++++++++++++++++-- src/gui/widgets/grid.hpp | 10 ++++++++++ src/gui/widgets/widget.cpp | 27 +++++++++++++++++++++++++++ src/gui/widgets/widget.hpp | 22 ++++++++++++++++++---- 4 files changed, 86 insertions(+), 6 deletions(-) diff --git a/src/gui/widgets/grid.cpp b/src/gui/widgets/grid.cpp index ae04e443ad2f..fc34db5cf10e 100644 --- a/src/gui/widgets/grid.cpp +++ b/src/gui/widgets/grid.cpp @@ -17,6 +17,7 @@ #include "gui/widgets/grid_private.hpp" #include "gui/auxiliary/iterator/walker_grid.hpp" +#include "gui/core/event/message.hpp" #include "gui/core/log.hpp" #include "gui/core/layout_exception.hpp" #include "gui/widgets/styled_widget.hpp" @@ -232,7 +233,7 @@ void grid::reduce_width(const unsigned maximum_width) /** @todo Implement. */ - /***** ***** ***** ***** Acknowlegde failure ***** ***** ***** *****/ + /***** ***** ***** ***** Acknowledge failure ***** ***** ***** *****/ DBG_GUI_L << LOG_HEADER << " Resizing failed.\n"; @@ -310,7 +311,7 @@ void grid::reduce_height(const unsigned maximum_height) /** @todo Implement. */ - /***** ***** ***** ***** Acknowlegde failure ***** ***** ***** *****/ + /***** ***** ***** ***** Acknowledge failure ***** ***** ***** *****/ DBG_GUI_L << LOG_HEADER << " Resizing failed.\n"; @@ -946,6 +947,34 @@ grid::child* grid::get_child(widget* w) return nullptr; } +void grid::set_child_alignment(widget* widget, unsigned set_flag, unsigned mode_mask) +{ + grid::child* cell = get_child(widget); + if(!cell) { + return; + } + + unsigned flags = cell->get_flags(); + + if((flags & mode_mask) == HORIZONTAL_GROW_SEND_TO_CLIENT) { + ERR_GUI_G << "Cannot set horizontal alignment (grid cell specifies dynamic growth)" << std::endl; + return; + } + + if((flags & mode_mask) == VERTICAL_GROW_SEND_TO_CLIENT) { + ERR_GUI_G << "Cannot set vertical alignment (grid cell specifies dynamic growth)" << std::endl; + return; + } + + flags &= ~mode_mask; + flags |= set_flag; + + cell->set_flags(flags); + + event::message message; + fire(event::REQUEST_PLACEMENT, *this, message); +} + void grid::layout(const point& origin) { point orig = origin; diff --git a/src/gui/widgets/grid.hpp b/src/gui/widgets/grid.hpp index ac923f355e93..86df674636e2 100644 --- a/src/gui/widgets/grid.hpp +++ b/src/gui/widgets/grid.hpp @@ -227,6 +227,16 @@ class grid : public widget */ point recalculate_best_size(); + /** + * Modifies the widget alignment data of a child cell containing a specific widget. + * + * @param widget The widget whose cell to modify. + * @param set_flag The alignment flag to set. + * @param mask Whether to affect horizontal or vertical alignment. + * Use either HORIZONTAL_MASK or VERTICAL_MASK + */ + void set_child_alignment(widget* widget, unsigned set_flag, unsigned mode_mask); + private: /** See @ref widget::calculate_best_size. */ virtual point calculate_best_size() const override; diff --git a/src/gui/widgets/widget.cpp b/src/gui/widgets/widget.cpp index 65faa231d4aa..1ea2a721bdf0 100644 --- a/src/gui/widgets/widget.cpp +++ b/src/gui/widgets/widget.cpp @@ -19,6 +19,7 @@ #include "gui/widgets/window.hpp" #include "gui/core/event/message.hpp" #include "gui/core/log.hpp" +#include "gui/core/window_builder/helper.hpp" #include "sdl/rect.hpp" namespace gui2 @@ -268,6 +269,32 @@ void widget::move(const int x_offset, const int y_offset) y_ += y_offset; } +void widget::set_horizontal_alignment(const std::string& alignment) +{ + grid* parent_grid = get_parent_grid(); + if(!parent_grid) { + return; + } + + parent_grid->set_child_alignment(this, implementation::get_h_align(alignment), grid::HORIZONTAL_MASK); + + // TODO: evaluate necessity + //get_window()->invalidate_layout(); +} + +void widget::set_vertical_alignment(const std::string& alignment) +{ + grid* parent_grid = get_parent_grid(); + if(!parent_grid) { + return; + } + + parent_grid->set_child_alignment(this, implementation::get_v_align(alignment), grid::VERTICAL_MASK); + + // TODO: evaluate necessity + //get_window()->invalidate_layout(); +} + void widget::layout_children() { /* DO NOTHING */ diff --git a/src/gui/widgets/widget.hpp b/src/gui/widgets/widget.hpp index 7f3f2e040ee5..92362b520c3b 100644 --- a/src/gui/widgets/widget.hpp +++ b/src/gui/widgets/widget.hpp @@ -181,6 +181,9 @@ class widget : public event_executor, public event::dispatcher */ window* get_window(); + /** The constant version of @ref get_window. */ + const window* get_window() const; + /** * Get the parent grid. * @@ -189,9 +192,6 @@ class widget : public event_executor, public event::dispatcher */ grid* get_parent_grid(); - /** The constant version of @ref get_window. */ - const window* get_window() const; - /** * Returns the top-level dialog. * @@ -203,7 +203,7 @@ class widget : public event_executor, public event::dispatcher * function will be removed. * * @returns The top-level dialog. - * @retval nullptr No top-level window or the top-level window is + * @retval nullptr No top-level window or the top-level window is * not owned by a dialog. */ dialogs::modal_dialog* dialog(); @@ -401,6 +401,20 @@ class widget : public event_executor, public event::dispatcher */ virtual void move(const int x_offset, const int y_offset); + /** + * Sets the horizontal alignment of the widget within its parent grid. + * + * @param alignment The new alignment. + */ + virtual void set_horizontal_alignment(const std::string& alignment); + + /** + * Sets the horizontal alignment of the widget within its parent grid. + * + * @param alignment The new alignment. + */ + virtual void set_vertical_alignment(const std::string& alignment); + /** * Allows a widget to update its children. *