Skip to content

Commit

Permalink
GUI2/Window Builder: added function to generate a single widget insta…
Browse files Browse the repository at this point in the history
…nce with its builder

This will be used in some upcoming changes. The main benefit of this over directly initializing a new widget
object is any extra builder steps can also be executed.

I'm not entirely happy with the design, though, especially with having to specify both the type and type ID...
  • Loading branch information
Vultraz committed Aug 25, 2017
1 parent da28824 commit d78158d
Show file tree
Hide file tree
Showing 2 changed files with 34 additions and 1 deletion.
9 changes: 9 additions & 0 deletions src/gui/core/window_builder.cpp
Expand Up @@ -219,6 +219,15 @@ builder_widget_ptr create_builder_widget(const config& cfg)
FAIL("Unknown widget type " + cfg.ordered_begin()->key);
}

widget* build_single_widget_instance_helper(const std::string& type, const config& cfg)
{
const auto& iter = builder_widget_lookup().find(type);
VALIDATE(iter != builder_widget_lookup().end(), "Invalid widget type '" + type + "'");

widget_builder_func_t& builder = iter->second;
return builder(cfg)->build();
}

/*WIKI
* @page = GUIToolkitWML
* @order = 1_window
Expand Down
26 changes: 25 additions & 1 deletion src/gui/core/window_builder.hpp
Expand Up @@ -87,7 +87,6 @@ using widget_builder_func_t = std::function<builder_widget_ptr(config)>;
void
register_builder_widget(const std::string& id, widget_builder_func_t functor);


/**
* Create a widget builder.
*
Expand Down Expand Up @@ -116,6 +115,31 @@ builder_widget_ptr build_widget(const config& cfg)
return std::make_shared<T>(cfg);
}

/**
* Helper function to implement @ref build_single_widget_instance. This keeps the main
* logic in the implementation despite said function being a template and therefor
* needing to be fully implemented in the declaration.
*/
widget* build_single_widget_instance_helper(const std::string& type, const config& cfg);

/**
* Builds a single widget instance of the given type with the specified attributes.
*
* This should be used in place of creating a widget object directly, as it
* allows the widget-specific builder code to be executed.
*
* @tparam The final widget type. The widget pointer will be
* cast to this.
*
* @param type String ID of the widget type.
* @param cfg Data config to pass to the widget's builder.
*/
template<typename T>
T* build_single_widget_instance(const std::string& type, const config& cfg = config())
{
return dynamic_cast<T*>(build_single_widget_instance_helper(type, cfg));
}

struct builder_grid : public builder_widget
{
public:
Expand Down

0 comments on commit d78158d

Please sign in to comment.