X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;f=libs%2Fgtkmm2ext%2Ftabbable.cc;h=5e4752454e6cfd6c8547b56799f59399b2307165;hb=1468e270defc24de767e86118d0210480fad27b9;hp=342283ee802307697736f0b742ca61ecfecba5a9;hpb=308f6ed8281d2b8913207e0236bd22678e73ec9b;p=ardour.git diff --git a/libs/gtkmm2ext/tabbable.cc b/libs/gtkmm2ext/tabbable.cc index 342283ee80..5e4752454e 100644 --- a/libs/gtkmm2ext/tabbable.cc +++ b/libs/gtkmm2ext/tabbable.cc @@ -27,7 +27,9 @@ #include "gtkmm2ext/utils.h" #include "gtkmm2ext/visibility_tracker.h" -#include "i18n.h" +#include "pbd/stacktrace.h" + +#include "pbd/i18n.h" using namespace Gtkmm2ext; using namespace Gtk; @@ -36,18 +38,9 @@ using std::string; Tabbable::Tabbable (Widget& w, const string& name) : WindowProxy (name) , _contents (w) - , tab_close_image (ArdourIcon::CloseCross, 0xffffffff) + , _parent_notebook (0) , tab_requested_by_state (true) { - /* make the image about the same size as an actual X */ - set_size_request_to_display_given_text (tab_close_image, "X", 0, 0); - - _tab_box.set_spacing (2); - _tab_box.pack_start (_tab_label, true, true); - _tab_box.pack_start (_tab_close_button, false, false); - _tab_close_button.add (tab_close_image); - - _tab_close_button.signal_clicked().connect (sigc::mem_fun (*this, &Tabbable::tab_close_clicked)); } Tabbable::~Tabbable () @@ -58,19 +51,10 @@ Tabbable::~Tabbable () } } -void -Tabbable::tab_close_clicked () -{ - hide_tab (); -} - void Tabbable::add_to_notebook (Notebook& notebook, const string& tab_title) { _parent_notebook = ¬ebook; - _tab_title = tab_title; - _tab_label.set_text (tab_title); - _tab_box.show_all (); if (tab_requested_by_state) { attach (); @@ -87,7 +71,7 @@ Tabbable::use_own_window (bool and_pack_it) if (parent) { parent->remove (_contents); } - _own_notebook.append_page (_contents, _tab_box); + _own_notebook.append_page (_contents); } return win; @@ -95,13 +79,13 @@ Tabbable::use_own_window (bool and_pack_it) } bool -Tabbable::window_visible () +Tabbable::window_visible () const { - if (!own_window()) { + if (!_window) { return false; } - return visible(); + return _window->is_visible(); } Window* @@ -115,9 +99,9 @@ Tabbable::get (bool create) return 0; } - /* From here on, we're creating the window + /* From here on, we're creating the window */ - + if ((_window = new Window (WINDOW_TOPLEVEL)) == 0) { return 0; } @@ -126,12 +110,15 @@ Tabbable::get (bool create) _own_notebook.show (); _own_notebook.set_show_tabs (false); + _window->signal_map().connect (sigc::mem_fun (*this, &Tabbable::window_mapped)); + _window->signal_unmap().connect (sigc::mem_fun (*this, &Tabbable::window_unmapped)); + /* do other window-related setup */ setup (); /* window should be ready for derived classes to do something with it */ - + return _window; } @@ -144,14 +131,15 @@ Tabbable::show_own_window (bool and_pack_it) if (parent) { alloc = parent->get_allocation(); } - + (void) use_own_window (and_pack_it); - + if (parent) { _window->set_default_size (alloc.get_width(), alloc.get_height()); } - _window->show_all (); + tab_requested_by_state = false; + _window->present (); } @@ -181,10 +169,34 @@ Tabbable::show_window () } } +/** If this Tabbable is currently parented by a tab, ensure that the tab is the + * current one. If it is parented by a window, then toggle the visibility of + * that window. + */ +void +Tabbable::change_visibility () +{ + if (tabbed()) { + _parent_notebook->set_current_page (_parent_notebook->page_num (_contents)); + return; + } + + if (tab_requested_by_state) { + /* should be tabbed, but currently isn't parented by a notebook */ + return; + } + + if (_window && (current_toplevel() == _window)) { + /* Use WindowProxy method which will rotate then hide */ + toggle(); + } +} + void Tabbable::make_visible () { if (_window && (current_toplevel() == _window)) { + set_pos (); _window->present (); } else { @@ -205,7 +217,7 @@ Tabbable::make_invisible () hide_tab (); } } - + void Tabbable::detach () { @@ -218,7 +230,7 @@ Tabbable::attach () if (!_parent_notebook) { return; } - + if (tabbed()) { /* already tabbed */ return; @@ -229,31 +241,27 @@ Tabbable::attach () /* unpack Tabbable from parent, put it back in the main tabbed * notebook */ - + save_pos_and_size (); - + _contents.get_parent()->remove (_contents); - + /* leave the window around */ - + _window->hide (); } - - _parent_notebook->append_page (_contents, _tab_box); + + _parent_notebook->append_page (_contents); _parent_notebook->set_tab_detachable (_contents); _parent_notebook->set_tab_reorderable (_contents); _parent_notebook->set_current_page (_parent_notebook->page_num (_contents)); - Gtkmm2ext::UI::instance()->set_tip (_tab_label, - string_compose (_("Drag this tab to the desktop to show %1 in its own window\n\n" - "To put the window back, click on its \"close\" button"), _tab_title)); - - /* have to force this on, which is semantically correct, since * the user has effectively asked for it. */ tab_requested_by_state = true; + StateChange (*this); } bool @@ -265,18 +273,16 @@ Tabbable::delete_event_handler (GdkEventAny *ev) } bool -Tabbable::is_tabbed () const +Tabbable::tabbed () const { - Window* toplevel = (Window*) _contents.get_toplevel(); - - if (_window && (toplevel == _window)) { + if (_window && (current_toplevel() == _window)) { return false; } - if (_parent_notebook && _contents.get_parent()) { + if (_parent_notebook && (_parent_notebook->page_num (_contents) >= 0)) { return true; } - + return false; } @@ -285,6 +291,7 @@ Tabbable::hide_tab () { if (tabbed()) { _parent_notebook->remove_page (_contents); + StateChange (*this); } } @@ -293,9 +300,11 @@ Tabbable::show_tab () { if (!window_visible() && _parent_notebook) { if (_contents.get_parent() == 0) { + tab_requested_by_state = true; add_to_notebook (*_parent_notebook, _tab_title); } _parent_notebook->set_current_page (_parent_notebook->page_num (_contents)); + current_toplevel()->present (); } } @@ -312,9 +321,9 @@ Tabbable::xml_node_name() } bool -Tabbable::tabbed () const +Tabbable::tabbed_by_default() const { - return _parent_notebook && (_parent_notebook->page_num (_contents) >= 0); + return tab_requested_by_state; } XMLNode& @@ -323,7 +332,7 @@ Tabbable::get_state() XMLNode& node (WindowProxy::get_state()); node.add_property (X_("tabbed"), tabbed() ? X_("yes") : X_("no")); - + return node; } @@ -332,31 +341,44 @@ Tabbable::set_state (const XMLNode& node, int version) { int ret; - if ((ret = WindowProxy::set_state (node, version)) == 0) { - if (_visible) { - if (use_own_window (true) == 0) { - ret = -1; - } - } + if ((ret = WindowProxy::set_state (node, version)) != 0) { + return ret; + } + + if (_visible) { + show_own_window (true); } XMLNodeList children = node.children (); XMLNode* window_node = node.child ("Window"); if (window_node) { - const XMLProperty* prop = window_node->property (X_("tabbed")); + XMLProperty const * prop = window_node->property (X_("tabbed")); if (prop) { tab_requested_by_state = PBD::string_is_affirmative (prop->value()); } } - if (tab_requested_by_state) { - attach (); - } else { - /* this does nothing if not tabbed */ - hide_tab (); + if (!_visible) { + if (tab_requested_by_state) { + attach (); + } else { + /* this does nothing if not tabbed */ + hide_tab (); + } } - + return ret; } +void +Tabbable::window_mapped () +{ + StateChange (*this); +} + +void +Tabbable::window_unmapped () +{ + StateChange (*this); +}