various changes to window visibility mgmt, including use of the mixbus2 code for toggling editor + mixer windows. no longer attempt to track changes made outside of ardour, which is a lost cause

This commit is contained in:
Paul Davis 2013-05-07 13:01:18 -04:00
parent e8301185c0
commit a902737db9
11 changed files with 125 additions and 59 deletions

View File

@ -146,8 +146,15 @@ sigc::signal<void> ARDOUR_UI::CloseAllDialogs;
ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], const char* localedir)
: Gtkmm2ext::UI (PROGRAM_NAME, argcp, argvp)
, gui_object_state (new GUIObjectState)
, _startup (0)
, engine (0)
, nsm (0)
, _was_dirty (false)
, _mixer_on_top (false)
, primary_clock (new MainClock (X_("primary"), false, X_("transport"), true, true, true, false, true))
, secondary_clock (new MainClock (X_("secondary"), false, X_("secondary"), true, true, false, false, true))
@ -197,7 +204,6 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], const char* localedir)
Gtkmm2ext::init(localedir);
splash = 0;
_startup = 0;
if (theArdourUI == 0) {
theArdourUI = this;
@ -688,7 +694,6 @@ ARDOUR_UI::startup ()
app->ready ();
nsm_url = getenv ("NSM_URL");
nsm = 0;
if (nsm_url) {
nsm = new NSM_Client;

View File

@ -301,6 +301,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
Gtk::Tooltips _tooltips;
NSM_Client *nsm;
bool _was_dirty;
bool _mixer_on_top;
void goto_editor_window ();
void goto_mixer_window ();

View File

@ -268,19 +268,21 @@ ARDOUR_UI::goto_editor_window ()
editor->show_window ();
editor->present ();
flush_pending ();
/* mixer should now be on top */
WindowManager::instance().set_transient_for (editor);
_mixer_on_top = false;
}
void
ARDOUR_UI::goto_mixer_window ()
{
if (!editor) {
return;
}
Glib::RefPtr<Gdk::Window> win = editor->get_window ();
Glib::RefPtr<Gdk::Window> win;
Glib::RefPtr<Gdk::Screen> screen;
if (editor) {
win = editor->get_window ();
}
if (win) {
screen = win->get_screen();
} else {
@ -295,10 +297,11 @@ ARDOUR_UI::goto_mixer_window ()
mixer->show_window ();
mixer->present ();
flush_pending ();
/* mixer should now be on top */
WindowManager::instance().set_transient_for (mixer);
_mixer_on_top = true;
}
void
ARDOUR_UI::toggle_mixer_window ()
{
@ -319,49 +322,80 @@ ARDOUR_UI::toggle_mixer_window ()
void
ARDOUR_UI::toggle_editor_mixer ()
{
if (editor && mixer) {
bool obscuring = false;
/* currently, if windows are on different
screens then we do nothing; but in the
future we may want to bring the window
to the front or something, so I'm leaving this
variable for future use
*/
bool same_screen = true;
if (editor && mixer) {
if (editor->get_screen() != mixer->get_screen()) {
// different screens, so don't do anything
return;
/* remeber: Screen != Monitor (Screen is a separately rendered
* continuous geometry that make include 1 or more monitors.
*/
if (editor->get_screen() != mixer->get_screen() && (mixer->get_screen() != 0) && (editor->get_screen() != 0)) {
// different screens, so don't do anything
same_screen = false;
} else {
// they are on the same screen, see if they are obscuring each other
gint ex, ey, ew, eh;
gint mx, my, mw, mh;
editor->get_position (ex, ey);
editor->get_size (ew, eh);
mixer->get_position (mx, my);
mixer->get_size (mw, mh);
GdkRectangle e;
GdkRectangle m;
GdkRectangle r;
e.x = ex;
e.y = ey;
e.width = ew;
e.height = eh;
m.x = mx;
m.y = my;
m.width = mw;
m.height = mh;
if (gdk_rectangle_intersect (&e, &m, &r)) {
obscuring = true;
}
}
}
if (mixer && !mixer->not_visible() && mixer->property_has_toplevel_focus()) {
if (obscuring && same_screen) {
goto_editor_window();
}
} else if (editor && !editor->not_visible() && editor->property_has_toplevel_focus()) {
if (obscuring && same_screen) {
goto_mixer_window();
}
} else if (mixer && mixer->not_visible()) {
if (obscuring && same_screen) {
goto_mixer_window ();
}
} else if (editor && editor->not_visible()) {
if (obscuring && same_screen) {
goto_editor_window ();
}
} else if (obscuring && same_screen) {
//it's unclear what to do here, so just do the opposite of what we did last time (old behavior)
if (_mixer_on_top) {
goto_editor_window ();
} else {
goto_mixer_window ();
}
/* See if they are obscuring each other */
gint ex, ey, ew, eh;
gint mx, my, mw, mh;
editor->get_position (ex, ey);
editor->get_size (ew, eh);
mixer->get_position (mx, my);
mixer->get_size (mw, mh);
GdkRectangle e;
GdkRectangle m;
GdkRectangle r;
e.x = ex;
e.y = ey;
e.width = ew;
e.height = eh;
m.x = mx;
m.y = my;
m.width = mw;
m.height = mh;
if (!gdk_rectangle_intersect (&e, &m, &r)) {
/* they do not intersect so do not toggle */
return;
}
}
if (mixer && mixer->fully_visible()) {
goto_editor_window ();
} else {
goto_mixer_window ();
}
}
}
void

View File

@ -229,8 +229,7 @@ pane_size_watcher (Paned* pane)
}
Editor::Editor ()
: VisibilityTracker (*((Gtk::Window*) this))
, _join_object_range_state (JOIN_OBJECT_RANGE_NONE)
: _join_object_range_state (JOIN_OBJECT_RANGE_NONE)
/* time display buttons */
, minsec_label (_("Mins:Secs"))

View File

@ -43,7 +43,6 @@
#include "gtkmm2ext/dndtreeview.h"
#include "gtkmm2ext/stateful_button.h"
#include "gtkmm2ext/bindings.h"
#include "gtkmm2ext/visibility_tracker.h"
#include "pbd/stateful.h"
#include "pbd/signals.h"
@ -137,7 +136,7 @@ class TimeSelection;
class RegionLayeringOrderEditor;
class VerboseCursor;
class Editor : public PublicEditor, public PBD::ScopedConnectionList, public ARDOUR::SessionHandlePtr, public Gtkmm2ext::VisibilityTracker
class Editor : public PublicEditor, public PBD::ScopedConnectionList, public ARDOUR::SessionHandlePtr
{
public:
Editor ();

View File

@ -30,6 +30,7 @@ sigc::signal<void> PublicEditor::DropDownKeys;
PublicEditor::PublicEditor ()
: Window (Gtk::WINDOW_TOPLEVEL)
, VisibilityTracker (*((Gtk::Window*)this))
{
}

View File

@ -39,6 +39,8 @@
#include "pbd/statefuldestructible.h"
#include "gtkmm2ext/visibility_tracker.h"
#include "editing.h"
#include "canvas.h"
#include "selection.h"
@ -97,7 +99,7 @@ using ARDOUR::framecnt_t;
* of PublicEditor need not be recompiled if private methods or member variables
* change.
*/
class PublicEditor : public Gtk::Window, public PBD::StatefulDestructible {
class PublicEditor : public Gtk::Window, public PBD::StatefulDestructible, public Gtkmm2ext::VisibilityTracker {
public:
PublicEditor ();
virtual ~PublicEditor ();

View File

@ -112,6 +112,26 @@ WindowManager::set_session (ARDOUR::Session* s)
}
}
void
WindowManager::set_transient_for (Gtk::Window* parent)
{
if (parent) {
for (Windows::const_iterator i = _windows.begin(); i != _windows.end(); ++i) {
Gtk::Window* win = (*i)->get();
if (win) {
win->set_transient_for (*parent);
}
}
} else {
for (Windows::const_iterator i = _windows.begin(); i != _windows.end(); ++i) {
Gtk::Window* win = (*i)->get();
if (win) {
gtk_window_set_transient_for (win->gobj(), 0);
}
}
}
}
/*-----------------------*/
WindowManager::ProxyBase::ProxyBase (const string& name, const std::string& menu_name)

View File

@ -180,6 +180,9 @@ class WindowManager
void set_session (ARDOUR::Session*);
void add_state (XMLNode&) const;
/* HACK HACK HACK */
void set_transient_for (Gtk::Window*);
private:
typedef std::list<ProxyBase*> Windows;
Windows _windows;

View File

@ -23,7 +23,6 @@
#include <gtk/gtkpaned.h>
#include <gtk/gtk.h>
#include <gtkmm2ext/utils.h>
#include <gtkmm/widget.h>
#include <gtkmm/button.h>
#include <gtkmm/window.h>
@ -32,6 +31,8 @@
#include <gtkmm/comboboxtext.h>
#include <gtkmm/tooltip.h>
#include "gtkmm2ext/utils.h"
#include "i18n.h"
using namespace std;
@ -659,3 +660,4 @@ Gtkmm2ext::disable_tooltips ()
{
gtk_rc_parse_string ("gtk-enable-tooltips = 0");
}

View File

@ -35,7 +35,7 @@ bool
VisibilityTracker::handle_visibility_notify_event (GdkEventVisibility* ev)
{
_visibility = ev->state;
std::cerr << "VT: " << _window.get_title() << " vis event, fv = " << fully_visible() << " pv = " << partially_visible() << " nv = " << not_visible() << std::endl;
// std::cerr << "VT: " << _window.get_title() << " vis event, fv = " << fully_visible() << " pv = " << partially_visible() << " nv = " << not_visible() << std::endl;
return false;
}