First go at saving window visibility and position state across saves.
git-svn-id: svn://localhost/ardour2/branches/3.0@7644 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
parent
8d8bc9baca
commit
579fcb70e2
|
@ -98,6 +98,9 @@ typedef uint64_t microseconds_t;
|
|||
#include "engine_dialog.h"
|
||||
#include "processor_box.h"
|
||||
#include "time_axis_view_item.h"
|
||||
#include "window_proxy.h"
|
||||
#include "global_port_matrix.h"
|
||||
#include "location_ui.h"
|
||||
|
||||
#include "i18n.h"
|
||||
|
||||
|
@ -164,7 +167,6 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[])
|
|||
|
||||
auditioning_alert_button (_("AUDITION")),
|
||||
solo_alert_button (_("SOLO")),
|
||||
shown_flag (false),
|
||||
error_log_button (_("Errors"))
|
||||
|
||||
{
|
||||
|
@ -290,6 +292,21 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[])
|
|||
|
||||
TimeAxisViewItem::set_constant_heights ();
|
||||
|
||||
/* The following must happen after ARDOUR::init() so that Config is set up */
|
||||
|
||||
location_ui = new ActionWindowProxy<LocationUIWindow> (X_("locations"), Config->extra_xml (X_("UI")), X_("ToggleLocations"));
|
||||
big_clock_window = new ActionWindowProxy<Gtk::Window> (X_("bigclock"), Config->extra_xml (X_("UI")), X_("ToggleBigClock"));
|
||||
|
||||
for (ARDOUR::DataType::iterator i = ARDOUR::DataType::begin(); i != ARDOUR::DataType::end(); ++i) {
|
||||
_global_port_matrix[*i] = new ActionWindowProxy<GlobalPortMatrixWindow> (
|
||||
string_compose ("GlobalPortMatrix-%1", (*i).to_string()),
|
||||
Config->extra_xml (X_("UI")),
|
||||
string_compose ("toggle-%1-connection-manager", (*i).to_string())
|
||||
);
|
||||
}
|
||||
|
||||
setup_clock ();
|
||||
|
||||
starting.connect (sigc::mem_fun(*this, &ARDOUR_UI::startup));
|
||||
stopping.connect (sigc::mem_fun(*this, &ARDOUR_UI::shutdown));
|
||||
|
||||
|
@ -660,8 +677,16 @@ ARDOUR_UI::startup ()
|
|||
|
||||
goto_editor_window ();
|
||||
|
||||
/* Add the window proxies here; their addition may cause windows to be opened, and we want them
|
||||
to be opened on top of the editor window that goto_editor_window() just opened.
|
||||
*/
|
||||
add_window_proxy (location_ui);
|
||||
add_window_proxy (big_clock_window);
|
||||
for (ARDOUR::DataType::iterator i = ARDOUR::DataType::begin(); i != ARDOUR::DataType::end(); ++i) {
|
||||
add_window_proxy (_global_port_matrix[*i]);
|
||||
}
|
||||
|
||||
BootMessage (string_compose (_("%1 is ready for use"), PROGRAM_NAME));
|
||||
show ();
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -784,17 +809,22 @@ If you still wish to quit, please use the\n\n\
|
|||
point_one_second_connection.disconnect ();
|
||||
point_oh_five_second_connection.disconnect ();
|
||||
point_zero_one_second_connection.disconnect();
|
||||
|
||||
_session->set_clean ();
|
||||
}
|
||||
|
||||
/* Save state before deleting the session, as that causes some
|
||||
windows to be destroyed before their visible state can be
|
||||
saved.
|
||||
*/
|
||||
save_ardour_state ();
|
||||
|
||||
if (_session) {
|
||||
// _session->set_deletion_in_progress ();
|
||||
_session->set_clean ();
|
||||
_session->remove_pending_capture_state ();
|
||||
delete _session;
|
||||
_session = 0;
|
||||
}
|
||||
|
||||
cerr << "Save before quit\n";
|
||||
save_ardour_state ();
|
||||
|
||||
ArdourDialog::close_all_dialogs ();
|
||||
engine->stop (true);
|
||||
quit ();
|
||||
|
@ -2571,7 +2601,6 @@ ARDOUR_UI::close_session()
|
|||
}
|
||||
|
||||
goto_editor_window ();
|
||||
show ();
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -2725,20 +2754,6 @@ ARDOUR_UI::build_session (const Glib::ustring& path, const Glib::ustring& snap_n
|
|||
return 0;
|
||||
}
|
||||
|
||||
void
|
||||
ARDOUR_UI::show ()
|
||||
{
|
||||
if (editor) {
|
||||
editor->show_window ();
|
||||
|
||||
if (!shown_flag) {
|
||||
editor->present ();
|
||||
}
|
||||
|
||||
shown_flag = true;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
ARDOUR_UI::launch_chat ()
|
||||
{
|
||||
|
@ -3355,22 +3370,10 @@ ARDOUR_UI::reconnect_to_jack ()
|
|||
void
|
||||
ARDOUR_UI::use_config ()
|
||||
{
|
||||
|
||||
XMLNode* node = Config->extra_xml (X_("TransportControllables"));
|
||||
if (node) {
|
||||
set_transport_controllable_state (*node);
|
||||
}
|
||||
|
||||
node = Config->extra_xml (X_("UI"));
|
||||
|
||||
if (node) {
|
||||
const XMLProperty* prop = node->property (X_("show-big-clock"));
|
||||
Glib::RefPtr<Action> act = ActionManager::get_action (X_("Common"), X_("ToggleBigClock"));
|
||||
if (act) {
|
||||
Glib::RefPtr<ToggleAction> tact = Glib::RefPtr<ToggleAction>::cast_dynamic(act);
|
||||
tact->set_active (string_is_affirmative (prop->value()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -3388,7 +3391,7 @@ ARDOUR_UI::update_transport_clocks (nframes_t pos)
|
|||
secondary_clock.set (pos);
|
||||
}
|
||||
|
||||
if (big_clock_window) {
|
||||
if (big_clock_window->get()) {
|
||||
big_clock.set (pos);
|
||||
}
|
||||
}
|
||||
|
@ -3414,7 +3417,7 @@ ARDOUR_UI::record_state_changed ()
|
|||
{
|
||||
ENSURE_GUI_THREAD (*this, &ARDOUR_UI::record_state_changed);
|
||||
|
||||
if (!_session || !big_clock_window) {
|
||||
if (!_session || !big_clock_window->get()) {
|
||||
/* why bother - the clock isn't visible */
|
||||
return;
|
||||
}
|
||||
|
@ -3614,3 +3617,23 @@ ARDOUR_UI::toggle_translations ()
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Add a window proxy to our list, so that its state will be saved.
|
||||
* This call also causes the window to be created and opened if its
|
||||
* state was saved as `visible'.
|
||||
*/
|
||||
void
|
||||
ARDOUR_UI::add_window_proxy (WindowProxyBase* p)
|
||||
{
|
||||
_window_proxies.push_back (p);
|
||||
p->maybe_show ();
|
||||
}
|
||||
|
||||
/** Remove a window proxy from our list. Must be called if a WindowProxy
|
||||
* is deleted, to prevent hanging pointers.
|
||||
*/
|
||||
void
|
||||
ARDOUR_UI::remove_window_proxy (WindowProxyBase* p)
|
||||
{
|
||||
_window_proxies.remove (p);
|
||||
}
|
||||
|
|
|
@ -67,6 +67,7 @@
|
|||
#include "ardour_dialog.h"
|
||||
#include "editing.h"
|
||||
#include "ui_config.h"
|
||||
#include "window_proxy.h"
|
||||
|
||||
class About;
|
||||
class AddRouteDialog;
|
||||
|
@ -85,6 +86,8 @@ class SessionOptionEditor;
|
|||
class Splash;
|
||||
class ThemeManager;
|
||||
class MidiTracer;
|
||||
class WindowProxyBase;
|
||||
class GlobalPortMatrixWindow;
|
||||
|
||||
namespace Gtkmm2ext {
|
||||
class TearOff;
|
||||
|
@ -110,9 +113,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
|
|||
|
||||
bool run_startup (bool should_be_new, std::string load_template);
|
||||
|
||||
void show ();
|
||||
bool shown() { return shown_flag; }
|
||||
|
||||
void show_splash ();
|
||||
void hide_splash ();
|
||||
|
||||
|
@ -233,6 +233,9 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
|
|||
|
||||
void set_shuttle_fract (double);
|
||||
|
||||
void add_window_proxy (WindowProxyBase *);
|
||||
void remove_window_proxy (WindowProxyBase *);
|
||||
|
||||
protected:
|
||||
friend class PublicEditor;
|
||||
|
||||
|
@ -313,7 +316,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
|
|||
void manage_window (Gtk::Window&);
|
||||
|
||||
AudioClock big_clock;
|
||||
Gtk::Window* big_clock_window;
|
||||
ActionWindowProxy<Gtk::Window>* big_clock_window;
|
||||
int original_big_clock_width;
|
||||
int original_big_clock_height;
|
||||
double original_big_clock_font_size;
|
||||
|
@ -588,10 +591,13 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
|
|||
BundleManager *bundle_manager;
|
||||
void create_bundle_manager ();
|
||||
|
||||
LocationUIWindow *location_ui;
|
||||
ActionWindowProxy<LocationUIWindow>* location_ui;
|
||||
int create_location_ui ();
|
||||
void handle_locations_change (ARDOUR::Location*);
|
||||
|
||||
ActionWindowProxy<GlobalPortMatrixWindow>* _global_port_matrix[ARDOUR::DataType::num_types];
|
||||
void toggle_global_port_matrix (ARDOUR::DataType);
|
||||
|
||||
static UIConfiguration *ui_config;
|
||||
ThemeManager *theme_manager;
|
||||
|
||||
|
@ -625,7 +631,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
|
|||
About* about;
|
||||
Splash* splash;
|
||||
void pop_back_splash ();
|
||||
bool shown_flag;
|
||||
|
||||
/* cleanup */
|
||||
|
||||
|
@ -707,6 +712,8 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
|
|||
*/
|
||||
bool idle_finish ();
|
||||
void queue_finish ();
|
||||
|
||||
std::list<WindowProxyBase*> _window_proxies;
|
||||
};
|
||||
|
||||
#endif /* __ardour_gui_h__ */
|
||||
|
|
|
@ -46,6 +46,8 @@
|
|||
#include "utils.h"
|
||||
#include "theme_manager.h"
|
||||
#include "midi_tracer.h"
|
||||
#include "global_port_matrix.h"
|
||||
#include "location_ui.h"
|
||||
|
||||
#include "i18n.h"
|
||||
|
||||
|
@ -103,7 +105,6 @@ ARDOUR_UI::setup_windows ()
|
|||
|
||||
editor->add_toplevel_controls (top_packer);
|
||||
|
||||
setup_clock ();
|
||||
setup_transport();
|
||||
build_menu_bar ();
|
||||
|
||||
|
|
|
@ -41,6 +41,7 @@
|
|||
#include "gui_thread.h"
|
||||
#include "midi_tracer.h"
|
||||
#include "add_route_dialog.h"
|
||||
#include "global_port_matrix.h"
|
||||
|
||||
#include "i18n.h"
|
||||
|
||||
|
@ -59,8 +60,8 @@ ARDOUR_UI::set_session (Session *s)
|
|||
return;
|
||||
}
|
||||
|
||||
if (location_ui) {
|
||||
location_ui->set_session(s);
|
||||
if (location_ui->get()) {
|
||||
location_ui->get()->set_session(s);
|
||||
}
|
||||
|
||||
if (route_params) {
|
||||
|
@ -75,6 +76,12 @@ ARDOUR_UI::set_session (Session *s)
|
|||
session_option_editor->set_session (s);
|
||||
}
|
||||
|
||||
for (ARDOUR::DataType::iterator i = ARDOUR::DataType::begin(); i != ARDOUR::DataType::end(); ++i) {
|
||||
if (_global_port_matrix[*i]->get()) {
|
||||
_global_port_matrix[*i]->get()->set_session (_session);
|
||||
}
|
||||
}
|
||||
|
||||
primary_clock.set_session (s);
|
||||
secondary_clock.set_session (s);
|
||||
big_clock.set_session (s);
|
||||
|
@ -217,10 +224,10 @@ ARDOUR_UI::toggle_big_clock_window ()
|
|||
RefPtr<ToggleAction> tact = RefPtr<ToggleAction>::cast_dynamic(act);
|
||||
|
||||
if (tact->get_active()) {
|
||||
big_clock_window->show_all ();
|
||||
big_clock_window->present ();
|
||||
big_clock_window->get()->show_all ();
|
||||
big_clock_window->get()->present ();
|
||||
} else {
|
||||
big_clock_window->hide ();
|
||||
big_clock_window->get()->hide ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -297,9 +304,9 @@ int
|
|||
ARDOUR_UI::create_location_ui ()
|
||||
{
|
||||
if (location_ui == 0) {
|
||||
location_ui = new LocationUIWindow ();
|
||||
location_ui->set_session (_session);
|
||||
location_ui->signal_unmap().connect (sigc::bind (sigc::ptr_fun(&ActionManager::uncheck_toggleaction), X_("<Actions>/Common/ToggleLocations")));
|
||||
location_ui->set (new LocationUIWindow ());
|
||||
location_ui->get()->set_session (_session);
|
||||
location_ui->get()->signal_unmap().connect (sigc::bind (sigc::ptr_fun(&ActionManager::uncheck_toggleaction), X_("<Actions>/Common/ToggleLocations")));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -316,10 +323,10 @@ ARDOUR_UI::toggle_location_window ()
|
|||
RefPtr<ToggleAction> tact = RefPtr<ToggleAction>::cast_dynamic(act);
|
||||
|
||||
if (tact->get_active()) {
|
||||
location_ui->show_all ();
|
||||
location_ui->present ();
|
||||
location_ui->get()->show_all ();
|
||||
location_ui->get()->present ();
|
||||
} else {
|
||||
location_ui->hide ();
|
||||
location_ui->get()->hide ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -47,6 +47,8 @@
|
|||
#include "mixer_ui.h"
|
||||
#include "startup.h"
|
||||
#include "utils.h"
|
||||
#include "window_proxy.h"
|
||||
#include "global_port_matrix.h"
|
||||
|
||||
#include <gtkmm2ext/application.h>
|
||||
|
||||
|
@ -68,7 +70,6 @@ using namespace Glib;
|
|||
|
||||
int
|
||||
ARDOUR_UI::create_editor ()
|
||||
|
||||
{
|
||||
try {
|
||||
editor = new Editor ();
|
||||
|
@ -225,6 +226,10 @@ ARDOUR_UI::install_actions ()
|
|||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
act = ActionManager::register_toggle_action (common_actions, X_("ToggleBigClock"), _("Big Clock"), sigc::mem_fun(*this, &ARDOUR_UI::toggle_big_clock_window));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
act = ActionManager::register_toggle_action (common_actions, X_("toggle-audio-connection-manager"), _("Audio Connection Manager"), sigc::bind (sigc::mem_fun(*this, &ARDOUR_UI::toggle_global_port_matrix), ARDOUR::DataType::AUDIO));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
act = ActionManager::register_toggle_action (common_actions, X_("toggle-midi-connection-manager"), _("MIDI Connection Manager"), sigc::bind (sigc::mem_fun(*this, &ARDOUR_UI::toggle_global_port_matrix), ARDOUR::DataType::MIDI));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
act = ActionManager::register_action (common_actions, X_("NewMIDITracer"), _("MIDI Tracer"), sigc::mem_fun(*this, &ARDOUR_UI::new_midi_tracer_window));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
ActionManager::register_action (common_actions, X_("About"), _("About"), sigc::mem_fun(*this, &ARDOUR_UI::show_about));
|
||||
|
@ -555,20 +560,20 @@ ARDOUR_UI::setup_clock ()
|
|||
{
|
||||
ARDOUR_UI::Clock.connect (sigc::bind (sigc::mem_fun (big_clock, &AudioClock::set), false));
|
||||
|
||||
big_clock_window = new Window (WINDOW_TOPLEVEL);
|
||||
big_clock_window->set (new Window (WINDOW_TOPLEVEL));
|
||||
|
||||
big_clock_window->set_keep_above (true);
|
||||
big_clock_window->set_border_width (0);
|
||||
big_clock_window->add (big_clock);
|
||||
big_clock_window->get()->set_keep_above (true);
|
||||
big_clock_window->get()->set_border_width (0);
|
||||
big_clock_window->get()->add (big_clock);
|
||||
|
||||
big_clock_window->set_title (_("Big Clock"));
|
||||
big_clock_window->set_type_hint (Gdk::WINDOW_TYPE_HINT_UTILITY);
|
||||
big_clock_window->signal_realize().connect (sigc::mem_fun (*this, &ARDOUR_UI::big_clock_realized));
|
||||
big_clock_window->signal_unmap().connect (sigc::bind (sigc::ptr_fun(&ActionManager::uncheck_toggleaction), X_("<Actions>/Common/ToggleBigClock")));
|
||||
big_clock_window->signal_key_press_event().connect (sigc::bind (sigc::ptr_fun (relay_key_press), big_clock_window), false);
|
||||
big_clock_window->signal_size_allocate().connect (sigc::mem_fun (*this, &ARDOUR_UI::big_clock_size_allocate));
|
||||
big_clock_window->get()->set_title (_("Big Clock"));
|
||||
big_clock_window->get()->set_type_hint (Gdk::WINDOW_TYPE_HINT_UTILITY);
|
||||
big_clock_window->get()->signal_realize().connect (sigc::mem_fun (*this, &ARDOUR_UI::big_clock_realized));
|
||||
big_clock_window->get()->signal_unmap().connect (sigc::bind (sigc::ptr_fun(&ActionManager::uncheck_toggleaction), X_("<Actions>/Common/ToggleBigClock")));
|
||||
big_clock_window->get()->signal_key_press_event().connect (sigc::bind (sigc::ptr_fun (relay_key_press), big_clock_window->get()), false);
|
||||
big_clock_window->get()->signal_size_allocate().connect (sigc::mem_fun (*this, &ARDOUR_UI::big_clock_size_allocate));
|
||||
|
||||
manage_window (*big_clock_window);
|
||||
manage_window (*big_clock_window->get());
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -576,8 +581,8 @@ ARDOUR_UI::big_clock_realized ()
|
|||
{
|
||||
int x, y, w, d;
|
||||
|
||||
set_decoration (big_clock_window, (Gdk::DECOR_BORDER|Gdk::DECOR_RESIZEH));
|
||||
big_clock_window->get_window()->get_geometry (x, y, w, big_clock_height, d);
|
||||
set_decoration (big_clock_window->get(), (Gdk::DECOR_BORDER|Gdk::DECOR_RESIZEH));
|
||||
big_clock_window->get()->get_window()->get_geometry (x, y, w, big_clock_height, d);
|
||||
|
||||
original_big_clock_height = big_clock_height;
|
||||
original_big_clock_width = w;
|
||||
|
@ -588,45 +593,6 @@ ARDOUR_UI::big_clock_realized ()
|
|||
if (!fd.get_size_is_absolute ()) {
|
||||
original_big_clock_font_size /= PANGO_SCALE;
|
||||
}
|
||||
|
||||
/* we can't set the real size until we know the original one, with the UI rc-file-set font
|
||||
size, so do this here.
|
||||
*/
|
||||
|
||||
XMLNode* node = Config->extra_xml (X_("UI"));
|
||||
|
||||
if (node) {
|
||||
|
||||
const XMLProperty* prop;
|
||||
int w, h, x, y;
|
||||
int have_pos = 0;
|
||||
|
||||
w = h = x = y = 0;
|
||||
|
||||
if ((prop = node->property ("big-clock-x-size")) != 0) {
|
||||
w = atoi (prop->value());
|
||||
}
|
||||
if ((prop = node->property ("big-clock-y-size")) != 0) {
|
||||
h = atoi (prop->value());
|
||||
}
|
||||
|
||||
if (w && h) {
|
||||
big_clock_window->set_default_size (w, h);
|
||||
}
|
||||
|
||||
if ((prop = node->property ("big-clock-x-off")) != 0) {
|
||||
x = atoi (prop->value());
|
||||
have_pos++;
|
||||
}
|
||||
if ((prop = node->property ("big-clock-y-off")) != 0) {
|
||||
y = atoi (prop->value());
|
||||
have_pos++;
|
||||
}
|
||||
|
||||
if (have_pos == 2) {
|
||||
big_clock_window->move (x, y);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -634,9 +600,9 @@ ARDOUR_UI::float_big_clock (Gtk::Window* parent)
|
|||
{
|
||||
if (big_clock_window) {
|
||||
if (parent) {
|
||||
big_clock_window->set_transient_for (*parent);
|
||||
big_clock_window->get()->set_transient_for (*parent);
|
||||
} else {
|
||||
gtk_window_set_transient_for (big_clock_window->gobj(), (GtkWindow*) 0);
|
||||
gtk_window_set_transient_for (big_clock_window->get()->gobj(), (GtkWindow*) 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -655,7 +621,7 @@ ARDOUR_UI::idle_big_clock_text_resizer (int win_w, int win_h)
|
|||
{
|
||||
big_clock_resize_in_progress = false;
|
||||
|
||||
Glib::RefPtr<Gdk::Window> win = big_clock_window->get_window();
|
||||
Glib::RefPtr<Gdk::Window> win = big_clock_window->get()->get_window();
|
||||
Pango::FontDescription fd (big_clock.get_style()->get_font());
|
||||
int current_size = fd.get_size ();
|
||||
int x, y, w, h, d;
|
||||
|
@ -708,30 +674,11 @@ ARDOUR_UI::save_ardour_state ()
|
|||
Config->add_extra_xml (get_transport_controllable_state());
|
||||
|
||||
XMLNode* window_node = new XMLNode (X_("UI"));
|
||||
|
||||
for (list<WindowProxyBase*>::iterator i = _window_proxies.begin(); i != _window_proxies.end(); ++i) {
|
||||
window_node->add_child_nocopy (*((*i)->get_state ()));
|
||||
}
|
||||
|
||||
window_node->add_property ("show-big-clock", (big_clock_window && big_clock_window->is_visible() ? "yes" : "no"));
|
||||
|
||||
Glib::RefPtr<Gdk::Window> win;
|
||||
|
||||
if (big_clock_window && (win = big_clock_window->get_window())) {
|
||||
|
||||
int w, h;
|
||||
int xoff, yoff;
|
||||
char buf[32];
|
||||
|
||||
win->get_size (w, h);
|
||||
win->get_position (xoff, yoff);
|
||||
|
||||
snprintf (buf, sizeof (buf), "%d", w);
|
||||
window_node->add_property ("big-clock-x-size", buf);
|
||||
snprintf (buf, sizeof (buf), "%d", h);
|
||||
window_node->add_property ("big-clock-y-size", buf);
|
||||
snprintf (buf, sizeof (buf), "%d", xoff);
|
||||
window_node->add_property ("big-clock-x-off", buf);
|
||||
snprintf (buf, sizeof (buf), "%d", yoff);
|
||||
window_node->add_property ("big-clock-y-off", buf);
|
||||
}
|
||||
|
||||
/* tearoffs */
|
||||
|
||||
XMLNode* tearoff_node = new XMLNode (X_("Tearoffs"));
|
||||
|
@ -778,3 +725,17 @@ ARDOUR_UI::save_ardour_state ()
|
|||
Keyboard::save_keybindings ();
|
||||
}
|
||||
|
||||
void
|
||||
ARDOUR_UI::toggle_global_port_matrix (ARDOUR::DataType t)
|
||||
{
|
||||
if (_global_port_matrix[t]->get() == 0) {
|
||||
_global_port_matrix[t]->set (new GlobalPortMatrixWindow (_session, t));
|
||||
}
|
||||
|
||||
if (_global_port_matrix[t]->get()->is_visible ()) {
|
||||
_global_port_matrix[t]->get()->hide ();
|
||||
} else {
|
||||
_global_port_matrix[t]->get()->present ();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -107,6 +107,10 @@ class AutomationTimeAxisView : public TimeAxisView {
|
|||
|
||||
bool has_automation () const;
|
||||
|
||||
boost::shared_ptr<ARDOUR::Route> parent_route () {
|
||||
return _route;
|
||||
}
|
||||
|
||||
protected:
|
||||
boost::shared_ptr<ARDOUR::Route> _route; ///< Parent route
|
||||
boost::shared_ptr<ARDOUR::AutomationControl> _control; ///< Control
|
||||
|
|
|
@ -385,9 +385,6 @@ Editor::Editor ()
|
|||
select_new_marker = false;
|
||||
rhythm_ferret = 0;
|
||||
_bundle_manager = 0;
|
||||
for (ARDOUR::DataType::iterator i = ARDOUR::DataType::begin(); i != ARDOUR::DataType::end(); ++i) {
|
||||
_global_port_matrix[*i] = 0;
|
||||
}
|
||||
no_save_visual = false;
|
||||
resize_idle_id = -1;
|
||||
|
||||
|
@ -668,9 +665,6 @@ Editor::Editor ()
|
|||
set_mouse_mode (MouseObject, true);
|
||||
set_edit_point_preference (EditAtMouse, true);
|
||||
|
||||
XMLNode* node = ARDOUR_UI::instance()->editor_settings();
|
||||
set_state (*node, Stateful::loading_state_version);
|
||||
|
||||
_playlist_selector = new PlaylistSelector();
|
||||
_playlist_selector->signal_delete_event().connect (sigc::bind (sigc::ptr_fun (just_hide_it), static_cast<Window *> (_playlist_selector)));
|
||||
|
||||
|
@ -1079,12 +1073,6 @@ Editor::set_session (Session *t)
|
|||
sfbrowser->set_session (_session);
|
||||
}
|
||||
|
||||
for (ARDOUR::DataType::iterator i = ARDOUR::DataType::begin(); i != ARDOUR::DataType::end(); ++i) {
|
||||
if (_global_port_matrix[*i]) {
|
||||
_global_port_matrix[*i]->set_session (_session);
|
||||
}
|
||||
}
|
||||
|
||||
compute_fixed_ruler_scale ();
|
||||
|
||||
/* there are never any selected regions at startup */
|
||||
|
@ -2555,6 +2543,11 @@ Editor::set_state (const XMLNode& node, int /*version*/)
|
|||
the_notebook.set_current_page (atoi (prop->value ()));
|
||||
}
|
||||
|
||||
XMLNodeList children = node.children ();
|
||||
for (XMLNodeList::const_iterator i = children.begin(); i != children.end(); ++i) {
|
||||
selection->set_state (**i, Stateful::current_state_version);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -2641,6 +2634,8 @@ Editor::get_state ()
|
|||
snprintf (buf, sizeof (buf), "%d", the_notebook.get_current_page ());
|
||||
node->add_property (X_("editor-list-page"), buf);
|
||||
|
||||
node->add_child_nocopy (selection->get_state ());
|
||||
|
||||
return *node;
|
||||
}
|
||||
|
||||
|
@ -4905,16 +4900,6 @@ Editor::show_rhythm_ferret ()
|
|||
rhythm_ferret->present ();
|
||||
}
|
||||
|
||||
void
|
||||
Editor::show_global_port_matrix (ARDOUR::DataType t)
|
||||
{
|
||||
if (_global_port_matrix[t] == 0) {
|
||||
_global_port_matrix[t] = new GlobalPortMatrixWindow (_session, t);
|
||||
}
|
||||
|
||||
_global_port_matrix[t]->show ();
|
||||
}
|
||||
|
||||
void
|
||||
Editor::first_idle ()
|
||||
{
|
||||
|
@ -5200,12 +5185,13 @@ Editor::foreach_time_axis_view (sigc::slot<void,TimeAxisView&> theslot)
|
|||
}
|
||||
}
|
||||
|
||||
/** Find a RouteTimeAxisView by the ID of its route */
|
||||
RouteTimeAxisView*
|
||||
Editor::get_route_view_by_id (PBD::ID& id)
|
||||
Editor::get_route_view_by_route_id (PBD::ID& id) const
|
||||
{
|
||||
RouteTimeAxisView* v;
|
||||
|
||||
for(TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) {
|
||||
for (TrackViewList::const_iterator i = track_views.begin(); i != track_views.end(); ++i) {
|
||||
if((v = dynamic_cast<RouteTimeAxisView*>(*i)) != 0) {
|
||||
if(v->route()->id() == id) {
|
||||
return v;
|
||||
|
|
|
@ -65,6 +65,7 @@
|
|||
#include "editor_items.h"
|
||||
#include "region_selection.h"
|
||||
#include "canvas.h"
|
||||
#include "window_proxy.h"
|
||||
|
||||
namespace Gnome { namespace Canvas {
|
||||
class NoEventText;
|
||||
|
@ -106,7 +107,6 @@ class BundleManager;
|
|||
class ControlPoint;
|
||||
class CrossfadeView;
|
||||
class DragManager;
|
||||
class GlobalPortMatrixWindow;
|
||||
class GroupedButtons;
|
||||
class Marker;
|
||||
class MidiRegionView;
|
||||
|
@ -213,7 +213,7 @@ class Editor : public PublicEditor, public PBD::ScopedConnectionList, public ARD
|
|||
void foreach_time_axis_view (sigc::slot<void,TimeAxisView&>);
|
||||
void add_to_idle_resize (TimeAxisView*, int32_t);
|
||||
|
||||
RouteTimeAxisView* get_route_view_by_id (PBD::ID& id);
|
||||
RouteTimeAxisView* get_route_view_by_route_id (PBD::ID& id) const;
|
||||
|
||||
void consider_auditioning (boost::shared_ptr<ARDOUR::Region>);
|
||||
void hide_a_region (boost::shared_ptr<ARDOUR::Region>);
|
||||
|
@ -413,7 +413,6 @@ class Editor : public PublicEditor, public PBD::ScopedConnectionList, public ARD
|
|||
void toggle_meter_updating();
|
||||
|
||||
void show_rhythm_ferret();
|
||||
void show_global_port_matrix (ARDOUR::DataType);
|
||||
|
||||
void goto_visual_state (uint32_t);
|
||||
void save_visual_state (uint32_t);
|
||||
|
@ -2003,7 +2002,6 @@ public:
|
|||
|
||||
RhythmFerret* rhythm_ferret;
|
||||
BundleManager* _bundle_manager;
|
||||
GlobalPortMatrixWindow* _global_port_matrix[ARDOUR::DataType::num_types];
|
||||
|
||||
void fit_tracks (TrackViewList &);
|
||||
void fit_selected_tracks ();
|
||||
|
|
|
@ -542,10 +542,6 @@ Editor::register_actions ()
|
|||
act = ActionManager::register_action (editor_actions, "toggle-rhythm-ferret", _("Rhythm Ferret..."), sigc::mem_fun(*this, &Editor::show_rhythm_ferret));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
ActionManager::region_selection_sensitive_actions.push_back (act);
|
||||
act = ActionManager::register_action (editor_actions, "toggle-audio-connection-manager", _("Audio Connection Manager"), sigc::bind (sigc::mem_fun (*this, &Editor::show_global_port_matrix), ARDOUR::DataType::AUDIO));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
act = ActionManager::register_action (editor_actions, "toggle-midi-connection-manager", _("MIDI Connection Manager"), sigc::bind (sigc::mem_fun (*this, &Editor::show_global_port_matrix), ARDOUR::DataType::MIDI));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
act = ActionManager::register_action (editor_actions, "toggle-log-window", _("Log"),
|
||||
sigc::mem_fun (ARDOUR_UI::instance(), &ARDOUR_UI::toggle_errors));
|
||||
ActionManager::session_sensitive_actions.push_back (act);
|
||||
|
|
|
@ -362,6 +362,8 @@ MixerStrip::set_route (boost::shared_ptr<Route> rt)
|
|||
button_table.remove (*show_sends_button);
|
||||
}
|
||||
|
||||
processor_box.set_route (rt);
|
||||
|
||||
RouteUI::set_route (rt);
|
||||
|
||||
/* map the current state */
|
||||
|
@ -377,8 +379,6 @@ MixerStrip::set_route (boost::shared_ptr<Route> rt)
|
|||
|
||||
revert_to_default_display ();
|
||||
|
||||
processor_box.set_route (rt);
|
||||
|
||||
if (set_color_from_route()) {
|
||||
set_color (unique_random_color());
|
||||
}
|
||||
|
@ -1540,6 +1540,7 @@ MixerStrip::map_frozen ()
|
|||
switch (at->freeze_state()) {
|
||||
case AudioTrack::Frozen:
|
||||
processor_box.set_sensitive (false);
|
||||
hide_redirect_editors ();
|
||||
break;
|
||||
default:
|
||||
processor_box.set_sensitive (true);
|
||||
|
@ -1547,8 +1548,6 @@ MixerStrip::map_frozen ()
|
|||
break;
|
||||
}
|
||||
}
|
||||
|
||||
hide_redirect_editors ();
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1565,10 +1564,10 @@ MixerStrip::hide_processor_editor (boost::weak_ptr<Processor> p)
|
|||
return;
|
||||
}
|
||||
|
||||
void* gui = processor->get_gui ();
|
||||
Gtk::Window* w = processor_box.get_processor_ui (processor);
|
||||
|
||||
if (gui) {
|
||||
static_cast<Gtk::Widget*>(gui)->hide ();
|
||||
if (w) {
|
||||
w->hide ();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -99,6 +99,10 @@ class MixerStrip : public RouteUI, public Gtk::EventBox
|
|||
void set_button_names ();
|
||||
void show_send (boost::shared_ptr<ARDOUR::Send>);
|
||||
|
||||
bool mixer_owned () const {
|
||||
return _mixer_owned;
|
||||
}
|
||||
|
||||
sigc::signal<void> WidthChanged;
|
||||
|
||||
static sigc::signal<void,boost::shared_ptr<ARDOUR::Route> > SwitchIO;
|
||||
|
|
|
@ -392,28 +392,6 @@ ProcessorBox::set_width (Width w)
|
|||
redisplay_processors ();
|
||||
}
|
||||
|
||||
void
|
||||
ProcessorBox::remove_processor_gui (boost::shared_ptr<Processor> processor)
|
||||
{
|
||||
boost::shared_ptr<Send> send;
|
||||
boost::shared_ptr<Return> retrn;
|
||||
boost::shared_ptr<PortInsert> port_insert;
|
||||
|
||||
if ((port_insert = boost::dynamic_pointer_cast<PortInsert> (processor)) != 0) {
|
||||
PortInsertUI *io_selector = reinterpret_cast<PortInsertUI *> (port_insert->get_gui());
|
||||
port_insert->set_gui (0);
|
||||
delete io_selector;
|
||||
} else if ((send = boost::dynamic_pointer_cast<Send> (processor)) != 0) {
|
||||
SendUIWindow *sui = reinterpret_cast<SendUIWindow*> (send->get_gui());
|
||||
send->set_gui (0);
|
||||
delete sui;
|
||||
} else if ((retrn = boost::dynamic_pointer_cast<Return> (processor)) != 0) {
|
||||
ReturnUIWindow *rui = reinterpret_cast<ReturnUIWindow*> (retrn->get_gui());
|
||||
retrn->set_gui (0);
|
||||
delete rui;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
ProcessorBox::build_send_action_menu ()
|
||||
{
|
||||
|
@ -958,6 +936,73 @@ ProcessorBox::redisplay_processors ()
|
|||
_route->foreach_processor (sigc::mem_fun (*this, &ProcessorBox::add_processor_to_display));
|
||||
|
||||
build_processor_tooltip (processor_eventbox, _("Inserts, sends & plugins:"));
|
||||
|
||||
_route->foreach_processor (sigc::mem_fun (*this, &ProcessorBox::maybe_add_processor_to_ui_list));
|
||||
|
||||
/* trim dead wood from the processor window proxy list */
|
||||
|
||||
list<ProcessorWindowProxy*>::iterator i = _processor_window_proxies.begin();
|
||||
while (i != _processor_window_proxies.end()) {
|
||||
list<ProcessorWindowProxy*>::iterator j = i;
|
||||
++j;
|
||||
|
||||
if (!(*i)->marked) {
|
||||
ARDOUR_UI::instance()->remove_window_proxy (*i);
|
||||
_processor_window_proxies.erase (i);
|
||||
delete *i;
|
||||
}
|
||||
|
||||
i = j;
|
||||
}
|
||||
}
|
||||
|
||||
/** Add a ProcessorWindowProxy for a processor to our list, if that processor does
|
||||
* not already have one.
|
||||
*/
|
||||
void
|
||||
ProcessorBox::maybe_add_processor_to_ui_list (boost::weak_ptr<Processor> w)
|
||||
{
|
||||
boost::shared_ptr<Processor> p = w.lock ();
|
||||
if (!p) {
|
||||
return;
|
||||
}
|
||||
|
||||
list<ProcessorWindowProxy*>::iterator i = _processor_window_proxies.begin ();
|
||||
while (i != _processor_window_proxies.end()) {
|
||||
|
||||
boost::shared_ptr<Processor> t = (*i)->processor().lock ();
|
||||
|
||||
if (p == t) {
|
||||
/* this processor is already on the list; done */
|
||||
(*i)->marked = true;
|
||||
return;
|
||||
}
|
||||
|
||||
++i;
|
||||
}
|
||||
|
||||
/* not on the list; add it */
|
||||
|
||||
string loc;
|
||||
if (_parent_strip) {
|
||||
if (_parent_strip->mixer_owned()) {
|
||||
loc = X_("M");
|
||||
} else {
|
||||
loc = X_("R");
|
||||
}
|
||||
} else {
|
||||
loc = X_("P");
|
||||
}
|
||||
|
||||
ProcessorWindowProxy* wp = new ProcessorWindowProxy (
|
||||
string_compose ("%1-%2-%3", loc, _route->id(), p->id()),
|
||||
Config->extra_xml (X_("UI")),
|
||||
this,
|
||||
w);
|
||||
|
||||
wp->marked = true;
|
||||
_processor_window_proxies.push_back (wp);
|
||||
ARDOUR_UI::instance()->add_window_proxy (wp);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1102,10 +1147,10 @@ ProcessorBox::cut_processors (const ProcSelection& to_be_removed)
|
|||
(boost::dynamic_pointer_cast<Send>((*i)) != 0) ||
|
||||
(boost::dynamic_pointer_cast<Return>((*i)) != 0)) {
|
||||
|
||||
void* gui = (*i)->get_gui ();
|
||||
Window* w = get_processor_ui (*i);
|
||||
|
||||
if (gui) {
|
||||
static_cast<Gtk::Widget*>(gui)->hide ();
|
||||
if (w) {
|
||||
w->hide ();
|
||||
}
|
||||
|
||||
XMLNode& child ((*i)->get_state());
|
||||
|
@ -1174,10 +1219,10 @@ ProcessorBox::delete_processors (const ProcSelection& targets)
|
|||
|
||||
for (ProcSelection::const_iterator i = targets.begin(); i != targets.end(); ++i) {
|
||||
|
||||
void* gui = (*i)->get_gui ();
|
||||
Window* w = get_processor_ui (*i);
|
||||
|
||||
if (gui) {
|
||||
static_cast<Gtk::Widget*>(gui)->hide ();
|
||||
if (w) {
|
||||
w->hide ();
|
||||
}
|
||||
|
||||
_route->remove_processor(*i);
|
||||
|
@ -1195,10 +1240,10 @@ ProcessorBox::delete_dragged_processors (const list<boost::shared_ptr<Processor>
|
|||
no_processor_redisplay = true;
|
||||
for (x = procs.begin(); x != procs.end(); ++x) {
|
||||
|
||||
void* gui = (*x)->get_gui ();
|
||||
Window* w = get_processor_ui (*x);
|
||||
|
||||
if (gui) {
|
||||
static_cast<Gtk::Widget*>(gui)->hide ();
|
||||
if (w) {
|
||||
w->hide ();
|
||||
}
|
||||
|
||||
_route->remove_processor(*x);
|
||||
|
@ -1488,13 +1533,14 @@ ProcessorBox::edit_processor (boost::shared_ptr<Processor> processor)
|
|||
#ifdef OLD_SEND_EDITING
|
||||
SendUIWindow *send_ui;
|
||||
|
||||
if (send->get_gui() == 0) {
|
||||
Window* w = get_processor_ui (send);
|
||||
if (w == 0) {
|
||||
send_ui = new SendUIWindow (send, _session);
|
||||
send_ui->set_title (send->name());
|
||||
send->set_gui (send_ui);
|
||||
set_processor_ui (send, send_ui);
|
||||
|
||||
} else {
|
||||
send_ui = reinterpret_cast<SendUIWindow *> (send->get_gui());
|
||||
send_ui = dynamic_cast<SendUIWindow *> (w);
|
||||
}
|
||||
|
||||
gidget = send_ui;
|
||||
|
@ -1513,15 +1559,16 @@ ProcessorBox::edit_processor (boost::shared_ptr<Processor> processor)
|
|||
boost::shared_ptr<Return> retrn = boost::dynamic_pointer_cast<Return> (processor);
|
||||
|
||||
ReturnUIWindow *return_ui;
|
||||
Window* w = get_processor_ui (retrn);
|
||||
|
||||
if (retrn->get_gui() == 0) {
|
||||
if (w == 0) {
|
||||
|
||||
return_ui = new ReturnUIWindow (retrn, _session);
|
||||
return_ui->set_title (retrn->name ());
|
||||
send->set_gui (return_ui);
|
||||
set_processor_ui (send, return_ui);
|
||||
|
||||
} else {
|
||||
return_ui = reinterpret_cast<ReturnUIWindow *> (retrn->get_gui());
|
||||
return_ui = dynamic_cast<ReturnUIWindow *> (w);
|
||||
}
|
||||
|
||||
gidget = return_ui;
|
||||
|
@ -1535,14 +1582,16 @@ ProcessorBox::edit_processor (boost::shared_ptr<Processor> processor)
|
|||
Container* toplevel = get_toplevel();
|
||||
Window* win = dynamic_cast<Gtk::Window*>(toplevel);
|
||||
|
||||
if (plugin_insert->get_gui() == 0) {
|
||||
Window* w = get_processor_ui (plugin_insert);
|
||||
|
||||
if (w == 0) {
|
||||
|
||||
plugin_ui = new PluginUIWindow (win, plugin_insert);
|
||||
plugin_ui->set_title (generate_processor_title (plugin_insert));
|
||||
plugin_insert->set_gui (plugin_ui);
|
||||
set_processor_ui (plugin_insert, plugin_ui);
|
||||
|
||||
} else {
|
||||
plugin_ui = reinterpret_cast<PluginUIWindow *> (plugin_insert->get_gui());
|
||||
plugin_ui = dynamic_cast<PluginUIWindow *> (w);
|
||||
plugin_ui->set_parent (win);
|
||||
}
|
||||
|
||||
|
@ -1558,12 +1607,14 @@ ProcessorBox::edit_processor (boost::shared_ptr<Processor> processor)
|
|||
|
||||
PortInsertWindow *io_selector;
|
||||
|
||||
if (port_insert->get_gui() == 0) {
|
||||
Window* w = get_processor_ui (port_insert);
|
||||
|
||||
if (w == 0) {
|
||||
io_selector = new PortInsertWindow (_session, port_insert);
|
||||
port_insert->set_gui (io_selector);
|
||||
set_processor_ui (port_insert, io_selector);
|
||||
|
||||
} else {
|
||||
io_selector = reinterpret_cast<PortInsertWindow *> (port_insert->get_gui());
|
||||
io_selector = dynamic_cast<PortInsertWindow *> (w);
|
||||
}
|
||||
|
||||
gidget = io_selector;
|
||||
|
@ -1838,18 +1889,18 @@ ProcessorBox::route_property_changed (const PropertyChange& what_changed)
|
|||
|
||||
processor = (*iter)->processor ();
|
||||
|
||||
void* gui = processor->get_gui();
|
||||
Window* w = get_processor_ui (processor);
|
||||
|
||||
if (!gui) {
|
||||
if (!w) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* rename editor windows for sends and plugins */
|
||||
|
||||
if ((send = boost::dynamic_pointer_cast<Send> (processor)) != 0) {
|
||||
static_cast<Window*>(gui)->set_title (send->name ());
|
||||
w->set_title (send->name ());
|
||||
} else if ((plugin_insert = boost::dynamic_pointer_cast<PluginInsert> (processor)) != 0) {
|
||||
static_cast<Window*>(gui)->set_title (generate_processor_title (plugin_insert));
|
||||
w->set_title (generate_processor_title (plugin_insert));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1882,3 +1933,75 @@ ProcessorBox::on_size_allocate (Allocation& a)
|
|||
(*i)->set_pixel_width (a.get_width ());
|
||||
}
|
||||
}
|
||||
|
||||
/** @param p Processor.
|
||||
* @return the UI window for \a p.
|
||||
*/
|
||||
Window *
|
||||
ProcessorBox::get_processor_ui (boost::shared_ptr<Processor> p) const
|
||||
{
|
||||
list<ProcessorWindowProxy*>::const_iterator i = _processor_window_proxies.begin ();
|
||||
while (i != _processor_window_proxies.end()) {
|
||||
boost::shared_ptr<Processor> t = (*i)->processor().lock ();
|
||||
if (t && t == p) {
|
||||
return (*i)->get ();
|
||||
}
|
||||
|
||||
++i;
|
||||
}
|
||||
|
||||
/* we shouldn't get here, because the ProcessorUIList should always contain
|
||||
an entry for each processor.
|
||||
*/
|
||||
assert (false);
|
||||
}
|
||||
|
||||
/** Make a note of the UI window that a processor is using.
|
||||
* @param p Processor.
|
||||
* @param w UI window.
|
||||
*/
|
||||
void
|
||||
ProcessorBox::set_processor_ui (boost::shared_ptr<Processor> p, Gtk::Window* w)
|
||||
{
|
||||
list<ProcessorWindowProxy*>::iterator i = _processor_window_proxies.begin ();
|
||||
while (i != _processor_window_proxies.end()) {
|
||||
boost::shared_ptr<Processor> t = (*i)->processor().lock ();
|
||||
if (t && t == p) {
|
||||
(*i)->set (w);
|
||||
return;
|
||||
}
|
||||
|
||||
++i;
|
||||
}
|
||||
|
||||
/* we shouldn't get here, because the ProcessorUIList should always contain
|
||||
an entry for each processor.
|
||||
*/
|
||||
assert (false);
|
||||
}
|
||||
|
||||
ProcessorWindowProxy::ProcessorWindowProxy (
|
||||
string const & name,
|
||||
XMLNode const * node,
|
||||
ProcessorBox* box,
|
||||
boost::weak_ptr<Processor> processor
|
||||
)
|
||||
: WindowProxy<Gtk::Window> (name, node)
|
||||
, marked (false)
|
||||
, _processor_box (box)
|
||||
, _processor (processor)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ProcessorWindowProxy::show ()
|
||||
{
|
||||
boost::shared_ptr<Processor> p = _processor.lock ();
|
||||
if (!p) {
|
||||
return;
|
||||
}
|
||||
|
||||
_processor_box->edit_processor (p);
|
||||
}
|
||||
|
|
|
@ -52,6 +52,7 @@
|
|||
#include "io_selector.h"
|
||||
#include "send_ui.h"
|
||||
#include "enums.h"
|
||||
#include "window_proxy.h"
|
||||
|
||||
class MotionController;
|
||||
class PluginSelector;
|
||||
|
@ -71,6 +72,29 @@ namespace ARDOUR {
|
|||
class Session;
|
||||
}
|
||||
|
||||
class ProcessorBox;
|
||||
|
||||
/** A WindowProxy for Processor UI windows; it knows how to ask a ProcessorBox
|
||||
* to create a UI window for a particular processor.
|
||||
*/
|
||||
class ProcessorWindowProxy : public WindowProxy<Gtk::Window>
|
||||
{
|
||||
public:
|
||||
ProcessorWindowProxy (std::string const &, XMLNode const *, ProcessorBox *, boost::weak_ptr<ARDOUR::Processor>);
|
||||
|
||||
void show ();
|
||||
|
||||
boost::weak_ptr<ARDOUR::Processor> processor () const {
|
||||
return _processor;
|
||||
}
|
||||
|
||||
bool marked;
|
||||
|
||||
private:
|
||||
ProcessorBox* _processor_box;
|
||||
boost::weak_ptr<ARDOUR::Processor> _processor;
|
||||
};
|
||||
|
||||
class ProcessorEntry : public Gtkmm2ext::DnDVBoxChild, public sigc::trackable
|
||||
{
|
||||
public:
|
||||
|
@ -145,12 +169,19 @@ class ProcessorBox : public Gtk::HBox, public PluginInterestedObject, public ARD
|
|||
void select_all_inserts ();
|
||||
void select_all_sends ();
|
||||
|
||||
Gtk::Window* get_processor_ui (boost::shared_ptr<ARDOUR::Processor>) const;
|
||||
void edit_processor (boost::shared_ptr<ARDOUR::Processor>);
|
||||
|
||||
sigc::signal<void,boost::shared_ptr<ARDOUR::Processor> > ProcessorSelected;
|
||||
sigc::signal<void,boost::shared_ptr<ARDOUR::Processor> > ProcessorUnselected;
|
||||
|
||||
static void register_actions();
|
||||
|
||||
private:
|
||||
|
||||
/* prevent copy construction */
|
||||
ProcessorBox (ProcessorBox const &);
|
||||
|
||||
boost::shared_ptr<ARDOUR::Route> _route;
|
||||
MixerStrip* _parent_strip; // null if in RouteParamsUI
|
||||
bool _owner_is_mixer;
|
||||
|
@ -212,8 +243,6 @@ class ProcessorBox : public Gtk::HBox, public PluginInterestedObject, public ARD
|
|||
void reordered ();
|
||||
void route_processors_changed (ARDOUR::RouteProcessorChange);
|
||||
|
||||
void remove_processor_gui (boost::shared_ptr<ARDOUR::Processor>);
|
||||
|
||||
void processors_reordered (const Gtk::TreeModel::Path&, const Gtk::TreeModel::iterator&, int*);
|
||||
void compute_processor_sort_keys ();
|
||||
|
||||
|
@ -249,7 +278,6 @@ class ProcessorBox : public Gtk::HBox, public PluginInterestedObject, public ARD
|
|||
|
||||
void activate_processor (boost::shared_ptr<ARDOUR::Processor>);
|
||||
void deactivate_processor (boost::shared_ptr<ARDOUR::Processor>);
|
||||
void edit_processor (boost::shared_ptr<ARDOUR::Processor>);
|
||||
void hide_processor_editor (boost::shared_ptr<ARDOUR::Processor>);
|
||||
void rename_processor (boost::shared_ptr<ARDOUR::Processor>);
|
||||
|
||||
|
@ -281,6 +309,10 @@ class ProcessorBox : public Gtk::HBox, public PluginInterestedObject, public ARD
|
|||
|
||||
void route_property_changed (const PBD::PropertyChange&);
|
||||
std::string generate_processor_title (boost::shared_ptr<ARDOUR::PluginInsert> pi);
|
||||
|
||||
std::list<ProcessorWindowProxy*> _processor_window_proxies;
|
||||
void set_processor_ui (boost::shared_ptr<ARDOUR::Processor>, Gtk::Window *);
|
||||
void maybe_add_processor_to_ui_list (boost::weak_ptr<ARDOUR::Processor>);
|
||||
};
|
||||
|
||||
#endif /* __ardour_gtk_processor_box__ */
|
||||
|
|
|
@ -274,7 +274,7 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulDestructible {
|
|||
virtual TimeAxisView* get_named_time_axis(const std::string & name) = 0;
|
||||
#endif
|
||||
|
||||
virtual RouteTimeAxisView* get_route_view_by_id (PBD::ID& id) = 0;
|
||||
virtual RouteTimeAxisView* get_route_view_by_route_id (PBD::ID& id) const = 0;
|
||||
|
||||
virtual void get_equivalent_regions (RegionView* rv, std::vector<RegionView*>&, PBD::PropertyID) const = 0;
|
||||
|
||||
|
|
|
@ -2275,7 +2275,7 @@ RouteTimeAxisView::set_underlay_state()
|
|||
if (prop) {
|
||||
PBD::ID id (prop->value());
|
||||
|
||||
RouteTimeAxisView* v = _editor.get_route_view_by_id (id);
|
||||
RouteTimeAxisView* v = _editor.get_route_view_by_route_id (id);
|
||||
|
||||
if (v) {
|
||||
add_underlay(v->view(), false);
|
||||
|
|
|
@ -1075,3 +1075,68 @@ Selection::set_point_selection_from_line (AutomationLine const & line)
|
|||
|
||||
PointsChanged (); /* EMIT SIGNAL */
|
||||
}
|
||||
|
||||
XMLNode&
|
||||
Selection::get_state () const
|
||||
{
|
||||
/* XXX: not complete; just sufficient to get track selection state
|
||||
so that re-opening plugin windows for editor mixer strips works
|
||||
*/
|
||||
|
||||
XMLNode* node = new XMLNode (X_("Selection"));
|
||||
|
||||
for (TrackSelection::const_iterator i = tracks.begin(); i != tracks.end(); ++i) {
|
||||
RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*> (*i);
|
||||
AutomationTimeAxisView* atv = dynamic_cast<AutomationTimeAxisView*> (*i);
|
||||
if (rtv) {
|
||||
XMLNode* t = node->add_child (X_("RouteView"));
|
||||
t->add_property (X_("id"), atoi (rtv->route()->id().to_s().c_str()));
|
||||
} else if (atv) {
|
||||
XMLNode* t = node->add_child (X_("AutomationView"));
|
||||
t->add_property (X_("id"), atoi (atv->parent_route()->id().to_s().c_str()));
|
||||
t->add_property (X_("parameter"), EventTypeMap::instance().to_symbol (atv->control()->parameter ()));
|
||||
}
|
||||
}
|
||||
|
||||
return *node;
|
||||
}
|
||||
|
||||
int
|
||||
Selection::set_state (XMLNode const & node, int)
|
||||
{
|
||||
if (node.name() != X_("Selection")) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
XMLNodeList children = node.children ();
|
||||
for (XMLNodeList::const_iterator i = children.begin(); i != children.end(); ++i) {
|
||||
if ((*i)->name() == X_("RouteView")) {
|
||||
|
||||
XMLProperty* prop_id = (*i)->property (X_("id"));
|
||||
assert (prop_id);
|
||||
PBD::ID id (prop_id->value ());
|
||||
RouteTimeAxisView* rtv = editor->get_route_view_by_route_id (id);
|
||||
assert (rtv);
|
||||
add (rtv);
|
||||
|
||||
} else if ((*i)->name() == X_("AutomationView")) {
|
||||
|
||||
XMLProperty* prop_id = (*i)->property (X_("id"));
|
||||
XMLProperty* prop_parameter = (*i)->property (X_("parameter"));
|
||||
|
||||
assert (prop_id);
|
||||
assert (prop_parameter);
|
||||
|
||||
PBD::ID id (prop_id->value ());
|
||||
RouteTimeAxisView* rtv = editor->get_route_view_by_route_id (id);
|
||||
assert (rtv);
|
||||
|
||||
boost::shared_ptr<AutomationTimeAxisView> atv = rtv->automation_child (EventTypeMap::instance().new_parameter (prop_parameter->value ()));
|
||||
assert (atv);
|
||||
|
||||
add (atv.get());
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -191,6 +191,9 @@ class Selection : public sigc::trackable, public PBD::ScopedConnectionList
|
|||
void foreach_midi_regionview (void (MidiRegionView::*method)(void));
|
||||
template<class A> void foreach_region (void (ARDOUR::Region::*method)(A), A arg);
|
||||
|
||||
XMLNode& get_state () const;
|
||||
int set_state (XMLNode const &, int);
|
||||
|
||||
private:
|
||||
void set_point_selection_from_line (AutomationLine const &);
|
||||
|
||||
|
|
|
@ -0,0 +1,150 @@
|
|||
/*
|
||||
Copyright (C) 2010 Paul Davis
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
|
||||
*/
|
||||
|
||||
#include <gtkmm/window.h>
|
||||
#include "window_proxy.h"
|
||||
|
||||
using namespace std;
|
||||
|
||||
/** WindowProxyBase constructor.
|
||||
* @param name Unique internal name for this window.
|
||||
* @param node <UI> node containing <Window> children, the appropriate one of which is used
|
||||
* to set up this object.
|
||||
*/
|
||||
WindowProxyBase::WindowProxyBase (string const & name, XMLNode const * node)
|
||||
: _name (name)
|
||||
, _visible (false)
|
||||
, _x_off (-1)
|
||||
, _y_off (-1)
|
||||
, _width (-1)
|
||||
, _height (-1)
|
||||
{
|
||||
XMLNodeList children = node->children ();
|
||||
|
||||
XMLNodeList::const_iterator i = children.begin ();
|
||||
while (i != children.end()) {
|
||||
XMLProperty* prop = (*i)->property (X_("name"));
|
||||
if ((*i)->name() == X_("Window") && prop && prop->value() == _name) {
|
||||
break;
|
||||
}
|
||||
|
||||
++i;
|
||||
}
|
||||
|
||||
if (i != children.end()) {
|
||||
|
||||
XMLProperty* prop;
|
||||
|
||||
if ((prop = (*i)->property (X_("visible"))) != 0) {
|
||||
_visible = string_is_affirmative (prop->value ());
|
||||
}
|
||||
|
||||
if ((prop = (*i)->property (X_("x-off"))) != 0) {
|
||||
_x_off = atoi (prop->value().c_str());
|
||||
}
|
||||
if ((prop = (*i)->property (X_("y-off"))) != 0) {
|
||||
_y_off = atoi (prop->value().c_str());
|
||||
}
|
||||
if ((prop = (*i)->property (X_("x-size"))) != 0) {
|
||||
_width = atoi (prop->value().c_str());
|
||||
}
|
||||
if ((prop = (*i)->property (X_("y-size"))) != 0) {
|
||||
_height = atoi (prop->value().c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Show this window if it was configured as visible. This should
|
||||
* be called at session startup only.
|
||||
*/
|
||||
void
|
||||
WindowProxyBase::maybe_show ()
|
||||
{
|
||||
if (_visible) {
|
||||
show ();
|
||||
setup ();
|
||||
}
|
||||
}
|
||||
|
||||
/** Set up our window's position and size */
|
||||
void
|
||||
WindowProxyBase::setup ()
|
||||
{
|
||||
Gtk::Window* window = get_gtk_window ();
|
||||
if (!window) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (_width != -1 && _height != -1) {
|
||||
window->set_default_size (_width, _height);
|
||||
}
|
||||
|
||||
if (_x_off != -1 && _y_off != -1) {
|
||||
window->move (_x_off, _y_off);
|
||||
}
|
||||
}
|
||||
|
||||
XMLNode *
|
||||
WindowProxyBase::get_state () const
|
||||
{
|
||||
bool v = _visible;
|
||||
int x = _x_off;
|
||||
int y = _y_off;
|
||||
int w = _width;
|
||||
int h = _height;
|
||||
|
||||
/* If the window has been created, get its current state; otherwise use
|
||||
the state that we started off with.
|
||||
*/
|
||||
|
||||
Gtk::Window* gtk_window = get_gtk_window ();
|
||||
if (gtk_window) {
|
||||
v = gtk_window->is_visible ();
|
||||
|
||||
Glib::RefPtr<Gdk::Window> gdk_window = gtk_window->get_window ();
|
||||
if (gdk_window) {
|
||||
gdk_window->get_position (x, y);
|
||||
gdk_window->get_size (w, h);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return state_node (v, x, y, w, h);
|
||||
}
|
||||
|
||||
|
||||
XMLNode *
|
||||
WindowProxyBase::state_node (bool v, int x, int y, int w, int h) const
|
||||
{
|
||||
XMLNode* node = new XMLNode (X_("Window"));
|
||||
node->add_property (X_("name"), _name);
|
||||
node->add_property (X_("visible"), v ? X_("yes") : X_("no"));
|
||||
|
||||
char buf[32];
|
||||
snprintf (buf, sizeof (buf), "%d", x);
|
||||
node->add_property (X_("x-off"), buf);
|
||||
snprintf (buf, sizeof (buf), "%d", y);
|
||||
node->add_property (X_("y-off"), buf);
|
||||
snprintf (buf, sizeof (buf), "%d", w);
|
||||
node->add_property (X_("x-size"), buf);
|
||||
snprintf (buf, sizeof (buf), "%d", h);
|
||||
node->add_property (X_("y-size"), buf);
|
||||
|
||||
return node;
|
||||
}
|
|
@ -0,0 +1,131 @@
|
|||
/*
|
||||
Copyright (C) 2010 Paul Davis
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
|
||||
*/
|
||||
|
||||
#ifndef __ardour_window_proxy_h__
|
||||
#define __ardour_window_proxy_h__
|
||||
|
||||
#include <gtkmm/action.h>
|
||||
#include <gtkmm/toggleaction.h>
|
||||
#include "actions.h"
|
||||
|
||||
class XMLNode;
|
||||
|
||||
/** A class to proxy for a window that may not have been created yet.
|
||||
* It allows the management of visibility, position and size state
|
||||
* so that it can be saved and restored across session loads.
|
||||
*
|
||||
* Subclasses of WindowProxy handle windows that are created in different
|
||||
* ways.
|
||||
*/
|
||||
|
||||
class WindowProxyBase
|
||||
{
|
||||
public:
|
||||
WindowProxyBase (std::string const &, XMLNode const *);
|
||||
virtual ~WindowProxyBase () {}
|
||||
|
||||
std::string name () const {
|
||||
return _name;
|
||||
}
|
||||
|
||||
void maybe_show ();
|
||||
XMLNode* get_state () const;
|
||||
void setup ();
|
||||
|
||||
/** Show this window */
|
||||
virtual void show () = 0;
|
||||
|
||||
virtual Gtk::Window* get_gtk_window () const = 0;
|
||||
|
||||
private:
|
||||
XMLNode* state_node (bool, int, int, int, int) const;
|
||||
|
||||
std::string _name; ///< internal unique name for this window
|
||||
bool _visible; ///< true if the window should be visible on startup
|
||||
int _x_off; ///< x position
|
||||
int _y_off; ///< y position
|
||||
int _width; ///< width
|
||||
int _height; ///< height
|
||||
};
|
||||
|
||||
/** Templated WindowProxy which contains a pointer to the window that is proxying for */
|
||||
template <class T>
|
||||
class WindowProxy : public WindowProxyBase
|
||||
{
|
||||
public:
|
||||
WindowProxy (std::string const & name, XMLNode const * node)
|
||||
: WindowProxyBase (name, node)
|
||||
, _window (0)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
Gtk::Window* get_gtk_window () const {
|
||||
return _window;
|
||||
}
|
||||
|
||||
T* get () const {
|
||||
return _window;
|
||||
}
|
||||
|
||||
/** Set the window and set it up. To be used after initial window creation */
|
||||
void set (T* w) {
|
||||
_window = w;
|
||||
setup ();
|
||||
}
|
||||
|
||||
private:
|
||||
T* _window;
|
||||
};
|
||||
|
||||
/** WindowProxy for windows that are created in response to a GTK Action being set active.
|
||||
* Templated on the type of the window.
|
||||
*/
|
||||
template <class T>
|
||||
class ActionWindowProxy : public WindowProxy<T>
|
||||
{
|
||||
public:
|
||||
/** ActionWindowProxy constructor.
|
||||
* @param name Unique internal name for this window.
|
||||
* @param node <UI> node containing <Window> children, the appropriate one of which is used
|
||||
* to set up this object.
|
||||
* @param action Name of the ToggleAction that controls this window's visibility.
|
||||
*/
|
||||
ActionWindowProxy (std::string const & name, XMLNode const * node, std::string const & action)
|
||||
: WindowProxy<T> (name, node)
|
||||
, _action (action)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void show () {
|
||||
/* Set the appropriate action active so that the window gets shown */
|
||||
Glib::RefPtr<Gtk::Action> act = ActionManager::get_action ("Common", _action.c_str());
|
||||
if (act) {
|
||||
Glib::RefPtr<Gtk::ToggleAction> tact = Glib::RefPtr<Gtk::ToggleAction>::cast_dynamic (act);
|
||||
assert (tact);
|
||||
tact->set_active (true);
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
std::string _action;
|
||||
};
|
||||
|
||||
#endif
|
|
@ -209,6 +209,7 @@ gtk2_ardour_sources = [
|
|||
'version.cc',
|
||||
'volume_controller.cc',
|
||||
'waveview.cc',
|
||||
'window_proxy.cc'
|
||||
]
|
||||
|
||||
def set_options(opt):
|
||||
|
|
|
@ -95,9 +95,6 @@ class Processor : public SessionObject, public Automatable, public Latent
|
|||
XMLNode& get_state (void);
|
||||
int set_state (const XMLNode&, int version);
|
||||
|
||||
void *get_gui () const { return _gui; }
|
||||
void set_gui (void *p) { _gui = p; }
|
||||
|
||||
void set_pre_fader (bool);
|
||||
|
||||
PBD::Signal0<void> ActiveChanged;
|
||||
|
@ -110,7 +107,6 @@ protected:
|
|||
bool _configured;
|
||||
ChanCount _configured_input;
|
||||
ChanCount _configured_output;
|
||||
void* _gui; /* generic, we don't know or care what this is */
|
||||
bool _display_to_user;
|
||||
bool _pre_fader;
|
||||
|
||||
|
|
|
@ -66,7 +66,6 @@ Processor::Processor(Session& session, const string& name)
|
|||
, _active(false)
|
||||
, _next_ab_is_active(false)
|
||||
, _configured(false)
|
||||
, _gui(0)
|
||||
, _display_to_user (true)
|
||||
, _pre_fader (false)
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue