diff --git a/include/nana/gui/widgets/menu.hpp b/include/nana/gui/widgets/menu.hpp index 8e0e7b44..693310a2 100644 --- a/include/nana/gui/widgets/menu.hpp +++ b/include/nana/gui/widgets/menu.hpp @@ -1,7 +1,7 @@ /** * A Menu implementation * Nana C++ Library(http://www.nanapro.org) - * Copyright(C) 2009-2016 Jinhao(cnjinhao@hotmail.com) + * Copyright(C) 2009-2017 Jinhao(cnjinhao@hotmail.com) * * Distributed under the Boost Software License, Version 1.0. * (See accompanying file LICENSE_1_0.txt or copy at @@ -48,6 +48,8 @@ namespace nana item_proxy& checked(bool); bool checked() const; + std::string text() const; + std::size_t index() const; private: std::size_t index_; @@ -123,8 +125,19 @@ namespace nana ~menu(); /// Appends an item to the menu. - item_proxy append(std::string text_utf8, const event_fn_t& callback= event_fn_t()); + item_proxy append(std::string text_utf8, const event_fn_t& handler = {}); void append_splitter(); + + /// Inserts new item at specified position + /** + * It will invalidate the existing item proxies from the specified position. + * @param pos The position where new item to be inserted + * @param text_utf8 The title of item + * @param handler The event handler for the item. + * @return the item proxy to the new inserted item. + */ + item_proxy insert(std::size_t pos, std::string text_utf8, const event_fn_t& handler = {}); + void clear(); ///< Erases all of the items. /// Closes the menu. It does not destroy the menu; just close the window for the menu. void close(); diff --git a/source/gui/widgets/menu.cpp b/source/gui/widgets/menu.cpp index 1decffd5..02ba5649 100644 --- a/source/gui/widgets/menu.cpp +++ b/source/gui/widgets/menu.cpp @@ -1,7 +1,7 @@ /* * A Menu implementation * Nana C++ Library(http://www.nanapro.org) -* Copyright(C) 2009-2016 Jinhao(cnjinhao@hotmail.com) +* Copyright(C) 2009-2017 Jinhao(cnjinhao@hotmail.com) * * Distributed under the Boost Software License, Version 1.0. * (See accompanying file LICENSE_1_0.txt or copy at @@ -86,6 +86,11 @@ namespace nana return item_.flags.checked; } + std::string menu_item_type::item_proxy::text() const + { + return item_.text; + } + std::size_t menu_item_type::item_proxy::index() const { return index_; @@ -1117,10 +1122,11 @@ namespace nana delete impl_; } - auto menu::append(std::string text_utf8, const menu::event_fn_t& callback) -> item_proxy + auto menu::append(std::string text_utf8, const menu::event_fn_t& handler) -> item_proxy { - impl_->mbuilder.data().items.emplace_back(new item_type(std::move(text_utf8), callback)); - return item_proxy(size() - 1, *impl_->mbuilder.data().items.back()); + std::unique_ptr item{ new item_type{ std::move(text_utf8), handler } }; + impl_->mbuilder.data().items.emplace_back(item.get()); + return item_proxy(size() - 1, *item.release()); } void menu::append_splitter() @@ -1128,6 +1134,18 @@ namespace nana impl_->mbuilder.data().items.emplace_back(new item_type); } + auto menu::insert(std::size_t pos, std::string text_utf8, const event_fn_t& handler) -> item_proxy + { + auto & items = impl_->mbuilder.data().items; + if (pos > items.size()) + throw std::out_of_range("menu: a new item inserted to an invalid position"); + + std::unique_ptr item{ new item_type{ std::move(text_utf8), handler } }; + impl_->mbuilder.data().items.emplace(impl_->mbuilder.data().items.cbegin() + pos, item.get()); + + return item_proxy{ pos, *item.release() }; + } + void menu::clear() { internal_scope_guard lock;