From e04b0749e0fec9ecefce308c4dd2ca0dc9509b0c Mon Sep 17 00:00:00 2001 From: Jinhao Date: Mon, 25 May 2015 01:19:35 +0800 Subject: [PATCH] remove the internal signal manager of window_manager --- include/nana/gui/detail/basic_window.hpp | 11 +- include/nana/gui/detail/inner_fwd.hpp | 33 +----- .../nana/gui/detail/inner_fwd_implement.hpp | 28 ----- include/nana/gui/detail/window_manager.hpp | 31 +---- include/nana/gui/programming_interface.hpp | 7 -- include/nana/gui/widgets/widget.hpp | 112 ++++++------------ source/gui/detail/basic_window.cpp | 4 +- source/gui/detail/bedrock_pi.cpp | 12 ++ source/gui/detail/linux_X11/bedrock.cpp | 15 --- source/gui/detail/win32/bedrock.cpp | 41 ++----- source/gui/detail/window_manager.cpp | 55 +++------ source/gui/programming_interface.cpp | 8 +- source/gui/widgets/widget.cpp | 50 +++++++- 13 files changed, 132 insertions(+), 275 deletions(-) diff --git a/include/nana/gui/detail/basic_window.hpp b/include/nana/gui/detail/basic_window.hpp index b0a5bfe7..ef4d5038 100644 --- a/include/nana/gui/detail/basic_window.hpp +++ b/include/nana/gui/detail/basic_window.hpp @@ -15,13 +15,12 @@ #include "drawer.hpp" #include "events_holder.hpp" #include "widget_colors.hpp" +#include "widget_notifier_interface.hpp" #include #include #include -#include namespace nana{ - class widget; //declaration of nana/widgets/widget.hpp namespace detail { struct basic_window; @@ -89,11 +88,11 @@ namespace detail //basic_window //@brief: constructor for the root window - basic_window(basic_window* owner, widget*, category::root_tag**); + basic_window(basic_window* owner, std::unique_ptr&&, category::root_tag**); template - basic_window(basic_window* parent, const rectangle& r, widget* wdg, Category**) - : widget_ptr(wdg), other(Category::value) + basic_window(basic_window* parent, std::unique_ptr&& wdg_notifier, const rectangle& r, Category**) + : widget_notifier(std::move(wdg_notifier)), other(Category::value) { drawer.bind(this); if(parent) @@ -146,7 +145,7 @@ namespace detail basic_window* root_widget; //A pointer refers to the root basic window, if the window is a root, the pointer refers to itself. paint::graphics* root_graph; //Refer to the root buffer graphics cursor predef_cursor; - widget* const widget_ptr; + std::unique_ptr widget_notifier; struct flags_type { diff --git a/include/nana/gui/detail/inner_fwd.hpp b/include/nana/gui/detail/inner_fwd.hpp index 00a1f24e..ffe18a52 100644 --- a/include/nana/gui/detail/inner_fwd.hpp +++ b/include/nana/gui/detail/inner_fwd.hpp @@ -1,7 +1,7 @@ /* * Inner Forward Declaration * Nana C++ Library(http://www.nanapro.org) -* Copyright(C) 2003-2014 Jinhao(cnjinhao@hotmail.com) +* Copyright(C) 2003-2015 Jinhao(cnjinhao@hotmail.com) * * Distributed under the Boost Software License, Version 1.0. * (See accompanying file LICENSE_1_0.txt or copy at @@ -19,37 +19,6 @@ namespace nana{ namespace detail { - struct signals - { - enum class code - { - caption, - read_caption, - destroy, - size, - end - }; - - union - { - const nana::char_t* caption; - nana::string * str; - struct - { - unsigned width; - unsigned height; - }size; - }info; - }; - - class signal_invoker_interface - { - public: - virtual ~signal_invoker_interface() - {} - - virtual void call_signal(signals::code, const signals&) = 0; - }; } } #endif //NANA_GUI_INNER_FWD_HPP diff --git a/include/nana/gui/detail/inner_fwd_implement.hpp b/include/nana/gui/detail/inner_fwd_implement.hpp index 5384aec4..30de2c71 100644 --- a/include/nana/gui/detail/inner_fwd_implement.hpp +++ b/include/nana/gui/detail/inner_fwd_implement.hpp @@ -170,34 +170,6 @@ namespace nana{ std::map table_; }; - - - class signal_manager - { - typedef basic_window core_window_t; - public: - void make(core_window_t* wd, signal_invoker_interface* si) - { - if (si) - table_[wd].reset(si); - else - table_.erase(wd); - } - - void umake(core_window_t * wd) - { - table_.erase(wd); - } - - void call_signal(core_window_t * wd, signals::code code, const signals& s) - { - auto i = table_.find(wd); - if (i != table_.end()) - i->second->call_signal(code, s); - } - private: - std::map> table_; - }; } }//end namespace nana #endif //NANA_GUI_INNER_FWD_IMPLEMENT_HPP diff --git a/include/nana/gui/detail/window_manager.hpp b/include/nana/gui/detail/window_manager.hpp index 37c9c150..c86dd821 100644 --- a/include/nana/gui/detail/window_manager.hpp +++ b/include/nana/gui/detail/window_manager.hpp @@ -42,24 +42,7 @@ namespace nana namespace nana{ namespace detail { - template - class signal_invoker_mf - : public signal_invoker_interface - { - public: - signal_invoker_mf(T& obj, void(T::*mf)(signals::code, const signals&)) - : obj_(obj), - mf_(mf) - {} - - void call_signal(signals::code code, const signals& s) override - { - (obj_.*mf_)(code, s); - } - private: - T& obj_; - void(T::*mf_)(signals::code, const signals&); - }; + class widget_notifier_interface; //forward declaration struct root_misc; @@ -103,14 +86,6 @@ namespace detail mutex_type & internal_lock() const; void all_handles(std::vector&) const; - template - void attach_signal(core_window_t* wd, T& obj, void(Concept::*mf)(signals::code, const signals&)) - { - return _m_attach_signal(wd, new signal_invoker_mf(obj, mf)); - } - - void signal_fire_caption(core_window_t*, const nana::char_t*); - nana::string signal_fire_caption(core_window_t*); void event_filter(core_window_t*, bool is_make, event_code); void default_icon(const nana::paint::image&); @@ -121,6 +96,7 @@ namespace detail core_window_t* create_root(core_window_t*, bool nested, rectangle, const appearance&, widget*); core_window_t* create_widget(core_window_t*, const rectangle&, bool is_lite, widget*); core_window_t* create_frame(core_window_t*, const rectangle&, widget*); + bool insert_frame(core_window_t* frame, native_window); bool insert_frame(core_window_t* frame, core_window_t*); void close(core_window_t*); @@ -188,7 +164,6 @@ namespace detail core_window_t* find_shortkey(native_window_type, unsigned long key); private: - void _m_attach_signal(core_window_t*, signal_invoker_interface*); void _m_disengage(core_window_t*, core_window_t* for_new); void _m_destroy(core_window_t*); void _m_move_core(core_window_t*, const point& delta); @@ -200,8 +175,6 @@ namespace detail struct wdm_private_impl; wdm_private_impl * const impl_; - signals signals_; - struct attribute { struct captured diff --git a/include/nana/gui/programming_interface.hpp b/include/nana/gui/programming_interface.hpp index 57765e76..5606def9 100644 --- a/include/nana/gui/programming_interface.hpp +++ b/include/nana/gui/programming_interface.hpp @@ -48,13 +48,6 @@ namespace API //@brief: The interfaces defined in namespace dev are used for developing the nana.gui namespace dev { - template - void attach_signal(window wd, Object& object, void (Concept::*f)(::nana::detail::signals::code, const ::nana::detail::signals&)) - { - using namespace ::nana::detail; - bedrock::instance().wd_manager.attach_signal(reinterpret_cast(wd), object, f); - } - bool set_events(window, const std::shared_ptr&); template diff --git a/include/nana/gui/widgets/widget.hpp b/include/nana/gui/widgets/widget.hpp index 9d298fbe..a89aa597 100644 --- a/include/nana/gui/widgets/widget.hpp +++ b/include/nana/gui/widgets/widget.hpp @@ -22,10 +22,18 @@ namespace nana { + namespace detail + { + //Forward declaration of widget_notifier_interface + class widget_notifier_interface; + } + /// Abstract class for defining the capacity interface. class widget : nana::noncopyable, nana::nonmovable { + friend class detail::widget_notifier_interface; + class notifier; typedef void(*dummy_bool_type)(widget* (*)(const widget&)); public: virtual ~widget() = default; @@ -88,6 +96,11 @@ namespace nana operator dummy_bool_type() const; operator window() const; + protected: + std::unique_ptr<::nana::detail::widget_notifier_interface> _m_wdg_notifier(); + private: + virtual void _m_notify_destroy() = 0; + protected: //protected members, a derived class must call this implementation if it overrides an implementation virtual void _m_complete_creation(); @@ -152,7 +165,6 @@ namespace nana handle_ = API::dev::create_widget(parent_wd, r, this); API::dev::set_events(handle_, events_); API::dev::set_scheme(handle_, scheme_.get()); - API::dev::attach_signal(handle_, *this, &widget_object::signal); API::dev::attach_drawer(*this, trigger_); if(visible) API::show_window(handle_, true); @@ -193,29 +205,15 @@ namespace nana return trigger_; } private: - void signal(detail::signals::code code, const detail::signals& sig) - { - typedef detail::signals::code codes; - switch(code) - { - case codes::caption: - this->_m_caption(sig.info.caption); - break; - case codes::read_caption: - *sig.info.str = this->_m_caption(); - break; - case codes::destroy: - handle_ = nullptr; - break; - default: - break; - } - } - general_events& _m_get_general_events() const override { return *events_; } + + void _m_notify_destroy() override final + { + handle_ = nullptr; + } private: window handle_{nullptr}; DrawerTrigger trigger_; @@ -276,29 +274,15 @@ namespace nana return *scheme_; } private: - void signal(detail::signals::code code, const detail::signals& sig) - { - typedef detail::signals::code codes; - switch(code) - { - case codes::caption: - this->_m_caption(sig.info.caption); - break; - case codes::read_caption: - *sig.info.str = this->_m_caption(); - break; - case codes::destroy: - handle_ = nullptr; - break; - default: - break; - } - } - general_events& _m_get_general_events() const override { return *events_; } + + void _m_notify_destroy() override final + { + handle_ = nullptr; + } private: window handle_{nullptr}; std::shared_ptr events_; @@ -430,25 +414,6 @@ namespace nana return trigger_; } private: - void signal(detail::signals::code code, const detail::signals& sig) - { - typedef detail::signals::code codes; - switch(code) - { - case codes::caption: - this->_m_caption(sig.info.caption); - break; - case codes::read_caption: - *sig.info.str = this->_m_caption(); - break; - case codes::destroy: - handle_ = nullptr; - break; - default: - break; - } - } - void _m_bind_and_attach() { events_ = std::make_shared(); @@ -456,7 +421,6 @@ namespace nana scheme_ = API::dev::make_scheme(); API::dev::set_scheme(handle_, scheme_.get()); - API::dev::attach_signal(handle_, *this, &widget_object::signal); API::dev::attach_drawer(*this, trigger_); } @@ -464,6 +428,11 @@ namespace nana { return *events_; } + + void _m_notify_destroy() override final + { + handle_ = nullptr; + } private: window handle_; DrawerTrigger trigger_; @@ -511,7 +480,6 @@ namespace nana handle_ = API::dev::create_frame(parent_wd, r, this); API::dev::set_events(handle_, events_); API::dev::set_scheme(handle_, scheme_.get()); - API::dev::attach_signal(handle_, *this, &widget_object::signal); API::show_window(handle_, visible); this->_m_complete_creation(); } @@ -533,29 +501,15 @@ namespace nana return nullptr; } - void signal(detail::signals::code code, const detail::signals& sig) - { - typedef detail::signals::code codes; - switch(code) - { - case codes::caption: - this->_m_caption(sig.info.caption); - break; - case codes::read_caption: - *sig.info.str = this->_m_caption(); - break; - case codes::destroy: - handle_ = nullptr; - break; - default: - break; - } - } - general_events& _m_get_general_events() const override { return *events_; } + + void _m_notify_destroy() override final + { + handle_ = nullptr; + } private: window handle_{nullptr}; std::shared_ptr events_; diff --git a/source/gui/detail/basic_window.cpp b/source/gui/detail/basic_window.cpp index 91cb5db5..f0525e50 100644 --- a/source/gui/detail/basic_window.cpp +++ b/source/gui/detail/basic_window.cpp @@ -221,8 +221,8 @@ namespace nana //basic_window //@brief: constructor for the root window - basic_window::basic_window(basic_window* owner, widget* wdg, category::root_tag**) - : widget_ptr(wdg), other(category::root_tag::value) + basic_window::basic_window(basic_window* owner, std::unique_ptr&& wdg_notifier, category::root_tag**) + : widget_notifier(std::move(wdg_notifier)), other(category::root_tag::value) { drawer.bind(this); _m_init_pos_and_size(nullptr, rectangle()); diff --git a/source/gui/detail/bedrock_pi.cpp b/source/gui/detail/bedrock_pi.cpp index 7843fbaa..1bcd66e4 100644 --- a/source/gui/detail/bedrock_pi.cpp +++ b/source/gui/detail/bedrock_pi.cpp @@ -26,6 +26,18 @@ namespace nana { + //class internal_scope_guard + internal_scope_guard::internal_scope_guard() + { + detail::bedrock::instance().wd_manager.internal_lock().lock(); + } + + internal_scope_guard::~internal_scope_guard() + { + detail::bedrock::instance().wd_manager.internal_lock().unlock(); + } + //end class internal_scope_guard + //class event_arg event_arg::~event_arg(){} diff --git a/source/gui/detail/linux_X11/bedrock.cpp b/source/gui/detail/linux_X11/bedrock.cpp index f5bf3c14..a8df88ac 100644 --- a/source/gui/detail/linux_X11/bedrock.cpp +++ b/source/gui/detail/linux_X11/bedrock.cpp @@ -23,16 +23,6 @@ namespace nana { - //class internal_scope_guard - internal_scope_guard::internal_scope_guard() - { - detail::bedrock::instance().wd_manager.internal_lock().lock(); - } - internal_scope_guard::~internal_scope_guard() - { - detail::bedrock::instance().wd_manager.internal_lock().unlock(); - } - //end class internal_scope_guard namespace detail { #pragma pack(1) @@ -138,11 +128,6 @@ namespace detail //here is the definition of this object bedrock bedrock::bedrock_object; - inline window mycast(bedrock::core_window_t* wd) - { - return reinterpret_cast(wd); - } - Window event_window(const XEvent& event) { switch(event.type) diff --git a/source/gui/detail/win32/bedrock.cpp b/source/gui/detail/win32/bedrock.cpp index a1eb7c59..2085a00d 100644 --- a/source/gui/detail/win32/bedrock.cpp +++ b/source/gui/detail/win32/bedrock.cpp @@ -41,16 +41,6 @@ namespace nana { void notifications_window_proc(HWND wd, WPARAM wparam, LPARAM lparam); //Defined in notifier.cpp - //class internal_scope_guard - internal_scope_guard::internal_scope_guard() - { - detail::bedrock::instance().wd_manager.internal_lock().lock(); - } - internal_scope_guard::~internal_scope_guard() - { - detail::bedrock::instance().wd_manager.internal_lock().unlock(); - } - //end class internal_scope_guard namespace detail { namespace restrict @@ -985,14 +975,12 @@ namespace detail nana::arg_mouse arg; assign_arg(arg, msgwnd, message, pmdec); - const bool hit = msgwnd->dimension.is_hit(arg.pos); - bool fire_click = false; - if(msgwnd == pressed_wd) + if (msgwnd->dimension.is_hit(arg.pos)) { - if(msgwnd->flags.enabled && hit) + msgwnd->flags.action = mouse_action::over; + if ((msgwnd == pressed_wd) && msgwnd->flags.enabled) { - msgwnd->flags.action = mouse_action::over; arg.evt_code = event_code::click; emit_drawer(&drawer::click, msgwnd, arg, &context); fire_click = true; @@ -1002,9 +990,6 @@ namespace detail //Do mouse_up, this handle may be closed by click handler. if(brock.wd_manager.available(msgwnd) && msgwnd->flags.enabled) { - if(hit) - msgwnd->flags.action = mouse_action::over; - arg.evt_code = event_code::mouse_up; emit_drawer(&drawer::mouse_up, msgwnd, arg, &context); @@ -1521,15 +1506,10 @@ namespace detail return ::DefWindowProc(root_window, message, wParam, lParam); } - nana::category::flags bedrock::category(core_window_t* wd) + ::nana::category::flags bedrock::category(core_window_t* wd) { - if(wd) - { - internal_scope_guard isg; - if(wd_manager.available(wd)) - return wd->other.category; - } - return nana::category::flags::super; + internal_scope_guard lock; + return (wd_manager.available(wd) ? wd->other.category : ::nana::category::flags::super); } auto bedrock::focus() ->core_window_t* @@ -1540,13 +1520,8 @@ namespace detail native_window_type bedrock::root(core_window_t* wd) { - if(wd) - { - internal_scope_guard isg; - if(wd_manager.available(wd)) - return wd->root; - } - return nullptr; + internal_scope_guard lock; + return (wd_manager.available(wd) ? wd->root : nullptr); } void bedrock::set_menubar_taken(core_window_t* wd) diff --git a/source/gui/detail/window_manager.cpp b/source/gui/detail/window_manager.cpp index 9ff2a187..63840e0a 100644 --- a/source/gui/detail/window_manager.cpp +++ b/source/gui/detail/window_manager.cpp @@ -1,7 +1,7 @@ /* * Window Manager Implementation * Nana C++ Library(http://www.nanapro.org) - * Copyright(C) 2003-2014 Jinhao(cnjinhao@hotmail.com) + * Copyright(C) 2003-2015 Jinhao(cnjinhao@hotmail.com) * * Distributed under the Boost Software License, Version 1.0. * (See accompanying file LICENSE_1_0.txt or copy at @@ -42,7 +42,6 @@ namespace detail { root_register misc_register; handle_manager wd_register; - signal_manager signal; paint::image default_icon; }; //end struct wdm_private_impl @@ -171,22 +170,6 @@ namespace detail impl_->wd_register.all(v); } - void window_manager::signal_fire_caption(core_window_t* wd, const nana::char_t* str) - { - detail::signals sig; - sig.info.caption = str; - impl_->signal.call_signal(wd, signals::code::caption, sig); - } - - nana::string window_manager::signal_fire_caption(core_window_t* wd) - { - nana::string str; - detail::signals sig; - sig.info.str = &str; - impl_->signal.call_signal(wd, signals::code::read_caption, sig); - return str; - } - void window_manager::event_filter(core_window_t* wd, bool is_make, event_code evtid) { switch(evtid) @@ -224,10 +207,10 @@ namespace detail return false; } - window_manager::core_window_t* window_manager::create_root(core_window_t* owner, bool nested, rectangle r, const appearance& app, widget * wdg) + window_manager::core_window_t* window_manager::create_root(core_window_t* owner, bool nested, rectangle r, const appearance& app, widget* wdg) { native_window_type native = nullptr; - if(owner) + if (owner) { //Thread-Safe Required! std::lock_guard lock(mutex_); @@ -235,7 +218,7 @@ namespace detail if (impl_->wd_register.available(owner)) { native = (owner->other.category == category::frame_tag::value ? - owner->other.attribute.frame->container : owner->root_widget->root); + owner->other.attribute.frame->container : owner->root_widget->root); r.x += owner->pos_root.x; r.y += owner->pos_root.y; } @@ -244,9 +227,9 @@ namespace detail } auto result = native_interface::create_window(native, nested, r, app); - if(result.native_handle) + if (result.native_handle) { - core_window_t* wd = new core_window_t(owner, wdg, (category::root_tag**)nullptr); + core_window_t* wd = new core_window_t(owner, widget_notifier_interface::get_notifier(wdg), (category::root_tag**)nullptr); wd->flags.take_active = !app.no_activate; wd->title = native_interface::window_caption(result.native_handle); @@ -260,7 +243,7 @@ namespace detail wd->bind_native_window(result.native_handle, result.width, result.height, result.extra_width, result.extra_height, value->root_graph); impl_->wd_register.insert(wd, wd->thread_id); - if(owner && owner->other.category == category::frame_tag::value) + if (owner && owner->other.category == category::frame_tag::value) insert_frame(owner, wd); bedrock::inc_window(wd->thread_id); @@ -277,7 +260,7 @@ namespace detail if (impl_->wd_register.available(parent) == false) return nullptr; - core_window_t * wd = new core_window_t(parent, r, wdg, (category::frame_tag**)nullptr); + core_window_t * wd = new core_window_t(parent, widget_notifier_interface::get_notifier(wdg), r, (category::frame_tag**)nullptr); wd->frame_window(native_interface::create_child_window(parent->root, rectangle(wd->pos_root.x, wd->pos_root.y, r.width, r.height))); impl_->wd_register.insert(wd, wd->thread_id); @@ -324,11 +307,13 @@ namespace detail if (impl_->wd_register.available(parent) == false) throw std::invalid_argument("invalid parent/owner handle"); + auto wdg_notifier = widget_notifier_interface::get_notifier(wdg); + core_window_t * wd; - if(is_lite) - wd = new core_window_t(parent, r, wdg, (category::lite_widget_tag**)nullptr); + if (is_lite) + wd = new core_window_t(parent, std::move(wdg_notifier), r, (category::lite_widget_tag**)nullptr); else - wd = new core_window_t(parent, r, wdg, (category::widget_tag**)nullptr); + wd = new core_window_t(parent, std::move(wdg_notifier), r, (category::widget_tag**)nullptr); impl_->wd_register.insert(wd, wd->thread_id); return wd; } @@ -358,8 +343,8 @@ namespace detail //before the window_manager destroyes the window, and then, window_manager detaches the //non-existing drawer_trigger which is destroyed by destruction of widget. Crash! wd->drawer.detached(); - impl_->signal.call_signal(wd, signals::code::destroy, signals_); - impl_->signal.umake(wd); + + wd->widget_notifier->destroy(); native_interface::close_window(wd->root); } @@ -793,7 +778,7 @@ namespace detail ::nana::widget* window_manager::get_widget(core_window_t* wd) const { std::lock_guard lock(mutex_); - return (impl_->wd_register.available(wd) ? wd->widget_ptr : nullptr); + return (impl_->wd_register.available(wd) ? wd->widget_notifier->widget_ptr() : nullptr); } std::vector window_manager::get_children(core_window_t* wd) const @@ -1151,11 +1136,6 @@ namespace detail return nullptr; } - void window_manager::_m_attach_signal(core_window_t* wd, signal_invoker_interface* si) - { - impl_->signal.make(wd, si); - } - bool check_tree(basic_window* wd, basic_window* const cond) { if (wd == cond) return true; @@ -1366,8 +1346,7 @@ namespace detail wndlayout_type::enable_effects_bground(wd, false); wd->drawer.detached(); - impl_->signal.call_signal(wd, signals::code::destroy, signals_); - impl_->signal.umake(wd); + wd->widget_notifier->destroy(); if(wd->other.category == category::frame_tag::value) { diff --git a/source/gui/programming_interface.cpp b/source/gui/programming_interface.cpp index b4238fbd..83d27d0d 100644 --- a/source/gui/programming_interface.cpp +++ b/source/gui/programming_interface.cpp @@ -770,16 +770,16 @@ namespace API { auto const iwd = reinterpret_cast(wd); internal_scope_guard lock; - if(restrict::window_manager.available(iwd)) - restrict::window_manager.signal_fire_caption(iwd, title.c_str()); + if (restrict::window_manager.available(iwd)) + iwd->widget_notifier->caption(title); } nana::string window_caption(window wd) { auto const iwd = reinterpret_cast(wd); internal_scope_guard lock; - if(restrict::window_manager.available(iwd)) - return restrict::window_manager.signal_fire_caption(iwd); + if (restrict::window_manager.available(iwd)) + return iwd->widget_notifier->caption(); return{}; } diff --git a/source/gui/widgets/widget.cpp b/source/gui/widgets/widget.cpp index 07e81946..cd504eac 100644 --- a/source/gui/widgets/widget.cpp +++ b/source/gui/widgets/widget.cpp @@ -1,6 +1,6 @@ /* * The fundamental widget class implementation - * Copyright(C) 2003-2013 Jinhao(cnjinhao@hotmail.com) + * Copyright(C) 2003-2015 Jinhao(cnjinhao@hotmail.com) * * Distributed under the Boost Software License, Version 1.0. * (See accompanying file LICENSE_1_0.txt or copy at @@ -11,6 +11,7 @@ #include #include +#include namespace nana { @@ -18,8 +19,41 @@ namespace nana { void set_eval(window, i18n_eval&&); } + //class widget //@brief:The definition of class widget + class widget::notifier: public detail::widget_notifier_interface + { + public: + notifier(widget& wdg) + : wdg_(wdg) + {} + + private: + //implementation of widget_notifier_interface + widget* widget_ptr() const override + { + return &wdg_; + } + + void destroy() override + { + wdg_._m_notify_destroy(); + } + + std::wstring caption() override + { + return wdg_._m_caption(); + } + + virtual void caption(std::wstring text) + { + wdg_._m_caption(std::move(text)); + } + private: + widget& wdg_; + }; + nana::string widget::caption() const { return this->_m_caption(); @@ -205,6 +239,11 @@ namespace nana return handle(); } + std::unique_ptr<::nana::detail::widget_notifier_interface> widget::_m_wdg_notifier() + { + return std::unique_ptr<::nana::detail::widget_notifier_interface>(new notifier(*this)); + } + void widget::_m_complete_creation() {} @@ -298,7 +337,14 @@ namespace nana { return API::bgcolor(handle()); } - //end class widget + + namespace detail + { + std::unique_ptr widget_notifier_interface::get_notifier(widget* wdg) + { + return std::unique_ptr(new widget::notifier(*wdg)); + } + } }//end namespace nana