From 68e943265edf04e63a8e8b8f62bab20f99d9c637 Mon Sep 17 00:00:00 2001 From: Paul Davis Date: Wed, 10 Sep 2008 15:03:30 +0000 Subject: merge from 2.0-ongoing @ 3581 git-svn-id: svn://localhost/ardour2/branches/3.0@3711 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/SConscript | 7 +- gtk2_ardour/actions.cc | 57 +++ gtk2_ardour/actions.h | 5 + gtk2_ardour/analysis_window.cc | 81 ++-- gtk2_ardour/ardour-sae.menus | 16 + gtk2_ardour/ardour.menus | 47 ++- gtk2_ardour/ardour_ui.cc | 217 +++++----- gtk2_ardour/ardour_ui.h | 43 +- gtk2_ardour/ardour_ui2.cc | 8 +- gtk2_ardour/ardour_ui_dialogs.cc | 21 + gtk2_ardour/ardour_ui_ed.cc | 19 + gtk2_ardour/ardour_ui_mixer.cc | 2 + gtk2_ardour/ardour_ui_options.cc | 6 + gtk2_ardour/au_pluginui.mm | 3 + gtk2_ardour/audio_clock.cc | 13 +- gtk2_ardour/audio_clock.h | 1 + gtk2_ardour/audio_region_view.cc | 128 +++--- gtk2_ardour/audio_region_view.h | 15 +- gtk2_ardour/audio_streamview.cc | 27 +- gtk2_ardour/audio_streamview.h | 11 +- gtk2_ardour/audio_time_axis.h | 2 + gtk2_ardour/automation_controller.cc | 2 +- gtk2_ardour/automation_line.cc | 6 +- gtk2_ardour/automation_line.h | 2 +- gtk2_ardour/automation_region_view.cc | 6 +- gtk2_ardour/automation_streamview.cc | 2 +- gtk2_ardour/automation_streamview.h | 7 +- gtk2_ardour/automation_time_axis.cc | 81 ++-- gtk2_ardour/automation_time_axis.h | 5 +- gtk2_ardour/axis_view.h | 5 +- gtk2_ardour/bundle_manager.cc | 2 +- gtk2_ardour/canvas_vars.h | 6 +- gtk2_ardour/crossfade_view.cc | 17 +- gtk2_ardour/editing.cc | 2 +- gtk2_ardour/editor.cc | 566 ++++++++++++++++++++------ gtk2_ardour/editor.h | 216 +++++----- gtk2_ardour/editor_actions.cc | 70 +++- gtk2_ardour/editor_audio_import.cc | 4 +- gtk2_ardour/editor_audiotrack.cc | 1 + gtk2_ardour/editor_canvas.cc | 46 ++- gtk2_ardour/editor_canvas_events.cc | 12 +- gtk2_ardour/editor_cursors.cc | 2 +- gtk2_ardour/editor_export_audio.cc | 27 +- gtk2_ardour/editor_imageframe.cc | 70 ++-- gtk2_ardour/editor_markers.cc | 66 ++- gtk2_ardour/editor_mixer.cc | 8 +- gtk2_ardour/editor_mouse.cc | 206 +++++----- gtk2_ardour/editor_ops.cc | 621 +++++++++++++++++++++-------- gtk2_ardour/editor_region_list.cc | 28 ++ gtk2_ardour/editor_route_list.cc | 36 +- gtk2_ardour/editor_rulers.cc | 98 ++--- gtk2_ardour/editor_selection.cc | 22 +- gtk2_ardour/editor_tempodisplay.cc | 4 +- gtk2_ardour/editor_timefx.cc | 2 - gtk2_ardour/engine_dialog.cc | 50 ++- gtk2_ardour/export_dialog.cc | 8 +- gtk2_ardour/export_range_markers_dialog.cc | 4 +- gtk2_ardour/gain_meter.cc | 548 +++++++++++++------------ gtk2_ardour/gain_meter.h | 72 ++-- gtk2_ardour/ghostregion.cc | 6 +- gtk2_ardour/imageframe_time_axis.cc | 6 +- gtk2_ardour/imageframe_time_axis.h | 4 +- gtk2_ardour/imageframe_time_axis_view.cc | 2 +- gtk2_ardour/imageframe_view.cc | 4 +- gtk2_ardour/io_selector.cc | 73 +++- gtk2_ardour/keyboard.cc | 78 +++- gtk2_ardour/keyboard.h | 21 +- gtk2_ardour/keyeditor.cc | 3 + gtk2_ardour/latency_gui.cc | 1 + gtk2_ardour/latency_gui.h | 2 +- gtk2_ardour/level_meter.cc | 4 + gtk2_ardour/location_ui.cc | 34 +- gtk2_ardour/location_ui.h | 3 + gtk2_ardour/main.cc | 9 + gtk2_ardour/marker.cc | 2 +- gtk2_ardour/marker_time_axis.cc | 9 +- gtk2_ardour/marker_time_axis.h | 4 +- gtk2_ardour/midi_region_view.cc | 42 +- gtk2_ardour/midi_region_view.h | 12 +- gtk2_ardour/midi_streamview.cc | 4 +- gtk2_ardour/midi_streamview.h | 4 +- gtk2_ardour/midi_time_axis.cc | 14 +- gtk2_ardour/mixer_strip.cc | 7 +- gtk2_ardour/mixer_ui.cc | 23 +- gtk2_ardour/mnemonic-us.bindings.in | 39 +- gtk2_ardour/option_editor.cc | 76 ++-- gtk2_ardour/option_editor.h | 2 + gtk2_ardour/panner.cc | 2 +- gtk2_ardour/panner2d.cc | 2 +- gtk2_ardour/panner_ui.cc | 2 +- gtk2_ardour/panner_ui.h | 2 +- gtk2_ardour/plugin_interest.h | 36 ++ gtk2_ardour/plugin_selector.cc | 223 ++++++++++- gtk2_ardour/plugin_selector.h | 22 +- gtk2_ardour/plugin_ui.cc | 15 + gtk2_ardour/plugin_ui.h | 3 + gtk2_ardour/po/sv_SE.po | 565 +++++++++++++++++++++++++- gtk2_ardour/processor_box.cc | 318 +++++++-------- gtk2_ardour/processor_box.h | 39 +- gtk2_ardour/public_editor.cc | 7 +- gtk2_ardour/public_editor.h | 36 +- gtk2_ardour/region_view.cc | 31 +- gtk2_ardour/region_view.h | 1 + gtk2_ardour/rhythm_ferret.cc | 152 ++++++- gtk2_ardour/rhythm_ferret.h | 25 ++ gtk2_ardour/route_params_ui.cc | 8 +- gtk2_ardour/route_time_axis.cc | 231 +++-------- gtk2_ardour/route_time_axis.h | 28 +- gtk2_ardour/route_ui.cc | 6 +- gtk2_ardour/route_ui.h | 4 - gtk2_ardour/send_ui.cc | 9 +- gtk2_ardour/send_ui.h | 3 + gtk2_ardour/sfdb_ui.cc | 25 +- gtk2_ardour/sfdb_ui.h | 1 + gtk2_ardour/streamview.cc | 2 +- gtk2_ardour/streamview.h | 2 +- gtk2_ardour/tape_region_view.cc | 2 +- gtk2_ardour/time_axis_view.cc | 266 +++++++----- gtk2_ardour/time_axis_view.h | 59 +-- gtk2_ardour/time_axis_view_item.cc | 26 +- gtk2_ardour/time_axis_view_item.h | 13 +- gtk2_ardour/ui_config.cc | 8 +- gtk2_ardour/utils.cc | 101 +++-- gtk2_ardour/utils.h | 1 + gtk2_ardour/visual_time_axis.cc | 46 +-- gtk2_ardour/visual_time_axis.h | 4 +- 126 files changed, 4336 insertions(+), 2137 deletions(-) create mode 100644 gtk2_ardour/plugin_interest.h (limited to 'gtk2_ardour') diff --git a/gtk2_ardour/SConscript b/gtk2_ardour/SConscript index ebc4529490..836755c064 100644 --- a/gtk2_ardour/SConscript +++ b/gtk2_ardour/SConscript @@ -6,8 +6,8 @@ import glob Import('env install_prefix final_prefix config_prefix libraries i18n ardour_version') -gtkardour = env.Copy() -gtkmmtests = env.Copy() +gtkardour = env.Clone() +gtkmmtests = env.Clone() # # this defines the version number of the GTK interface to ardour @@ -409,7 +409,7 @@ my_subst_dict = { } keybindings_dict = { } -if gtkardour['GTKOSX'] and gtkardour['NATIVE_OSX_KEYS']: +if gtkardour['GTKOSX']: # # Command(Meta), Alt(Mod1), Ctrl, Shift # **** as of february 4th 2008, OUR VERSION OF ***** @@ -487,6 +487,7 @@ env.Alias('install', env.Install(os.path.join(install_prefix, 'share', 'ardour3' env.Alias('install', env.Install(os.path.join(install_prefix, 'share', 'ardour3', 'pixmaps'), pixmap_files)) env.Alias('install', env.Install(os.path.join(install_prefix, 'share', 'ardour3', 'icons'), icon_files)) env.Alias ('version', gtkardour.VersionBuild(['version.cc','version.h'], [])) +env.Alias ('version', gtkardour.VersionBuild(['version.cc','version.h'], [])) # This will install icons and MIME type as per freedesktop.org specs. # if env['FREEDESKTOP']: diff --git a/gtk2_ardour/actions.cc b/gtk2_ardour/actions.cc index f25dc1c9b2..fcfc6d75ce 100644 --- a/gtk2_ardour/actions.cc +++ b/gtk2_ardour/actions.cc @@ -162,6 +162,50 @@ struct SortActionsByLabel { } }; +void +ActionManager::get_all_actions (vector& groups, vector& names, vector& bindings) +{ + /* the C++ API for functions used here appears to be broken in + gtkmm2.6, so we fall back to the C level. + */ + + GList* list = gtk_ui_manager_get_action_groups (ui_manager->gobj()); + GList* node; + GList* acts; + + for (node = list; node; node = g_list_next (node)) { + + GtkActionGroup* group = (GtkActionGroup*) node->data; + + /* first pass: collect them all */ + + typedef std::list > action_list; + action_list the_acts; + + for (acts = gtk_action_group_list_actions (group); acts; acts = g_list_next (acts)) { + GtkAction* action = (GtkAction*) acts->data; + the_acts.push_back (Glib::wrap (action, true)); + } + + /* now sort by label */ + + SortActionsByLabel cmp; + the_acts.sort (cmp); + + for (action_list::iterator a = the_acts.begin(); a != the_acts.end(); ++a) { + + string accel_path = (*a)->get_accel_path (); + + groups.push_back (gtk_action_group_get_name(group)); + names.push_back (accel_path.substr (accel_path.find_last_of ('/') + 1)); + + AccelKey key; + lookup_entry (accel_path, key); + bindings.push_back (AccelKey (key.get_key(), Gdk::ModifierType (key.get_mod()))); + } + } +} + void ActionManager::get_all_actions (vector& names, vector& paths, vector& keys, vector& bindings) { @@ -226,6 +270,19 @@ ActionManager::get_widget (const char * name) return ui_manager->get_widget (name); } +RefPtr +ActionManager::get_action (const char* path) +{ + GtkAction* _act; + RefPtr act; + + if ((_act = gtk_ui_manager_get_action (ui_manager->gobj(), path)) != 0) { + return Glib::wrap (_act, true); + } + + return act; +} + RefPtr ActionManager::get_action (const char* group_name, const char* action_name) { diff --git a/gtk2_ardour/actions.h b/gtk2_ardour/actions.h index e05f3194bd..d8b2c64eda 100644 --- a/gtk2_ardour/actions.h +++ b/gtk2_ardour/actions.h @@ -70,6 +70,7 @@ class ActionManager static Gtk::Widget* get_widget (const char * name); static Glib::RefPtr get_action (const char* group, const char* name); + static Glib::RefPtr get_action (const char* path); static void add_action_group (Glib::RefPtr); @@ -100,6 +101,10 @@ class ActionManager std::vector& keys, std::vector& bindings); + static void get_all_actions (std::vector& groups, + std::vector& paths, + std::vector& bindings); + static void uncheck_toggleaction (const char * actionname); }; diff --git a/gtk2_ardour/analysis_window.cc b/gtk2_ardour/analysis_window.cc index 8f84febbba..b76a1b356e 100644 --- a/gtk2_ardour/analysis_window.cc +++ b/gtk2_ardour/analysis_window.cc @@ -262,7 +262,8 @@ AnalysisWindow::analyze_data (Gtk::Button *button) continue; RouteUI *rui = dynamic_cast(*i); - + int n_inputs = rui->route()->n_inputs().n_audio(); // FFT is audio only + // Busses don't have playlists, so we need to check that we actually are working with a playlist if (!pl || !rui) continue; @@ -275,29 +276,31 @@ AnalysisWindow::analyze_data (Gtk::Button *button) for (std::list::iterator j = ts.begin(); j != ts.end(); ++j) { - nframes_t i = 0; int n; - - while ( i < (*j).length() ) { - // TODO: What about stereo+ channels? composite all to one, I guess + for (int channel = 0; channel < n_inputs; channel++) { + nframes_t x = 0; - n = fft_graph.windowSize(); + while ( x < (*j).length() ) { + // TODO: What about stereo+ channels? composite all to one, I guess - if (i + n >= (*j).length() ) { - n = (*j).length() - i; - } - - n = pl->read(buf, mixbuf, gain, (*j).start + i, n); - - if ( n < fft_graph.windowSize()) { - for (int j = n; j < fft_graph.windowSize(); j++) { - buf[j] = 0.0; + n = fft_graph.windowSize(); + + if (x + n >= (*j).length() ) { + n = (*j).length() - x; + } + + n = pl->read(buf, mixbuf, gain, (*j).start + x, n, channel); + + if ( n < fft_graph.windowSize()) { + for (int j = n; j < fft_graph.windowSize(); j++) { + buf[j] = 0.0; + } } + + res->analyzeWindow(buf); + + x += n; } - - res->analyzeWindow(buf); - - i += n; } } } else if (source_selection_regions_rb.get_active()) { @@ -316,28 +319,36 @@ AnalysisWindow::analyze_data (Gtk::Button *button) continue; // cerr << " - " << (*j)->region().name() << ": " << (*j)->region().length() << " samples starting at " << (*j)->region().position() << endl; - nframes_t i = 0; int n; + for (int channel = 0; channel < n_inputs; channel++) { - while ( i < arv->region()->length() ) { - // TODO: What about stereo+ channels? composite all to one, I guess + nframes_t x = 0; - n = fft_graph.windowSize(); - if (i + n >= arv->region()->length() ) { - n = arv->region()->length() - i; - } + nframes_t length = arv->region()->length(); - n = arv->audio_region()->read_at(buf, mixbuf, gain, arv->region()->position() + i, n); - - if ( n < fft_graph.windowSize()) { - for (int j = n; j < fft_graph.windowSize(); j++) { - buf[j] = 0.0; + while ( x < length ) { + // TODO: What about stereo+ channels? composite all to one, I guess + + n = fft_graph.windowSize(); + if (x + n >= length ) { + n = length - x; } + + n = arv->audio_region()->read_at(buf, mixbuf, gain, arv->region()->position() + x, n, channel); + + if (n == 0) + break; + + if ( n < fft_graph.windowSize()) { + for (int j = n; j < fft_graph.windowSize(); j++) { + buf[j] = 0.0; + } + } + + res->analyzeWindow(buf); + + x += n; } - - res->analyzeWindow(buf); - - i += n; } // cerr << "Found: " << (*j)->get_item_name() << endl; diff --git a/gtk2_ardour/ardour-sae.menus b/gtk2_ardour/ardour-sae.menus index dc9d7d1b5f..c2721f2a29 100644 --- a/gtk2_ardour/ardour-sae.menus +++ b/gtk2_ardour/ardour-sae.menus @@ -326,6 +326,7 @@ +<<<<<<< .working @@ -339,6 +340,21 @@ +======= + + + + + + + + + + + + + +>>>>>>> .merge-right.r3622 diff --git a/gtk2_ardour/ardour.menus b/gtk2_ardour/ardour.menus index e9b4800ae9..8e316de05c 100644 --- a/gtk2_ardour/ardour.menus +++ b/gtk2_ardour/ardour.menus @@ -56,7 +56,6 @@ - @@ -82,6 +81,8 @@ + + @@ -251,6 +252,14 @@ + + + + + + + + @@ -325,19 +334,38 @@ - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -450,6 +478,7 @@ + @@ -536,7 +565,7 @@ - + diff --git a/gtk2_ardour/ardour_ui.cc b/gtk2_ardour/ardour_ui.cc index 8ca22b2dd5..1e55d2be1f 100644 --- a/gtk2_ardour/ardour_ui.cc +++ b/gtk2_ardour/ardour_ui.cc @@ -25,6 +25,7 @@ #include #include #include +#include #include #include @@ -72,6 +73,8 @@ #include #include +typedef uint64_t microseconds_t; + #include "actions.h" #include "ardour_ui.h" #include "public_editor.h" @@ -88,6 +91,8 @@ #include "gui_thread.h" #include "theme_manager.h" #include "bundle_manager.h" +#include "gain_meter.h" +#include "route_time_axis.h" #include "i18n.h" @@ -114,10 +119,6 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[]) preroll_clock (X_("preroll"), false, X_("PreRollClock"), true, true), postroll_clock (X_("postroll"), false, X_("PostRollClock"), true, true), - /* adjuster table */ - - adjuster_table (3, 3), - /* preroll stuff */ preroll_button (_("pre\nroll")), @@ -129,14 +130,14 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[]) /* transport */ - roll_controllable ("transport roll", *this, TransportControllable::Roll), - stop_controllable ("transport stop", *this, TransportControllable::Stop), - goto_start_controllable ("transport goto start", *this, TransportControllable::GotoStart), - goto_end_controllable ("transport goto end", *this, TransportControllable::GotoEnd), - auto_loop_controllable ("transport auto loop", *this, TransportControllable::AutoLoop), - play_selection_controllable ("transport play selection", *this, TransportControllable::PlaySelection), - rec_controllable ("transport rec-enable", *this, TransportControllable::RecordEnable), - shuttle_controllable ("shuttle", *this, TransportControllable::ShuttleControl), + roll_controllable (new TransportControllable ("transport roll", *this, TransportControllable::Roll)), + stop_controllable (new TransportControllable ("transport stop", *this, TransportControllable::Stop)), + goto_start_controllable (new TransportControllable ("transport goto start", *this, TransportControllable::GotoStart)), + goto_end_controllable (new TransportControllable ("transport goto end", *this, TransportControllable::GotoEnd)), + auto_loop_controllable (new TransportControllable ("transport auto loop", *this, TransportControllable::AutoLoop)), + play_selection_controllable (new TransportControllable ("transport play selection", *this, TransportControllable::PlaySelection)), + rec_controllable (new TransportControllable ("transport rec-enable", *this, TransportControllable::RecordEnable)), + shuttle_controllable (new TransportControllable ("shuttle", *this, TransportControllable::ShuttleControl)), shuttle_controller_binding_proxy (shuttle_controllable), roll_button (roll_controllable), @@ -210,8 +211,7 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[]) last_speed_displayed = -1.0f; ignore_dual_punch = false; - last_configure_time.tv_sec = 0; - last_configure_time.tv_usec = 0; + last_configure_time= 0; shuttle_grabbed = false; shuttle_fract = 0.0; @@ -220,8 +220,9 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[]) shuttle_style_menu = 0; shuttle_unit_menu = 0; - gettimeofday (&last_peak_grab, 0); - gettimeofday (&last_shuttle_request, 0); + // We do not have jack linked in yet so; + + last_shuttle_request = last_peak_grab = 0; // get_microseconds(); ARDOUR::Diskstream::DiskOverrun.connect (mem_fun(*this, &ARDOUR_UI::disk_overrun_handler)); ARDOUR::Diskstream::DiskUnderrun.connect (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler)); @@ -249,6 +250,9 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[]) Config->set_current_owner (ConfigVariableBase::Interface); setup_profile (); + GainMeter::setup_slider_pix (); + RouteTimeAxisView::setup_slider_pix (); + } catch (failed_constructor& err) { error << _("could not initialize Ardour.") << endmsg; // pass it on up @@ -417,21 +421,15 @@ ARDOUR_UI::pop_back_splash () gint ARDOUR_UI::configure_timeout () { - struct timeval now; - struct timeval diff; - - if (last_configure_time.tv_sec == 0 && last_configure_time.tv_usec == 0) { + if (last_configure_time == 0) { /* no configure events yet */ return TRUE; } - gettimeofday (&now, 0); - timersub (&now, &last_configure_time, &diff); - /* force a gap of 0.5 seconds since the last configure event */ - if (diff.tv_sec == 0 && diff.tv_usec < 500000) { + if (get_microseconds() - last_configure_time < 500000) { return TRUE; } else { have_configure_timeout = false; @@ -444,7 +442,7 @@ gboolean ARDOUR_UI::configure_handler (GdkEventConfigure* conf) { if (have_configure_timeout) { - gettimeofday (&last_configure_time, 0); + last_configure_time = get_microseconds(); } else { Glib::signal_timeout().connect (mem_fun(*this, &ARDOUR_UI::configure_timeout), 100); have_configure_timeout = true; @@ -459,28 +457,28 @@ ARDOUR_UI::set_transport_controllable_state (const XMLNode& node) const XMLProperty* prop; if ((prop = node.property ("roll")) != 0) { - roll_controllable.set_id (prop->value()); + roll_controllable->set_id (prop->value()); } if ((prop = node.property ("stop")) != 0) { - stop_controllable.set_id (prop->value()); + stop_controllable->set_id (prop->value()); } if ((prop = node.property ("goto_start")) != 0) { - goto_start_controllable.set_id (prop->value()); + goto_start_controllable->set_id (prop->value()); } if ((prop = node.property ("goto_end")) != 0) { - goto_end_controllable.set_id (prop->value()); + goto_end_controllable->set_id (prop->value()); } if ((prop = node.property ("auto_loop")) != 0) { - auto_loop_controllable.set_id (prop->value()); + auto_loop_controllable->set_id (prop->value()); } if ((prop = node.property ("play_selection")) != 0) { - play_selection_controllable.set_id (prop->value()); + play_selection_controllable->set_id (prop->value()); } if ((prop = node.property ("rec")) != 0) { - rec_controllable.set_id (prop->value()); + rec_controllable->set_id (prop->value()); } if ((prop = node.property ("shuttle")) != 0) { - shuttle_controllable.set_id (prop->value()); + shuttle_controllable->set_id (prop->value()); } } @@ -490,21 +488,21 @@ ARDOUR_UI::get_transport_controllable_state () XMLNode* node = new XMLNode(X_("TransportControllables")); char buf[64]; - roll_controllable.id().print (buf, sizeof (buf)); + roll_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("roll"), buf); - stop_controllable.id().print (buf, sizeof (buf)); + stop_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("stop"), buf); - goto_start_controllable.id().print (buf, sizeof (buf)); + goto_start_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("goto_start"), buf); - goto_end_controllable.id().print (buf, sizeof (buf)); + goto_end_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("goto_end"), buf); - auto_loop_controllable.id().print (buf, sizeof (buf)); + auto_loop_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("auto_loop"), buf); - play_selection_controllable.id().print (buf, sizeof (buf)); + play_selection_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("play_selection"), buf); - rec_controllable.id().print (buf, sizeof (buf)); + rec_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("rec"), buf); - shuttle_controllable.id().print (buf, sizeof (buf)); + shuttle_controllable->id().print (buf, sizeof (buf)); node->add_property (X_("shuttle"), buf); return *node; @@ -544,13 +542,22 @@ ARDOUR_UI::save_ardour_state () gint ARDOUR_UI::autosave_session () { - if (!Config->get_periodic_safety_backups()) + if (g_main_depth() > 1) { + /* inside a recursive main loop, + give up because we may not be able to + take a lock. + */ return 1; + } - if (session) { - session->maybe_write_autosave(); + if (!Config->get_periodic_safety_backups()) { + return 1; } + if (session) { + session->maybe_write_autosave(); + } + return 1; } @@ -796,8 +803,7 @@ ARDOUR_UI::ask_about_saving_session (const string & what) prompt_label.set_name (X_("PrompterLabel")); prompt_label.set_alignment(ALIGN_LEFT, ALIGN_TOP); - dimage->set_alignment(ALIGN_CENTER, ALIGN_TOP) -; + dimage->set_alignment(ALIGN_CENTER, ALIGN_TOP); dhbox.set_homogeneous (false); dhbox.pack_start (*dimage, false, false, 5); dhbox.pack_start (prompt_label, true, false, 5); @@ -812,9 +818,6 @@ ARDOUR_UI::ask_about_saving_session (const string & what) prompt_label.show(); dimage->show(); window.show(); - - save_the_session = 0; - window.set_keep_above (true); window.present (); @@ -1152,33 +1155,6 @@ ARDOUR_UI::open_recent_session () } } -bool -ARDOUR_UI::filter_ardour_session_dirs (const FileFilter::Info& info) -{ - struct stat statbuf; - - if (stat (info.filename.c_str(), &statbuf) != 0) { - return false; - } - - if (!S_ISDIR(statbuf.st_mode)) { - return false; - } - - // XXX Portability - - string session_file = info.filename; - session_file += '/'; - session_file += Glib::path_get_basename (info.filename); - session_file += ".ardour"; - - if (stat (session_file.c_str(), &statbuf) != 0) { - return false; - } - - return S_ISREG (statbuf.st_mode); -} - bool ARDOUR_UI::check_audioengine () { @@ -1401,6 +1377,34 @@ ARDOUR_UI::transport_goto_zero () } } +void +ARDOUR_UI::transport_goto_wallclock () +{ + if (session && editor) { + + time_t now; + struct tm tmnow; + nframes64_t frames; + + time (&now); + localtime_r (&now, &tmnow); + + frames = tmnow.tm_hour * (60 * 60 * session->frame_rate()); + frames += tmnow.tm_min * (60 * session->frame_rate()); + frames += tmnow.tm_sec * session->frame_rate(); + + session->request_locate (frames); + + /* force displayed area in editor to start no matter + what "follow playhead" setting is. + */ + + if (editor) { + editor->reset_x_origin (frames - (editor->current_page_frames()/2)); + } + } +} + void ARDOUR_UI::transport_goto_end () { @@ -1916,17 +1920,6 @@ ARDOUR_UI::save_state_canfail (string name) return 0; } -void -ARDOUR_UI::restore_state (string name) -{ - if (session) { - if (name.length() == 0) { - name = session->name(); - } - session->restore_state (name); - } -} - void ARDOUR_UI::primary_clock_value_changed () { @@ -1951,37 +1944,6 @@ ARDOUR_UI::secondary_clock_value_changed () } } -void -ARDOUR_UI::rec_enable_button_blink (bool onoff, AudioDiskstream *dstream, Widget *w) -{ - if (session && dstream && dstream->record_enabled()) { - - Session::RecordState rs; - - rs = session->record_status (); - - switch (rs) { - case Session::Disabled: - case Session::Enabled: - if (w->get_state() != STATE_SELECTED) { - w->set_state (STATE_SELECTED); - } - break; - - case Session::Recording: - if (w->get_state() != STATE_ACTIVE) { - w->set_state (STATE_ACTIVE); - } - break; - } - - } else { - if (w->get_state() != STATE_NORMAL) { - w->set_state (STATE_NORMAL); - } - } -} - void ARDOUR_UI::transport_rec_enable_blink (bool onoff) { @@ -2352,10 +2314,13 @@ ARDOUR_UI::get_session_parameters (bool backend_audio_is_running, bool should_be fontconfig_dialog(); if (!backend_audio_is_running) { - if (new_session_dialog->engine_control.setup_engine ()) { - new_session_dialog->hide (); + int ret = new_session_dialog->engine_control.setup_engine (); + if (ret < 0) { return false; - } + } else if (ret > 0) { + response = Gtk::RESPONSE_REJECT; + goto try_again; + } } if (create_engine ()) { @@ -2459,7 +2424,7 @@ ARDOUR_UI::get_session_parameters (bool backend_audio_is_running, bool should_be } } - } while (response == Gtk::RESPONSE_NONE); + } while (response == Gtk::RESPONSE_NONE || response == Gtk::RESPONSE_REJECT); done: show(); @@ -2861,8 +2826,11 @@ After cleanup, unused audio files will be moved to a \ } if (session->cleanup_sources (rep)) { + editor->finish_cleanup (); return; } + + editor->finish_cleanup (); checker.hide(); display_cleanup_results (rep, @@ -2876,8 +2844,6 @@ release an additional\n\ %4 %5bytes of disk space.\n" )); - - } void @@ -3024,7 +2990,6 @@ ARDOUR_UI::keyboard_settings () const void ARDOUR_UI::create_xrun_marker(nframes_t where) { - ENSURE_GUI_THREAD (bind(mem_fun(*this, &ARDOUR_UI::create_xrun_marker), where)); editor->mouse_add_new_marker (where, false, true); } @@ -3039,6 +3004,8 @@ ARDOUR_UI::halt_on_xrun_message () void ARDOUR_UI::xrun_handler(nframes_t where) { + ENSURE_GUI_THREAD (bind(mem_fun(*this, &ARDOUR_UI::xrun_handler), where)); + if (Config->get_create_xrun_marker() && session->actively_recording()) { create_xrun_marker(where); } diff --git a/gtk2_ardour/ardour_ui.h b/gtk2_ardour/ardour_ui.h index 442d319f77..6be85f6a80 100644 --- a/gtk2_ardour/ardour_ui.h +++ b/gtk2_ardour/ardour_ui.h @@ -59,6 +59,7 @@ #include #include #include +#include #include "audio_clock.h" #include "ardour_dialog.h" @@ -152,7 +153,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI int save_state_canfail (string state_name = ""); void save_state (const string & state_name = ""); - void restore_state (string state_name = ""); static double gain_to_slider_position (ARDOUR::gain_t g); static ARDOUR::gain_t slider_position_to_gain (double pos); @@ -181,12 +181,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI static sigc::signal SuperRapidScreenUpdate; static sigc::signal Clock; - /* this is a helper function to centralize the (complex) logic for - blinking rec-enable buttons. - */ - - void rec_enable_button_blink (bool onoff, ARDOUR::AudioDiskstream *, Gtk::Widget *w); - void name_io_setup (ARDOUR::AudioEngine&, string&, ARDOUR::IO& io, bool in); static gint hide_and_quit (GdkEventAny *ev, ArdourDialog *); @@ -309,9 +303,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI Gtk::ToggleButton preroll_button; Gtk::ToggleButton postroll_button; - Gtk::Table transport_table; - Gtk::Table option_table; - int setup_windows (); void setup_transport (); void setup_clock (); @@ -324,7 +315,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI void finish(); int ask_about_saving_session (const string & why); - int save_the_session; /* periodic safety backup, to be precise */ gint autosave_session(); @@ -361,9 +351,11 @@ class ARDOUR_UI : public Gtkmm2ext::UI void manage_window (Gtk::Window&); AudioClock big_clock; - Gtk::Frame big_clock_frame; Gtk::Window* big_clock_window; + void float_big_clock (Gtk::Window* parent); + bool main_window_state_event_handler (GdkEventWindowState*, bool window_was_editor); + void update_transport_clocks (nframes_t pos); void record_state_changed (); @@ -412,14 +404,14 @@ class ARDOUR_UI : public Gtkmm2ext::UI ToggleType type; }; - TransportControllable roll_controllable; - TransportControllable stop_controllable; - TransportControllable goto_start_controllable; - TransportControllable goto_end_controllable; - TransportControllable auto_loop_controllable; - TransportControllable play_selection_controllable; - TransportControllable rec_controllable; - TransportControllable shuttle_controllable; + boost::shared_ptr roll_controllable; + boost::shared_ptr stop_controllable; + boost::shared_ptr goto_start_controllable; + boost::shared_ptr goto_end_controllable; + boost::shared_ptr auto_loop_controllable; + boost::shared_ptr play_selection_controllable; + boost::shared_ptr rec_controllable; + boost::shared_ptr shuttle_controllable; BindingProxy shuttle_controller_binding_proxy; void set_transport_controllable_state (const XMLNode&); @@ -589,6 +581,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI void transport_goto_zero (); void transport_goto_start (); void transport_goto_end (); + void transport_goto_wallclock (); void transport_stop (); void transport_stop_and_forget_capture (); void transport_record (bool roll); @@ -675,11 +668,11 @@ class ARDOUR_UI : public Gtkmm2ext::UI void flush_trash (); bool have_configure_timeout; - struct timeval last_configure_time; + ARDOUR::microseconds_t last_configure_time; gint configure_timeout (); - struct timeval last_peak_grab; - struct timeval last_shuttle_request; + ARDOUR::microseconds_t last_peak_grab; + ARDOUR::microseconds_t last_shuttle_request; bool have_disk_speed_dialog_displayed; void disk_speed_dialog_gone (int ignored_response, Gtk::MessageDialog*); @@ -698,9 +691,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI Gtk::MenuItem* jack_reconnect_item; Gtk::Menu* jack_bufsize_menu; - int make_session_clean (); - bool filter_ardour_session_dirs (const Gtk::FileFilter::Info&); - Glib::RefPtr common_actions; void editor_realized (); @@ -742,6 +732,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI void toggle_ShowTrackMeters (); void toggle_only_copy_imported_files (); void toggle_use_narrow_ms(); + void toggle_NameNewMarkers (); void toggle_rubberbanding_snaps_to_grid (); void toggle_auto_analyse_audio (); void toggle_TapeMachineMode(); diff --git a/gtk2_ardour/ardour_ui2.cc b/gtk2_ardour/ardour_ui2.cc index b497d6ab32..568bfb54ed 100644 --- a/gtk2_ardour/ardour_ui2.cc +++ b/gtk2_ardour/ardour_ui2.cc @@ -773,17 +773,13 @@ ARDOUR_UI::set_shuttle_fract (double f) void ARDOUR_UI::use_shuttle_fract (bool force) { - struct timeval now; - struct timeval diff; + microseconds_t now = get_microseconds(); /* do not attempt to submit a motion-driven transport speed request more than once per process cycle. */ - gettimeofday (&now, 0); - timersub (&now, &last_shuttle_request, &diff); - - if (!force && (diff.tv_usec + (diff.tv_sec * 1000000)) < engine->usecs_per_cycle()) { + if (!force && (last_shuttle_request - now) < (microseconds_t) engine->usecs_per_cycle()) { return; } diff --git a/gtk2_ardour/ardour_ui_dialogs.cc b/gtk2_ardour/ardour_ui_dialogs.cc index 32b9f5adc7..f87ce85476 100644 --- a/gtk2_ardour/ardour_ui_dialogs.cc +++ b/gtk2_ardour/ardour_ui_dialogs.cc @@ -433,3 +433,24 @@ ARDOUR_UI::handle_locations_change (Location* ignored) } } } + +bool +ARDOUR_UI::main_window_state_event_handler (GdkEventWindowState* ev, bool window_was_editor) +{ + if (window_was_editor) { + + if ((ev->changed_mask & GDK_WINDOW_STATE_FULLSCREEN) && + (ev->new_window_state & GDK_WINDOW_STATE_FULLSCREEN)) { + float_big_clock (editor); + } + + } else { + + if ((ev->changed_mask & GDK_WINDOW_STATE_FULLSCREEN) && + (ev->new_window_state & GDK_WINDOW_STATE_FULLSCREEN)) { + float_big_clock (mixer); + } + } + + return false; +} diff --git a/gtk2_ardour/ardour_ui_ed.cc b/gtk2_ardour/ardour_ui_ed.cc index 7eb13892ee..504205dbf4 100644 --- a/gtk2_ardour/ardour_ui_ed.cc +++ b/gtk2_ardour/ardour_ui_ed.cc @@ -30,6 +30,7 @@ #include #include +#include #include "ardour_ui.h" #include "public_editor.h" @@ -73,6 +74,7 @@ ARDOUR_UI::create_editor () } editor->Realized.connect (mem_fun (*this, &ARDOUR_UI::editor_realized)); + editor->signal_window_state_event().connect (sigc::bind (mem_fun (*this, &ARDOUR_UI::main_window_state_event_handler), true)); return 0; } @@ -303,6 +305,9 @@ ARDOUR_UI::install_actions () act = ActionManager::register_action (transport_actions, X_("GotoEnd"), _("Goto End"), mem_fun(*this, &ARDOUR_UI::transport_goto_end)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); + act = ActionManager::register_action (transport_actions, X_("GotoWallClock"), _("Goto Wall Clock"), mem_fun(*this, &ARDOUR_UI::transport_goto_wallclock)); + ActionManager::session_sensitive_actions.push_back (act); + ActionManager::transport_sensitive_actions.push_back (act); act = ActionManager::register_action (transport_actions, X_("focus-on-clock"), _("Focus On Clock"), mem_fun(primary_clock, &AudioClock::focus)); ActionManager::session_sensitive_actions.push_back (act); @@ -460,6 +465,7 @@ ARDOUR_UI::install_actions () ActionManager::register_toggle_action (option_actions, X_("AutoAnalyseAudio"), _("Auto-analyse new audio"), mem_fun (*this, &ARDOUR_UI::toggle_auto_analyse_audio)); ActionManager::register_toggle_action (option_actions, X_("DefaultNarrowMS"), _("Use narrow mixer strips"), mem_fun (*this, &ARDOUR_UI::toggle_use_narrow_ms)); + ActionManager::register_toggle_action (option_actions, X_("NameNewMarkers"), _("Name New Markers"), mem_fun (*this, &ARDOUR_UI::toggle_NameNewMarkers)); RadioAction::Group denormal_group; @@ -864,3 +870,16 @@ ARDOUR_UI::setup_clock () manage_window (*big_clock_window); } + +void +ARDOUR_UI::float_big_clock (Gtk::Window* parent) +{ + if (big_clock_window) { + if (parent) { + big_clock_window->set_transient_for (*parent); + } else { + gtk_window_set_transient_for (big_clock_window->gobj(), (GtkWindow*) 0); + } + } +} + diff --git a/gtk2_ardour/ardour_ui_mixer.cc b/gtk2_ardour/ardour_ui_mixer.cc index dfc5d644b0..6373bc8b8c 100644 --- a/gtk2_ardour/ardour_ui_mixer.cc +++ b/gtk2_ardour/ardour_ui_mixer.cc @@ -41,6 +41,8 @@ ARDOUR_UI::create_mixer () return -1; } + mixer->signal_window_state_event().connect (bind (mem_fun (*this, &ARDOUR_UI::main_window_state_event_handler), false)); + return 0; } diff --git a/gtk2_ardour/ardour_ui_options.cc b/gtk2_ardour/ardour_ui_options.cc index 75d33d9416..4c1aae1583 100644 --- a/gtk2_ardour/ardour_ui_options.cc +++ b/gtk2_ardour/ardour_ui_options.cc @@ -587,6 +587,12 @@ ARDOUR_UI::toggle_use_narrow_ms() ActionManager::toggle_config_state ("options", "DefaultNarrowMS", &Configuration::set_default_narrow_ms, &Configuration::get_default_narrow_ms); } +void +ARDOUR_UI::toggle_NameNewMarkers() +{ + ActionManager::toggle_config_state ("options", "NameNewMarkers", &Configuration::set_name_new_markers, &Configuration::get_name_new_markers); +} + void ARDOUR_UI::toggle_rubberbanding_snaps_to_grid () { diff --git a/gtk2_ardour/au_pluginui.mm b/gtk2_ardour/au_pluginui.mm index ab14d4aafd..977e5762a7 100644 --- a/gtk2_ardour/au_pluginui.mm +++ b/gtk2_ardour/au_pluginui.mm @@ -518,6 +518,8 @@ AUPluginUI::parent_cocoa_window () return -1; } + [win setAutodisplay:YES]; // turn of GTK stuff for this window + Gtk::Container* toplevel = get_toplevel(); if (!toplevel || !toplevel->is_toplevel()) { @@ -530,6 +532,7 @@ AUPluginUI::parent_cocoa_window () NSView* view = gdk_quartz_window_get_nsview (low_box.get_window()->gobj()); + [view setFrame:packFrame]; [view addSubview:packView]; diff --git a/gtk2_ardour/audio_clock.cc b/gtk2_ardour/audio_clock.cc index 5ce5159e72..a3dbc1d3d0 100644 --- a/gtk2_ardour/audio_clock.cc +++ b/gtk2_ardour/audio_clock.cc @@ -828,13 +828,15 @@ AudioClock::field_key_release_event (GdkEventKey *ev, Field field) break; case GDK_Tab: + case GDK_Return: + case GDK_KP_Enter: move_on = true; break; case GDK_Escape: - case GDK_Return: - case GDK_KP_Enter: + key_entry_state = 0; clock_base.grab_focus (); + ChangeAborted(); /* EMIT SIGNAL */ return true; default: @@ -960,6 +962,13 @@ AudioClock::field_key_release_event (GdkEventKey *ev, Field field) } + //if user hit Enter, lose focus + switch (ev->keyval) { + case GDK_Return: + case GDK_KP_Enter: + clock_base.grab_focus (); + } + return true; } diff --git a/gtk2_ardour/audio_clock.h b/gtk2_ardour/audio_clock.h index 426b2f02fc..fe3eef30dc 100644 --- a/gtk2_ardour/audio_clock.h +++ b/gtk2_ardour/audio_clock.h @@ -61,6 +61,7 @@ class AudioClock : public Gtk::HBox void set_session (ARDOUR::Session *s); sigc::signal ValueChanged; + sigc::signal ChangeAborted; static sigc::signal ModeChanged; static std::vector clocks; diff --git a/gtk2_ardour/audio_region_view.cc b/gtk2_ardour/audio_region_view.cc index e66b184adb..3a269c04bc 100644 --- a/gtk2_ardour/audio_region_view.cc +++ b/gtk2_ardour/audio_region_view.cc @@ -78,9 +78,10 @@ AudioRegionView::AudioRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView { } + AudioRegionView::AudioRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView &tv, boost::shared_ptr r, double spu, - Gdk::Color& basic_color, TimeAxisViewItem::Visibility visibility) - : RegionView (parent, tv, r, spu, basic_color, visibility) + Gdk::Color& basic_color, bool recording, TimeAxisViewItem::Visibility visibility) + : RegionView (parent, tv, r, spu, basic_color, recording, visibility) , sync_mark(0) , zero_line(0) , fade_in_shape(0) @@ -213,7 +214,7 @@ AudioRegionView::init (Gdk::Color& basic_color, bool wfd) gain_line->reset (); - set_y_position_and_height (0, trackview.height); + set_y_position_and_height (0, trackview.current_height()); region_muted (); region_sync_changed (); @@ -264,6 +265,7 @@ void AudioRegionView::region_changed (Change what_changed) { ENSURE_GUI_THREAD (bind (mem_fun(*this, &AudioRegionView::region_changed), what_changed)); + //cerr << "AudioRegionView::region_changed() called" << endl; RegionView::region_changed(what_changed); @@ -434,32 +436,53 @@ AudioRegionView::region_muted () } void -AudioRegionView::set_y_position_and_height (double y, double h) +AudioRegionView::setup_fade_handle_positions() { - RegionView::set_y_position_and_height(y, h - 1); + /* position of fade handle offset from the top of the region view */ + double const handle_pos = 2; + /* height of fade handles */ + double const handle_height = 5; + + if (fade_in_handle) { + fade_in_handle->property_y1() = _y_position + handle_pos; + fade_in_handle->property_y2() = _y_position + handle_pos + handle_height; + } - const uint32_t wcnt = waves.size(); + if (fade_out_handle) { + fade_out_handle->property_y1() = _y_position + handle_pos; + fade_out_handle->property_y2() = _y_position + handle_pos + handle_height; + } +} + +void +AudioRegionView::set_y_position_and_height (double y, double h) +{ + RegionView::set_y_position_and_height (y, h - 1); + + /* XXX why is this code here */ _y_position = y; _height = h; - for (uint32_t n = 0; n < wcnt; ++n) { - double ht; + const uint32_t wcnt = waves.size(); + + for (uint32_t n=0; n < wcnt; ++n) { + gdouble ht; - if (h <= NAME_HIGHLIGHT_THRESH) { - ht = ((_height - 2 * wcnt) / (double) wcnt); + if ((h) < NAME_HIGHLIGHT_THRESH) { + ht = ((_height-2*wcnt) / (double) wcnt); } else { - ht = (((_height - 2 * wcnt) - NAME_HIGHLIGHT_SIZE) / (double) wcnt); + ht = (((_height-2*wcnt) - NAME_HIGHLIGHT_SIZE) / (double) wcnt); } - double const yoff = n * (ht + 1); + gdouble yoff = n * (ht+1); waves[n]->property_height() = ht; - waves[n]->property_y() = _y_position + yoff + 2; + waves[n]->property_y() = yoff + 2; } if (gain_line) { - if ((_height / wcnt) < NAME_HIGHLIGHT_SIZE) { + if ((_height/wcnt) < NAME_HIGHLIGHT_THRESH) { gain_line->hide (); } else { if (_flags & EnvelopeVisible) { @@ -469,7 +492,6 @@ AudioRegionView::set_y_position_and_height (double y, double h) gain_line->set_y_position_and_height ((uint32_t) _y_position, (uint32_t) rint (_height - NAME_HIGHLIGHT_SIZE)); } - setup_fade_handle_positions (); manage_zero_line (); reset_fade_shapes (); @@ -478,25 +500,6 @@ AudioRegionView::set_y_position_and_height (double y, double h) } } -void -AudioRegionView::setup_fade_handle_positions() -{ - /* position of fade handle offset from the top of the region view */ - double const handle_pos = 2; - /* height of fade handles */ - double const handle_height = 5; - - if (fade_in_handle) { - fade_in_handle->property_y1() = _y_position + handle_pos; - fade_in_handle->property_y2() = _y_position + handle_pos + handle_height; - } - - if (fade_out_handle) { - fade_out_handle->property_y1() = _y_position + handle_pos; - fade_out_handle->property_y2() = _y_position + handle_pos + handle_height; - } -} - void AudioRegionView::manage_zero_line () { @@ -573,7 +576,7 @@ AudioRegionView::reset_fade_in_shape_width (nframes_t width) points = get_canvas_points ("fade in shape", npoints+3); - if (_height > NAME_HIGHLIGHT_THRESH) { + if (_height >= NAME_HIGHLIGHT_THRESH) { h = _height - NAME_HIGHLIGHT_SIZE; } else { h = _height; @@ -657,7 +660,7 @@ AudioRegionView::reset_fade_out_shape_width (nframes_t width) float curve[npoints]; audio_region()->fade_out()->curve().get_vector (0, audio_region()->fade_out()->back()->when, curve, npoints); - if (_height > NAME_HIGHLIGHT_THRESH) { + if (_height >= NAME_HIGHLIGHT_THRESH) { h = _height - NAME_HIGHLIGHT_SIZE; } else { h = _height; @@ -853,6 +856,7 @@ AudioRegionView::create_waves () if (audio_region()->audio_source(n)->peaks_ready (bind (mem_fun(*this, &AudioRegionView::peaks_ready_handler), n), data_ready_connection)) { // cerr << "\tData is ready\n"; cerr << "\tData is ready\n"; + // cerr << "\tData is ready\n"; create_one_wave (n, true); } else { // cerr << "\tdata is not ready\n"; @@ -878,10 +882,10 @@ AudioRegionView::create_one_wave (uint32_t which, bool direct) uint32_t nwaves = std::min (nchans, audio_region()->n_channels()); gdouble ht; - if (trackview.height < NAME_HIGHLIGHT_SIZE) { - ht = ((trackview.height) / (double) nchans); + if (trackview.current_height() < NAME_HIGHLIGHT_THRESH) { + ht = ((trackview.current_height()) / (double) nchans); } else { - ht = ((trackview.height - NAME_HIGHLIGHT_SIZE) / (double) nchans); + ht = ((trackview.current_height() - NAME_HIGHLIGHT_SIZE) / (double) nchans); } gdouble yoff = which * ht; @@ -900,8 +904,15 @@ AudioRegionView::create_one_wave (uint32_t which, bool direct) wave->property_height() = (double) ht; wave->property_samples_per_unit() = samples_per_unit; wave->property_amplitude_above_axis() = _amplitude_above_axis; - wave->property_wave_color() = _region->muted() ? UINT_RGBA_CHANGE_A(ARDOUR_UI::config()->canvasvar_WaveForm.get(), MUTED_ALPHA) : ARDOUR_UI::config()->canvasvar_WaveForm.get(); - wave->property_fill_color() = ARDOUR_UI::config()->canvasvar_WaveFormFill.get(); + + if (_recregion) { + wave->property_wave_color() = _region->muted() ? UINT_RGBA_CHANGE_A(ARDOUR_UI::config()->canvasvar_RecWaveForm.get(), MUTED_ALPHA) : ARDOUR_UI::config()->canvasvar_RecWaveForm.get(); + wave->property_fill_color() = ARDOUR_UI::config()->canvasvar_RecWaveFormFill.get(); + } else { + wave->property_wave_color() = _region->muted() ? UINT_RGBA_CHANGE_A(ARDOUR_UI::config()->canvasvar_WaveForm.get(), MUTED_ALPHA) : ARDOUR_UI::config()->canvasvar_WaveForm.get(); + wave->property_fill_color() = ARDOUR_UI::config()->canvasvar_WaveFormFill.get(); + } + wave->property_clip_color() = ARDOUR_UI::config()->canvasvar_WaveFormClip.get(); wave->property_zero_color() = ARDOUR_UI::config()->canvasvar_ZeroLine.get(); wave->property_region_start() = _region->start(); @@ -986,7 +997,7 @@ AudioRegionView::add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) /* compute vertical fractional position */ - y = 1.0 - ((y - _y_position) / (_height - NAME_HIGHLIGHT_SIZE)); + y = 1.0 - (y / (trackview.current_height() - NAME_HIGHLIGHT_SIZE)); /* map using gain line */ @@ -1275,16 +1286,31 @@ AudioRegionView::set_frame_color () } } } else { - UINT_TO_RGBA(ARDOUR_UI::config()->canvasvar_FrameBase.get(), &r, &g, &b, &a); - frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, fill_opacity ? fill_opacity : a); - - for (vector::iterator w = waves.begin(); w != waves.end(); ++w) { - if (_region->muted()) { - (*w)->property_wave_color() = UINT_RGBA_CHANGE_A(ARDOUR_UI::config()->canvasvar_WaveForm.get(), MUTED_ALPHA); - } else { - (*w)->property_wave_color() = ARDOUR_UI::config()->canvasvar_WaveForm.get(); - (*w)->property_fill_color() = ARDOUR_UI::config()->canvasvar_WaveFormFill.get(); + if (_recregion) { + UINT_TO_RGBA(ARDOUR_UI::config()->canvasvar_RecordingRect.get(), &r, &g, &b, &a); + frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, a); + + for (vector::iterator w = waves.begin(); w != waves.end(); ++w) { + if (_region->muted()) { + (*w)->property_wave_color() = UINT_RGBA_CHANGE_A(ARDOUR_UI::config()->canvasvar_RecWaveForm.get(), MUTED_ALPHA); + } else { + (*w)->property_wave_color() = ARDOUR_UI::config()->canvasvar_RecWaveForm.get(); + (*w)->property_fill_color() = ARDOUR_UI::config()->canvasvar_RecWaveFormFill.get(); + } + } + } else { + UINT_TO_RGBA(ARDOUR_UI::config()->canvasvar_FrameBase.get(), &r, &g, &b, &a); + frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, fill_opacity ? fill_opacity : a); + + for (vector::iterator w = waves.begin(); w != waves.end(); ++w) { + if (_region->muted()) { + (*w)->property_wave_color() = UINT_RGBA_CHANGE_A(ARDOUR_UI::config()->canvasvar_WaveForm.get(), MUTED_ALPHA); + } else { + (*w)->property_wave_color() = ARDOUR_UI::config()->canvasvar_WaveForm.get(); + (*w)->property_fill_color() = ARDOUR_UI::config()->canvasvar_WaveFormFill.get(); + } } } } } + diff --git a/gtk2_ardour/audio_region_view.h b/gtk2_ardour/audio_region_view.h index 58e3c7fce6..d93534cff7 100644 --- a/gtk2_ardour/audio_region_view.h +++ b/gtk2_ardour/audio_region_view.h @@ -54,6 +54,14 @@ class AudioRegionView : public RegionView double initial_samples_per_unit, Gdk::Color& basic_color); + AudioRegionView (ArdourCanvas::Group *, + RouteTimeAxisView&, + boost::shared_ptr, + double samples_per_unit, + Gdk::Color& basic_color, + bool recording, + TimeAxisViewItem::Visibility); + AudioRegionView (const AudioRegionView& other); AudioRegionView (const AudioRegionView& other, boost::shared_ptr); @@ -108,13 +116,6 @@ class AudioRegionView : public RegionView to the TimeAxisViewItem parent class */ - AudioRegionView (ArdourCanvas::Group *, - RouteTimeAxisView&, - boost::shared_ptr, - double samples_per_unit, - Gdk::Color& basic_color, - TimeAxisViewItem::Visibility); - enum Flags { EnvelopeVisible = 0x1, WaveformVisible = 0x4, diff --git a/gtk2_ardour/audio_streamview.cc b/gtk2_ardour/audio_streamview.cc index 08ac532319..0e3dda0bd6 100644 --- a/gtk2_ardour/audio_streamview.cc +++ b/gtk2_ardour/audio_streamview.cc @@ -112,7 +112,7 @@ AudioStreamView::set_amplitude_above_axis (gdouble app) } RegionView* -AudioStreamView::add_region_view_internal (boost::shared_ptr r, bool wait_for_waves) +AudioStreamView::add_region_view_internal (boost::shared_ptr r, bool wait_for_waves, bool recording) { AudioRegionView *region_view = 0; @@ -142,8 +142,13 @@ AudioStreamView::add_region_view_internal (boost::shared_ptr r, bool wai switch (_trackview.audio_track()->mode()) { case Normal: - region_view = new AudioRegionView (canvas_group, _trackview, region, + if (recording) { + region_view = new AudioRegionView (canvas_group, _trackview, region, + _samples_per_unit, region_color, recording, TimeAxisViewItem::Visibility(TimeAxisViewItem::ShowFrame | TimeAxisViewItem::HideFrameRight)); + } else { + region_view = new AudioRegionView (canvas_group, _trackview, region, _samples_per_unit, region_color); + } break; case Destructive: region_view = new TapeAudioRegionView (canvas_group, _trackview, region, @@ -159,7 +164,6 @@ AudioStreamView::add_region_view_internal (boost::shared_ptr r, bool wai region_view->set_amplitude_above_axis(_amplitude_above_axis); region_views.push_front (region_view); - /* if its the special single-sample length that we use for rec-regions, make it insensitive to events */ @@ -456,7 +460,7 @@ AudioStreamView::redisplay_diskstream () for (RegionViewList::iterator j = copy.begin(); j != copy.end(); ++j) { (*j)->enable_display(true); - (*j)->set_y_position_and_height(0, height); + (*j)->set_height (height); region_layered (*j); } } @@ -497,7 +501,7 @@ AudioStreamView::set_waveform_scale (WaveformScale scale) void AudioStreamView::setup_rec_box () { - // cerr << _trackview.name() << " streamview SRB\n"; + //cerr << _trackview.name() << " streamview SRB region_views.size() = " << region_views.size() << endl; if (_trackview.session().transport_rolling()) { @@ -506,7 +510,6 @@ AudioStreamView::setup_rec_box () if (!rec_active && _trackview.session().record_status() == Session::Recording && _trackview.get_diskstream()->record_enabled()) { - if (_trackview.audio_track()->mode() == Normal && use_rec_regions && rec_regions.size() == rec_rects.size()) { /* add a new region, but don't bother if they set use_rec_regions mid-record */ @@ -578,8 +581,9 @@ AudioStreamView::setup_rec_box () rec_rect->property_x1() = xstart; rec_rect->property_y1() = 1.0; rec_rect->property_x2() = xend; - rec_rect->property_y2() = (double) _trackview.height - 1; - rec_rect->property_outline_color_rgba() = ARDOUR_UI::config()->canvasvar_RecordingRect.get(); + rec_rect->property_y2() = (double) _trackview.current_height() - 1; + rec_rect->property_outline_color_rgba() = ARDOUR_UI::config()->canvasvar_TimeAxisFrame.get(); + rec_rect->property_outline_what() = 0x1 | 0x2 | 0x4 | 0x8; rec_rect->property_fill_color_rgba() = fill_color; rec_rect->lower_to_bottom(); @@ -598,11 +602,9 @@ AudioStreamView::setup_rec_box () } else if (rec_active && (_trackview.session().record_status() != Session::Recording || !_trackview.get_diskstream()->record_enabled())) { - screen_update_connection.disconnect(); rec_active = false; rec_updating = false; - } } else { @@ -688,7 +690,6 @@ void AudioStreamView::update_rec_regions () { if (use_rec_regions) { - uint32_t n = 0; for (list,RegionView*> >::iterator iter = rec_regions.begin(); iter != rec_regions.end(); n++) { @@ -726,7 +727,7 @@ AudioStreamView::update_rec_regions () if (origlen == 1) { /* our special initial length */ - add_region_view_internal (region, false); + add_region_view_internal (region, false, true); } /* also update rect */ @@ -751,7 +752,7 @@ AudioStreamView::update_rec_regions () if (origlen == 1) { /* our special initial length */ - add_region_view_internal (region, false); + add_region_view_internal (region, false, true); } /* also hide rect */ diff --git a/gtk2_ardour/audio_streamview.h b/gtk2_ardour/audio_streamview.h index 326a05f240..74868ea1a2 100644 --- a/gtk2_ardour/audio_streamview.h +++ b/gtk2_ardour/audio_streamview.h @@ -82,7 +82,7 @@ class AudioStreamView : public StreamView void rec_peak_range_ready (nframes_t start, nframes_t cnt, boost::weak_ptr src); void update_rec_regions (); - RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_waves); + RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_waves, bool recording = false); void remove_region_view (boost::weak_ptr ); void remove_audio_region_view (boost::shared_ptr ); @@ -106,10 +106,15 @@ class AudioStreamView : public StreamView CrossfadeViewList crossfade_views; bool crossfades_visible; + + std::list rec_data_ready_connections; + nframes_t last_rec_data_frame; + map, bool> rec_data_ready_map; + + bool outline_region; + Editing::WaveformShape _waveform_shape; Editing::WaveformScale _waveform_scale; - - map, bool> rec_data_ready_map; }; #endif /* __ardour_audio_streamview_h__ */ diff --git a/gtk2_ardour/audio_time_axis.h b/gtk2_ardour/audio_time_axis.h index 565d7cda9f..1b090d881e 100644 --- a/gtk2_ardour/audio_time_axis.h +++ b/gtk2_ardour/audio_time_axis.h @@ -86,6 +86,8 @@ class AudioTimeAxisView : public RouteTimeAxisView void first_idle (); + XMLNode* get_child_xml_node (const string & childname); + void set_waveform_shape (Editing::WaveformShape); void set_waveform_scale (Editing::WaveformScale); diff --git a/gtk2_ardour/automation_controller.cc b/gtk2_ardour/automation_controller.cc index dfbdb30ffe..0bf1482224 100644 --- a/gtk2_ardour/automation_controller.cc +++ b/gtk2_ardour/automation_controller.cc @@ -33,7 +33,7 @@ using namespace Gtk; AutomationController::AutomationController(boost::shared_ptr ac, Adjustment* adj) - : BarController(*adj, *ac) + : BarController(*adj, ac) , _ignore_change(false) , _controllable(ac) , _adjustment(adj) diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc index 8c721c7e84..b112a9481e 100644 --- a/gtk2_ardour/automation_line.cc +++ b/gtk2_ardour/automation_line.cc @@ -154,17 +154,17 @@ AutomationLine::control_point_box_size () } void -AutomationLine::set_y_position_and_height (guint32 y, guint32 h) +AutomationLine::set_y_position_and_height (double y, double h) { bool changed = false; if (y != _y_position) { - _y_position = y; + _y_position = (guint32) floor (y); changed = true; } if (h != _height) { - _height = h; + _height = (guint32) floor (h); double const bsz = control_point_box_size(); diff --git a/gtk2_ardour/automation_line.h b/gtk2_ardour/automation_line.h index 6ce548e55d..9e35903671 100644 --- a/gtk2_ardour/automation_line.h +++ b/gtk2_ardour/automation_line.h @@ -94,7 +94,7 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin void show (); void hide (); - void set_y_position_and_height (uint32_t, uint32_t); + void set_y_position_and_height (double, double); void set_verbose_cursor_uses_gain_mapping (bool yn); TimeAxisView& trackview; diff --git a/gtk2_ardour/automation_region_view.cc b/gtk2_ardour/automation_region_view.cc index f0dc23e043..0ba14398e6 100644 --- a/gtk2_ardour/automation_region_view.cc +++ b/gtk2_ardour/automation_region_view.cc @@ -53,7 +53,7 @@ AutomationRegionView::init (Gdk::Color& basic_color, bool wfd) reset_width_dependent_items ((double) _region->length() / samples_per_unit); - set_y_position_and_height (0, trackview.height); + set_height (trackview.current_height()); _region->StateChanged.connect (mem_fun(*this, &AutomationRegionView::region_changed)); @@ -90,8 +90,8 @@ AutomationRegionView::add_automation_event (GdkEvent* event, nframes_t when, dou /* compute vertical fractional position */ - const double height = trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE - 2; - y = 1.0 - (y / height); + const double h = trackview.current_height() - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE - 2; + y = 1.0 - (y / h); /* map using line */ diff --git a/gtk2_ardour/automation_streamview.cc b/gtk2_ardour/automation_streamview.cc index d068c51e5e..5803d283dc 100644 --- a/gtk2_ardour/automation_streamview.cc +++ b/gtk2_ardour/automation_streamview.cc @@ -70,7 +70,7 @@ AutomationStreamView::~AutomationStreamView () RegionView* -AutomationStreamView::add_region_view_internal (boost::shared_ptr region, bool wfd) +AutomationStreamView::add_region_view_internal (boost::shared_ptr region, bool wfd, bool recording) { if ( ! region) { cerr << "No region" << endl; diff --git a/gtk2_ardour/automation_streamview.h b/gtk2_ardour/automation_streamview.h index c5eac37021..5eebfaf28d 100644 --- a/gtk2_ardour/automation_streamview.h +++ b/gtk2_ardour/automation_streamview.h @@ -51,15 +51,16 @@ class AutomationStreamView : public StreamView void redisplay_diskstream (); - inline double contents_height() const - { return (_trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE - 2); } + inline double contents_height() const { + return (_trackview.current_height() - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE - 2); + } private: void setup_rec_box (); void rec_data_range_ready (jack_nframes_t start, jack_nframes_t dur); void update_rec_regions (jack_nframes_t start, jack_nframes_t dur); - RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_data); + RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_data, bool recording = false); void display_region(AutomationRegionView* region_view); void color_handler (); diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index 099a36c822..36d615453c 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -373,15 +373,19 @@ AutomationTimeAxisView::clear_clicked () } void -AutomationTimeAxisView::set_height (TrackHeight ht) +AutomationTimeAxisView::set_height (uint32_t h) { - uint32_t h = height_to_pixels (ht); bool changed = (height != (uint32_t) h) || first_call_to_set_height; if (first_call_to_set_height) first_call_to_set_height = false; + bool changed_between_small_and_normal = ( (h == hSmall || h == hSmaller) ^ (height == hSmall || height == hSmaller) ); - TimeAxisView::set_height (ht); + TimeAxisView* state_parent = get_parent_with_state (); + assert(state_parent); + XMLNode* xml_node = state_parent->get_automation_child_xml_node (_control->parameter()); + + TimeAxisView::set_height (h); _base_rect->property_y2() = h; if (_line) @@ -392,50 +396,16 @@ AutomationTimeAxisView::set_height (TrackHeight ht) _view->update_contents_y_position_and_height(); } - TimeAxisView* state_parent = get_parent_with_state (); - assert(state_parent); + char buf[32]; + snprintf (buf, sizeof (buf), "%u", height); + xml_node->add_property ("height", buf); - XMLNode* xml_node = state_parent->get_automation_child_xml_node(_control->parameter()); - assert(xml_node); - - switch (ht) { - case Largest: - xml_node->add_property ("track_height", "largest"); - break; - - case Large: - xml_node->add_property ("track_height", "large"); - break; - - case Larger: - xml_node->add_property ("track_height", "larger"); - break; - - case Normal: - xml_node->add_property ("track_height", "normal"); - break; - - case Smaller: - xml_node->add_property ("track_height", "smaller"); - break; - - case Small: - xml_node->add_property ("track_height", "small"); - break; - } - - switch (ht) { - case Large: - case Larger: - case Largest: - _controller->show (); - - case Normal: - if (ht == Normal) - _controller->hide(); + if (changed_between_small_and_normal || first_call_to_set_height) { + first_call_to_set_height = false; + if (h >= hNormal) { controls_table.remove (name_hbox); - + if (plugname) { if (plugname_packed) { controls_table.remove (*plugname); @@ -450,18 +420,13 @@ AutomationTimeAxisView::set_height (TrackHeight ht) hide_name_entry (); show_name_label (); name_hbox.show_all (); - + auto_button.show(); height_button.show(); clear_button.show(); hide_button.show_all(); - break; - - case Smaller: - _controller->hide(); - - case Small: + } else if (h >= hSmall) { controls_table.remove (name_hbox); if (plugname) { if (plugname_packed) { @@ -474,17 +439,17 @@ AutomationTimeAxisView::set_height (TrackHeight ht) hide_name_entry (); show_name_label (); name_hbox.show_all (); - + auto_button.hide(); height_button.hide(); clear_button.hide(); hide_button.hide(); - break; + } } if (changed) { /* only emit the signal if the height really changed */ - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ } } @@ -900,10 +865,10 @@ AutomationTimeAxisView::color_handler () } } -void +int AutomationTimeAxisView::set_state (const XMLNode& node) { - TimeAxisView::set_state (node); + return TimeAxisView::set_state (node); XMLNodeList kids; XMLNodeConstIterator iter; @@ -947,7 +912,9 @@ void AutomationTimeAxisView::update_extra_xml_shown (bool editor_shown) { XMLNode* xml_node = get_state_node(); - xml_node->add_property ("shown", editor_shown ? "yes" : "no"); +// if (xml_node) { + xml_node->add_property ("shown", editor_shown ? "yes" : "no"); +// } } guint32 diff --git a/gtk2_ardour/automation_time_axis.h b/gtk2_ardour/automation_time_axis.h index 8ddd007a3c..fb56c400c7 100644 --- a/gtk2_ardour/automation_time_axis.h +++ b/gtk2_ardour/automation_time_axis.h @@ -71,7 +71,8 @@ class AutomationTimeAxisView : public TimeAxisView { ~AutomationTimeAxisView(); - void set_height (TimeAxisView::TrackHeight); + + void set_height (uint32_t); void set_samples_per_unit (double); std::string name() const { return _name; } @@ -94,7 +95,7 @@ class AutomationTimeAxisView : public TimeAxisView { bool paste (nframes_t, float times, Selection&, size_t nth); void reset_objects (PointSelection&); - void set_state (const XMLNode&); + int set_state (const XMLNode&); guint32 show_at (double y, int& nth, Gtk::VBox *parent); void hide (); diff --git a/gtk2_ardour/axis_view.h b/gtk2_ardour/axis_view.h index e64ef99b16..3a15e05c99 100644 --- a/gtk2_ardour/axis_view.h +++ b/gtk2_ardour/axis_view.h @@ -52,11 +52,8 @@ class AxisView : public virtual Selectable virtual string name() const = 0; virtual bool marked_for_display() const { return _marked_for_display; } - virtual void set_marked_for_display (bool yn) { - if (yn != _marked_for_display) { - _marked_for_display = yn; - } + _marked_for_display = yn; } sigc::signal Hiding; diff --git a/gtk2_ardour/bundle_manager.cc b/gtk2_ardour/bundle_manager.cc index 4dacce782f..8486c5c30f 100644 --- a/gtk2_ardour/bundle_manager.cc +++ b/gtk2_ardour/bundle_manager.cc @@ -61,7 +61,7 @@ BundleEditorMatrix::get_state (int r, std::string const & p) const uint32_t BundleEditorMatrix::n_rows () const { - return _bundle->nchannels (); + return _bundle->nchannels ().n_total(); } uint32_t diff --git a/gtk2_ardour/canvas_vars.h b/gtk2_ardour/canvas_vars.h index 44a710703b..530d323961 100644 --- a/gtk2_ardour/canvas_vars.h +++ b/gtk2_ardour/canvas_vars.h @@ -24,7 +24,6 @@ CANVAS_VARIABLE(canvasvar_EnteredControlPointOutline, "entered control point out CANVAS_VARIABLE(canvasvar_EnteredControlPointSelected, "entered control point selected") CANVAS_VARIABLE(canvasvar_EnteredGainLine, "entered gain line") CANVAS_VARIABLE(canvasvar_EnteredMarker, "entered marker") -CANVAS_VARIABLE(canvasvar_FrameBase, "region base") CANVAS_VARIABLE(canvasvar_FrameHandle, "frame handle") CANVAS_VARIABLE(canvasvar_GainLine, "gain line") CANVAS_VARIABLE(canvasvar_GainLineInactive, "gain line inactive") @@ -82,6 +81,8 @@ CANVAS_VARIABLE(canvasvar_RangeDragBarRect, "range drag bar rect") CANVAS_VARIABLE(canvasvar_RangeDragRect, "range drag rect") CANVAS_VARIABLE(canvasvar_RangeMarkerBar, "range marker bar") CANVAS_VARIABLE(canvasvar_RecordingRect, "recording rect") +CANVAS_VARIABLE(canvasvar_RecWaveFormFill, "recorded waveform fill") +CANVAS_VARIABLE(canvasvar_RecWaveForm, "recorded waveform outline") CANVAS_VARIABLE(canvasvar_RubberBandRect, "rubber band rect") CANVAS_VARIABLE(canvasvar_SelectedCrossfadeEditorLine, "selected crossfade editor line") CANVAS_VARIABLE(canvasvar_SelectedCrossfadeEditorWave, "selected crossfade editor wave") @@ -103,8 +104,9 @@ CANVAS_VARIABLE(canvasvar_TrimHandleLocked, "trim handle locked") CANVAS_VARIABLE(canvasvar_TrimHandle, "trim handle") CANVAS_VARIABLE(canvasvar_VerboseCanvasCursor, "verbose canvas cursor") CANVAS_VARIABLE(canvasvar_VestigialFrame, "vestigial frame") +CANVAS_VARIABLE(canvasvar_FrameBase, "region base") +CANVAS_VARIABLE(canvasvar_WaveForm, "waveform outline") CANVAS_VARIABLE(canvasvar_WaveFormClip, "clipped waveform") CANVAS_VARIABLE(canvasvar_WaveFormFill, "waveform fill") -CANVAS_VARIABLE(canvasvar_WaveForm, "waveform outline") CANVAS_VARIABLE(canvasvar_ZeroLine, "zero line") CANVAS_VARIABLE(canvasvar_ZoomRect, "zoom rect") diff --git a/gtk2_ardour/crossfade_view.cc b/gtk2_ardour/crossfade_view.cc index 22119721ff..1b5f4d886a 100644 --- a/gtk2_ardour/crossfade_view.cc +++ b/gtk2_ardour/crossfade_view.cc @@ -52,7 +52,7 @@ CrossfadeView::CrossfadeView (ArdourCanvas::Group *parent, : TimeAxisViewItem ("xfade" /*xf.name()*/, *parent, tv, spu, basic_color, xf->position(), - xf->length(), TimeAxisViewItem::Visibility (TimeAxisViewItem::ShowFrame)), + xf->length(), false, TimeAxisViewItem::Visibility (TimeAxisViewItem::ShowFrame)), crossfade (xf), left_view (lview), right_view (rview) @@ -69,7 +69,7 @@ CrossfadeView::CrossfadeView (ArdourCanvas::Group *parent, fade_out->property_fill_color_rgba() = ARDOUR_UI::config()->canvasvar_CrossfadeLine.get(); fade_out->property_width_pixels() = 1; - set_y_position_and_height (0, get_time_axis_view().height); + set_y_position_and_height (0, get_time_axis_view().current_height()); /* no frame around the xfade or overlap rects */ @@ -109,15 +109,12 @@ CrossfadeView::reset_width_dependent_items (double pixel_width) void CrossfadeView::set_y_position_and_height (double y, double h) { - if (h == TimeAxisView::hSmaller || h == TimeAxisView::hSmall) { - TimeAxisViewItem::set_y_position_and_height (y, h - 3 ); + if (h <= TimeAxisView::hSmaller) { + TimeAxisViewItem::set_y_position_and_height (y, h - 3); } else { TimeAxisViewItem::set_y_position_and_height (y, h - NAME_HIGHLIGHT_SIZE - 3 ); } - _y_position = y; - _height = h; - redraw_curves (); } @@ -163,8 +160,10 @@ CrossfadeView::redraw_curves () At "height - 3.0" the bottom of the crossfade touches the name highlight or the bottom of the track (if the track is either Small or Smaller. */ - double const tav_height = get_time_axis_view().height; - if (tav_height == TimeAxisView::hSmaller || tav_height == TimeAxisView::hSmall) { + + double tav_height = get_time_axis_view().current_height(); + if (tav_height == TimeAxisView::hSmaller || + tav_height == TimeAxisView::hSmall) { h = tav_height - 3.0; } else { h = tav_height - NAME_HIGHLIGHT_SIZE - 3.0; diff --git a/gtk2_ardour/editing.cc b/gtk2_ardour/editing.cc index 2874e69308..1e58fcddbc 100644 --- a/gtk2_ardour/editing.cc +++ b/gtk2_ardour/editing.cc @@ -17,7 +17,7 @@ */ -#include +#include #include #include "editing.h" diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 3d14d96178..ab8940874c 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -84,6 +84,7 @@ #include "gui_thread.h" #include "simpleline.h" #include "rhythm_ferret.h" +#include "actions.h" #ifdef FFT_ANALYSIS #include "analysis_window.h" @@ -266,6 +267,7 @@ Editor::Editor () clicked_control_point = 0; last_update_frame = 0; drag_info.item = 0; + drag_info.copied_location = 0; current_mixer_strip = 0; current_bbt_points = 0; @@ -350,6 +352,13 @@ Editor::Editor () select_new_marker = false; zoomed_to_region = false; rhythm_ferret = 0; + allow_vertical_scroll = false; + no_save_visual = false; + need_resize_line = false; + resize_line_y = 0; + old_resize_line_y = -1; + no_region_list_redisplay = false; + resize_idle_id = -1; _scrubbing = false; scrubbing_direction = 0; @@ -370,8 +379,6 @@ Editor::Editor () set_midi_edit_mode (MidiEditPencil, true); set_mouse_mode (MouseObject, true); - last_visual_state.frames_per_unit = 0; - frames_per_unit = 2048; /* too early to use reset_zoom () */ reset_hscrollbar_stepping (); @@ -818,6 +825,7 @@ Editor::Editor () ControlProtocol::ZoomIn.connect (bind (mem_fun (*this, &Editor::temporal_zoom_step), false)); ControlProtocol::ZoomOut.connect (bind (mem_fun (*this, &Editor::temporal_zoom_step), true)); ControlProtocol::ScrollTimeline.connect (mem_fun (*this, &Editor::control_scroll)); + BasicUI::AccessAction.connect (mem_fun (*this, &Editor::access_action)); Config->ParameterChanged.connect (mem_fun (*this, &Editor::parameter_changed)); Route::SyncOrderKeys.connect (mem_fun (*this, &Editor::sync_order_keys)); @@ -850,6 +858,16 @@ Editor::~Editor() delete time_canvas; time_canvas = 0; } + + if (track_canvas) { + delete track_canvas; + track_canvas = 0; + } + + if (time_canvas) { + delete time_canvas; + time_canvas = 0; + } } void @@ -971,10 +989,10 @@ Editor::zoom_adjustment_changed () if (fpu < 1.0) { fpu = 1.0; - zoom_range_clock.set ((nframes_t) floor (fpu * canvas_width)); + zoom_range_clock.set ((nframes64_t) floor (fpu * canvas_width)); } else if (fpu > session->current_end_frame() / canvas_width) { fpu = session->current_end_frame() / canvas_width; - zoom_range_clock.set ((nframes_t) floor (fpu * canvas_width)); + zoom_range_clock.set ((nframes64_t) floor (fpu * canvas_width)); } temporal_zoom (fpu); @@ -994,7 +1012,7 @@ Editor::control_scroll (float fraction) /* _control_scroll_target is an optional - it acts like a pointer to an nframes_t, with + it acts like a pointer to an nframes64_t, with a operator conversion to boolean to check that it has a value could possibly use playhead_cursor->current_frame to store the @@ -1007,12 +1025,12 @@ Editor::control_scroll (float fraction) _dragging_playhead = true; } - if ((fraction < 0.0f) && (*_control_scroll_target < (nframes_t) fabs(step))) { + if ((fraction < 0.0f) && (*_control_scroll_target < (nframes64_t) fabs(step))) { *_control_scroll_target = 0; } else if ((fraction > 0.0f) && (max_frames - *_control_scroll_target < step)) { *_control_scroll_target = max_frames - (current_page_frames()*2); // allow room for slop in where the PH is on the screen } else { - *_control_scroll_target += (nframes_t) floor (step); + *_control_scroll_target += (nframes64_t) floor (step); } /* move visuals, we'll catch up with it later */ @@ -1043,7 +1061,7 @@ Editor::control_scroll (float fraction) } bool -Editor::deferred_control_scroll (nframes_t target) +Editor::deferred_control_scroll (nframes64_t target) { session->request_locate (*_control_scroll_target, session->transport_rolling()); // reset for next stream @@ -1052,6 +1070,27 @@ Editor::deferred_control_scroll (nframes_t target) return false; } +void +Editor::access_action (std::string action_group, std::string action_item) +{ + if (!session) { + return; + } + + ENSURE_GUI_THREAD (bind (mem_fun (*this, &Editor::access_action), action_group, action_item)); + + cout<< "OSC: Recieved: "<< action_item << endl; + + RefPtr act; + act = ActionManager::get_action( action_group.c_str(), action_item.c_str() ); + + if (act) { + act->activate(); + } + + +} + void Editor::on_realize () { @@ -1073,7 +1112,7 @@ Editor::stop_scrolling () } void -Editor::map_position_change (nframes_t frame) +Editor::map_position_change (nframes64_t frame) { ENSURE_GUI_THREAD (bind (mem_fun(*this, &Editor::map_position_change), frame)); @@ -1086,7 +1125,7 @@ Editor::map_position_change (nframes_t frame) } void -Editor::center_screen (nframes_t frame) +Editor::center_screen (nframes64_t frame) { double page = canvas_width * frames_per_unit; @@ -1099,12 +1138,12 @@ Editor::center_screen (nframes_t frame) } void -Editor::center_screen_internal (nframes_t frame, float page) +Editor::center_screen_internal (nframes64_t frame, float page) { page /= 2; if (frame > page) { - frame -= (nframes_t) page; + frame -= (nframes64_t) page; } else { frame = 0; } @@ -1117,7 +1156,7 @@ Editor::handle_new_duration () { ENSURE_GUI_THREAD (mem_fun (*this, &Editor::handle_new_duration)); - nframes_t new_end = session->get_maximum_extent() + (nframes_t) floorf (current_page_frames() * 0.10f); + nframes64_t new_end = session->get_maximum_extent() + (nframes64_t) floorf (current_page_frames() * 0.10f); if (new_end > last_canvas_frame) { last_canvas_frame = new_end; @@ -1126,6 +1165,7 @@ Editor::handle_new_duration () } horizontal_adjustment.set_value (leftmost_frame/frames_per_unit); + //cerr << "Editor::handle_new_duration () called ha v:l:u:ps:lcf = " << horizontal_adjustment.get_value() << ":" << horizontal_adjustment.get_lower() << ":" << horizontal_adjustment.get_upper() << ":" << horizontal_adjustment.get_page_size() << ":" << last_canvas_frame << endl;//DEBUG } void @@ -1217,6 +1257,7 @@ Editor::connect_to_session (Session *t) zoom_range_clock.set_session (session); _playlist_selector->set_session (session); nudge_clock.set_session (session); + nudge_clock.set (session->frame_rate() * 5); // default of 5 seconds if (rhythm_ferret) { rhythm_ferret->set_session (session); @@ -1471,10 +1512,10 @@ Editor::popup_fade_context_menu (int button, int32_t time, ArdourCanvas::Item* i } void -Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type, bool with_selection, nframes_t frame) +Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type, bool with_selection, nframes64_t frame) { using namespace Menu_Helpers; - Menu* (Editor::*build_menu_function)(nframes_t); + Menu* (Editor::*build_menu_function)(nframes64_t); Menu *menu; switch (item_type) { @@ -1590,7 +1631,7 @@ Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type, } Menu* -Editor::build_track_context_menu (nframes_t ignored) +Editor::build_track_context_menu (nframes64_t ignored) { using namespace Menu_Helpers; @@ -1602,7 +1643,7 @@ Editor::build_track_context_menu (nframes_t ignored) } Menu* -Editor::build_track_bus_context_menu (nframes_t ignored) +Editor::build_track_bus_context_menu (nframes64_t ignored) { using namespace Menu_Helpers; @@ -1614,7 +1655,7 @@ Editor::build_track_bus_context_menu (nframes_t ignored) } Menu* -Editor::build_track_region_context_menu (nframes_t frame) +Editor::build_track_region_context_menu (nframes64_t frame) { using namespace Menu_Helpers; MenuList& edit_items = track_region_context_menu.items(); @@ -1627,10 +1668,20 @@ Editor::build_track_region_context_menu (nframes_t frame) boost::shared_ptr pl; if ((ds = rtv->get_diskstream()) && ((pl = ds->playlist()))) { - Playlist::RegionList* regions = pl->regions_at ((nframes_t) floor ( (double)frame * ds->speed())); - for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { - add_region_context_items (rtv->view(), (*i), edit_items); + Playlist::RegionList* regions = pl->regions_at ((nframes64_t) floor ( (double)frame * ds->speed())); + + if (selection->regions.size() > 1) { + // there's already a multiple selection: just add a + // single region context menu that will act on all + // selected regions + boost::shared_ptr dummy_region; // = NULL + add_region_context_items (rtv->view(), dummy_region, edit_items); + } else { + for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { + add_region_context_items (rtv->view(), (*i), edit_items); + } } + delete regions; } } @@ -1641,7 +1692,7 @@ Editor::build_track_region_context_menu (nframes_t frame) } Menu* -Editor::build_track_crossfade_context_menu (nframes_t frame) +Editor::build_track_crossfade_context_menu (nframes64_t frame) { using namespace Menu_Helpers; MenuList& edit_items = track_crossfade_context_menu.items(); @@ -1667,10 +1718,17 @@ Editor::build_track_crossfade_context_menu (nframes_t frame) add_crossfade_context_items (atv->audio_view(), (*i), edit_items, many); } - for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { - add_region_context_items (atv->audio_view(), (*i), edit_items); + if (selection->regions.size() > 1) { + // there's already a multiple selection: just add a + // single region context menu that will act on all + // selected regions + boost::shared_ptr dummy_region; // = NULL + add_region_context_items (atv->audio_view(), dummy_region, edit_items); + } else { + for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { + add_region_context_items (atv->audio_view(), (*i), edit_items); + } } - delete regions; } } @@ -1719,7 +1777,7 @@ Editor::analyze_range_selection() #endif /* FFT_ANALYSIS */ Menu* -Editor::build_track_selection_context_menu (nframes_t ignored) +Editor::build_track_selection_context_menu (nframes64_t ignored) { using namespace Menu_Helpers; MenuList& edit_items = track_selection_context_menu.items(); @@ -1820,16 +1878,18 @@ Editor::add_region_context_items (StreamView* sv, boost::shared_ptr regi if (region) { ar = boost::dynamic_pointer_cast (region); mr = boost::dynamic_pointer_cast (region); - } - /* when this particular menu pops up, make the relevant region - become selected. - */ + /* when this particular menu pops up, make the relevant region + become selected. + */ - region_menu->signal_map_event().connect (bind (mem_fun(*this, &Editor::set_selected_regionview_from_map_event), sv, boost::weak_ptr(region))); + region_menu->signal_map_event().connect ( + bind (mem_fun(*this, &Editor::set_selected_regionview_from_map_event), sv, boost::weak_ptr(region))); + + items.push_back (MenuElem (_("Rename"), mem_fun(*this, &Editor::rename_region))); + items.push_back (MenuElem (_("Popup region editor"), mem_fun(*this, &Editor::edit_region))); + } - items.push_back (MenuElem (_("Rename"), mem_fun(*this, &Editor::rename_region))); - items.push_back (MenuElem (_("Popup region editor"), mem_fun(*this, &Editor::edit_region))); items.push_back (MenuElem (_("Raise to top layer"), mem_fun(*this, &Editor::raise_region_to_top))); items.push_back (MenuElem (_("Lower to bottom layer"), mem_fun (*this, &Editor::lower_region_to_bottom))); items.push_back (SeparatorElem()); @@ -1851,49 +1911,61 @@ Editor::add_region_context_items (StreamView* sv, boost::shared_ptr regi sigc::connection fooc; - items.push_back (CheckMenuElem (_("Lock"))); - CheckMenuItem* region_lock_item = static_cast(&items.back()); - if (region->locked()) { - region_lock_item->set_active(); - } - region_lock_item->signal_activate().connect (mem_fun(*this, &Editor::toggle_region_lock)); + if (region) { + items.push_back (CheckMenuElem (_("Lock"))); + CheckMenuItem* region_lock_item = static_cast(&items.back()); + if (region->locked()) { + region_lock_item->set_active(); + } + region_lock_item->signal_activate().connect (mem_fun(*this, &Editor::toggle_region_lock)); - items.push_back (CheckMenuElem (_("Glue to Bars&Beats"))); - CheckMenuItem* bbt_glue_item = static_cast(&items.back()); + items.push_back (CheckMenuElem (_("Glue to Bars&Beats"))); + CheckMenuItem* bbt_glue_item = static_cast(&items.back()); - switch (region->positional_lock_style()) { - case Region::MusicTime: - bbt_glue_item->set_active (true); - break; - default: - bbt_glue_item->set_active (false); - break; - } + switch (region->positional_lock_style()) { + case Region::MusicTime: + bbt_glue_item->set_active (true); + break; + default: + bbt_glue_item->set_active (false); + break; + } - bbt_glue_item->signal_activate().connect (bind (mem_fun (*this, &Editor::set_region_lock_style), Region::MusicTime)); + bbt_glue_item->signal_activate().connect (bind (mem_fun (*this, &Editor::set_region_lock_style), Region::MusicTime)); - items.push_back (CheckMenuElem (_("Mute"))); - CheckMenuItem* region_mute_item = static_cast(&items.back()); - fooc = region_mute_item->signal_activate().connect (mem_fun(*this, &Editor::toggle_region_mute)); - if (region->muted()) { - fooc.block (true); - region_mute_item->set_active(); - fooc.block (false); - } - - if (!Profile->get_sae()) { - items.push_back (CheckMenuElem (_("Opaque"))); - CheckMenuItem* region_opaque_item = static_cast(&items.back()); - fooc = region_opaque_item->signal_activate().connect (mem_fun(*this, &Editor::toggle_region_opaque)); - if (region->opaque()) { + items.push_back (CheckMenuElem (_("Mute"))); + CheckMenuItem* region_mute_item = static_cast(&items.back()); + fooc = region_mute_item->signal_activate().connect (mem_fun(*this, &Editor::toggle_region_mute)); + if (region->muted()) { fooc.block (true); - region_opaque_item->set_active(); + region_mute_item->set_active(); fooc.block (false); } + + if (!Profile->get_sae()) { + items.push_back (CheckMenuElem (_("Opaque"))); + CheckMenuItem* region_opaque_item = static_cast(&items.back()); + fooc = region_opaque_item->signal_activate().connect (mem_fun(*this, &Editor::toggle_region_opaque)); + if (region->opaque()) { + fooc.block (true); + region_opaque_item->set_active(); + fooc.block (false); + } + } + } else { + // multiple regions selected + // how should these act? + // here they toggle the property of all selected regions + + items.push_back (MenuElem (_("Lock"), mem_fun(*this, &Editor::toggle_region_lock))); + items.push_back (MenuElem (_("Mute"), mem_fun(*this, &Editor::toggle_region_mute))); + if (!Profile->get_sae()) { + items.push_back (MenuElem (_("Opaque"), mem_fun(*this, &Editor::toggle_region_opaque))); + } } items.push_back (CheckMenuElem (_("Original position"), mem_fun(*this, &Editor::naturalize))); - if (region->at_natural_position()) { + if (region && region->at_natural_position()) { items.back().set_sensitive (false); } @@ -1985,7 +2057,7 @@ Editor::add_region_context_items (StreamView* sv, boost::shared_ptr regi items.push_back (MenuElem (_("Multi-Duplicate"), (bind (mem_fun(*this, &Editor::duplicate_dialog), true)))); items.push_back (MenuElem (_("Fill Track"), (mem_fun(*this, &Editor::region_fill_track)))); items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("Remove"), mem_fun(*this, &Editor::remove_clicked_region))); + items.push_back (MenuElem (_("Remove"), mem_fun(*this, &Editor::remove_selected_regions))); /* OK, stick the region submenu at the top of the list, and then add the standard items. @@ -1996,7 +2068,7 @@ Editor::add_region_context_items (StreamView* sv, boost::shared_ptr regi */ string::size_type pos = 0; - string menu_item_name = region->name(); + string menu_item_name = (region) ? region->name() : _("Selected regions"); while ((pos = menu_item_name.find ("_", pos)) != string::npos) { menu_item_name.replace (pos, 1, "__"); @@ -2049,7 +2121,8 @@ Editor::add_selection_context_items (Menu_Helpers::MenuList& edit_items) items.push_back (MenuElem (_("Duplicate range"), bind (mem_fun(*this, &Editor::duplicate_dialog), false))); items.push_back (MenuElem (_("Create chunk from range"), mem_fun(*this, &Editor::create_named_selection))); items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("Bounce range"), mem_fun(*this, &Editor::bounce_range_selection))); + items.push_back (MenuElem (_("Consolidate range"), bind (mem_fun(*this, &Editor::bounce_range_selection), true))); + items.push_back (MenuElem (_("Bounce range to region list"), bind (mem_fun(*this, &Editor::bounce_range_selection), false))); items.push_back (MenuElem (_("Export range"), mem_fun(*this, &Editor::export_selection))); } @@ -2199,8 +2272,9 @@ Editor::add_bus_context_items (Menu_Helpers::MenuList& edit_items) void Editor::set_snap_to (SnapType st) -{ +{ unsigned int snap_ind = (unsigned int)st; + snap_type = st; if (snap_ind > snap_type_strings.size() - 1) { @@ -2355,7 +2429,7 @@ Editor::set_state (const XMLNode& node) move (x, y); if (session && (prop = node.property ("playhead"))) { - nframes_t pos = atol (prop->value().c_str()); + nframes64_t pos = atol (prop->value().c_str()); playhead_cursor->set_position (pos); } else { playhead_cursor->set_position (0); @@ -2546,7 +2620,7 @@ Editor::get_state () node->add_property ("edit-point", enum_2_string (_edit_point)); - snprintf (buf, sizeof (buf), "%" PRIu32, playhead_cursor->current_frame); + snprintf (buf, sizeof (buf), "%" PRIi64, playhead_cursor->current_frame); node->add_property ("playhead", buf); node->add_property ("show-waveforms", _show_waveforms ? "yes" : "no"); @@ -2614,17 +2688,17 @@ Editor::snap_to_internal (nframes64_t& start, int32_t direction, bool for_mark) switch (snap_type) { case SnapToCDFrame: if (((direction == 0) && (start % (one_second/75) > (one_second/75) / 2)) || (direction > 0)) { - start = (nframes_t) ceil ((double) start / (one_second / 75)) * (one_second / 75); + start = (nframes64_t) ceil ((double) start / (one_second / 75)) * (one_second / 75); } else { - start = (nframes_t) floor ((double) start / (one_second / 75)) * (one_second / 75); + start = (nframes64_t) floor ((double) start / (one_second / 75)) * (one_second / 75); } break; case SnapToSMPTEFrame: if (((direction == 0) && (fmod((double)start, (double)session->frames_per_smpte_frame()) > (session->frames_per_smpte_frame() / 2))) || (direction > 0)) { - start = (nframes_t) (ceil ((double) start / session->frames_per_smpte_frame()) * session->frames_per_smpte_frame()); + start = (nframes64_t) (ceil ((double) start / session->frames_per_smpte_frame()) * session->frames_per_smpte_frame()); } else { - start = (nframes_t) (floor ((double) start / session->frames_per_smpte_frame()) * session->frames_per_smpte_frame()); + start = (nframes64_t) (floor ((double) start / session->frames_per_smpte_frame()) * session->frames_per_smpte_frame()); } break; @@ -2636,9 +2710,9 @@ Editor::snap_to_internal (nframes64_t& start, int32_t direction, bool for_mark) start -= session->smpte_offset (); } if (((direction == 0) && (start % one_smpte_second > one_smpte_second / 2)) || direction > 0) { - start = (nframes_t) ceil ((double) start / one_smpte_second) * one_smpte_second; + start = (nframes64_t) ceil ((double) start / one_smpte_second) * one_smpte_second; } else { - start = (nframes_t) floor ((double) start / one_smpte_second) * one_smpte_second; + start = (nframes64_t) floor ((double) start / one_smpte_second) * one_smpte_second; } if (session->smpte_offset_negative()) @@ -2657,9 +2731,9 @@ Editor::snap_to_internal (nframes64_t& start, int32_t direction, bool for_mark) start -= session->smpte_offset (); } if (((direction == 0) && (start % one_smpte_minute > one_smpte_minute / 2)) || direction > 0) { - start = (nframes_t) ceil ((double) start / one_smpte_minute) * one_smpte_minute; + start = (nframes64_t) ceil ((double) start / one_smpte_minute) * one_smpte_minute; } else { - start = (nframes_t) floor ((double) start / one_smpte_minute) * one_smpte_minute; + start = (nframes64_t) floor ((double) start / one_smpte_minute) * one_smpte_minute; } if (session->smpte_offset_negative()) { @@ -2671,17 +2745,17 @@ Editor::snap_to_internal (nframes64_t& start, int32_t direction, bool for_mark) case SnapToSeconds: if (((direction == 0) && (start % one_second > one_second / 2)) || (direction > 0)) { - start = (nframes_t) ceil ((double) start / one_second) * one_second; + start = (nframes64_t) ceil ((double) start / one_second) * one_second; } else { - start = (nframes_t) floor ((double) start / one_second) * one_second; + start = (nframes64_t) floor ((double) start / one_second) * one_second; } break; case SnapToMinutes: if (((direction == 0) && (start % one_minute > one_minute / 2)) || (direction > 0)) { - start = (nframes_t) ceil ((double) start / one_minute) * one_minute; + start = (nframes64_t) ceil ((double) start / one_minute) * one_minute; } else { - start = (nframes_t) floor ((double) start / one_minute) * one_minute; + start = (nframes64_t) floor ((double) start / one_minute) * one_minute; } break; @@ -2758,7 +2832,7 @@ Editor::snap_to_internal (nframes64_t& start, int32_t direction, bool for_mark) case SnapToRegionSync: case SnapToRegionBoundary: if (!region_boundary_cache.empty()) { - vector::iterator i; + vector::iterator i; if (direction > 0) { i = std::upper_bound (region_boundary_cache.begin(), region_boundary_cache.end(), start); @@ -2808,7 +2882,7 @@ Editor::snap_to_internal (nframes64_t& start, int32_t direction, bool for_mark) } double -Editor::snap_length_beats (nframes_t start) +Editor::snap_length_beats (nframes64_t start) { if (!session) { return 1.0; @@ -3685,6 +3759,8 @@ Editor::zoom_focus_selection_done () focus_type = ZoomFocusEdit; } else if (choice == _("Active Mark")) { focus_type = ZoomFocusEdit; + } else if (choice == _("Active Mark")) { + focus_type = ZoomFocusEdit; } else { focus_type = ZoomFocusMouse; } @@ -3923,10 +3999,10 @@ Editor::playlist_selector () const return *_playlist_selector; } -nframes_t -Editor::get_nudge_distance (nframes_t pos, nframes_t& next) +nframes64_t +Editor::get_nudge_distance (nframes64_t pos, nframes64_t& next) { - nframes_t ret; + nframes64_t ret; ret = nudge_clock.current_duration (pos); next = ret + 1; /* XXXX fix me */ @@ -3978,7 +4054,7 @@ Editor::playlist_deletion_dialog (boost::shared_ptr pl) } bool -Editor::audio_region_selection_covers (nframes_t where) +Editor::audio_region_selection_covers (nframes64_t where) { for (RegionSelection::iterator a = selection->regions.begin(); a != selection->regions.end(); ++a) { if ((*a)->region()->covers (where)) { @@ -3997,6 +4073,15 @@ Editor::prepare_for_cleanup () selection->clear_regions (); selection->clear_playlists (); + + no_region_list_redisplay = true; +} + +void +Editor::finish_cleanup () +{ + no_region_list_redisplay = false; + redisplay_regions (); } Location* @@ -4212,8 +4297,8 @@ Editor::maximise_editing_space () post_maximal_pane_position = edit_pane.get_width(); } - fullscreen(); + if(post_maximal_editor_width) { edit_pane.set_position (post_maximal_pane_position - abs(post_maximal_editor_width - pre_maximal_editor_width)); @@ -4318,7 +4403,7 @@ Editor::on_key_release_event (GdkEventKey* ev) } void -Editor::reset_x_origin (nframes_t frame) +Editor::reset_x_origin (nframes64_t frame) { queue_visual_change (frame); } @@ -4330,28 +4415,97 @@ Editor::reset_zoom (double fpu) } void -Editor::reposition_and_zoom (nframes_t frame, double fpu) +Editor::reposition_and_zoom (nframes64_t frame, double fpu) { + //cerr << "Editor::reposition_and_zoom () called ha v:l:u:ps:fpu = " << horizontal_adjustment.get_value() << ":" << horizontal_adjustment.get_lower() << ":" << horizontal_adjustment.get_upper() << ":" << horizontal_adjustment.get_page_size() << ":" << frames_per_unit << endl;//DEBUG reset_x_origin (frame); reset_zoom (fpu); + + if (!no_save_visual) { + undo_visual_stack.push_back (current_visual_state(false)); + } +} + +Editor::VisualState* +Editor::current_visual_state (bool with_tracks) +{ + VisualState* vs = new VisualState; + vs->y_position = vertical_adjustment.get_value(); + vs->frames_per_unit = frames_per_unit; + vs->leftmost_frame = leftmost_frame; + vs->zoom_focus = zoom_focus; + vs->zoomed_to_region = zoomed_to_region; + + if (with_tracks) { + for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) { + vs->track_states.push_back (TAVState ((*i), &(*i)->get_state())); + } + } + + return vs; } void -Editor::swap_visual_state () +Editor::undo_visual_state () { - if (last_visual_state.frames_per_unit == 0) { - // never set + if (undo_visual_stack.empty()) { return; } - /* note: the correct functionality here is very dependent on the ordering of - setting zoom focus, horizontal position and finally zoom. this is because - it is set_frames_per_unit() that overwrites last_visual_state. - */ + VisualState* vs = undo_visual_stack.back(); + undo_visual_stack.pop_back(); + use_visual_state (*vs); + redo_visual_stack.push_back (vs); +} - set_zoom_focus (last_visual_state.zoom_focus); - reposition_and_zoom (last_visual_state.leftmost_frame, last_visual_state.frames_per_unit); - zoomed_to_region = false; +void +Editor::redo_visual_state () +{ + if (redo_visual_stack.empty()) { + return; + } + + VisualState* vs = redo_visual_stack.back(); + redo_visual_stack.pop_back(); + use_visual_state (*vs); + undo_visual_stack.push_back (vs); +} + +void +Editor::swap_visual_state () +{ + if (undo_visual_stack.empty()) { + redo_visual_state (); + } else { + undo_visual_state (); + } +} + +void +Editor::use_visual_state (VisualState& vs) +{ + no_save_visual = true; + + vertical_adjustment.set_value (vs.y_position); + + set_zoom_focus (vs.zoom_focus); + reposition_and_zoom (vs.leftmost_frame, vs.frames_per_unit); + + for (list::iterator i = vs.track_states.begin(); i != vs.track_states.end(); ++i) { + TrackViewList::iterator t; + + /* check if the track still exists - it could have been deleted */ + + if ((t = find (track_views.begin(), track_views.end(), i->first)) != track_views.end()) { + (*t)->set_state (*(i->second)); + } + } + + if (!vs.track_states.empty()) { + update_route_visibility (); + } + + no_save_visual = false; } void @@ -4381,10 +4535,6 @@ Editor::set_frames_per_unit (double fpu) if (fpu == frames_per_unit) { return; } - - last_visual_state.frames_per_unit = frames_per_unit; - last_visual_state.leftmost_frame = leftmost_frame; - last_visual_state.zoom_focus = zoom_focus; frames_per_unit = fpu; post_zoom (); @@ -4395,7 +4545,7 @@ Editor::post_zoom () { // convert fpu to frame count - nframes_t frames = (nframes_t) floor (frames_per_unit * canvas_width); + nframes64_t frames = (nframes64_t) floor (frames_per_unit * canvas_width); if (frames_per_unit != zoom_range_clock.current_duration()) { zoom_range_clock.set (frames); @@ -4424,11 +4574,11 @@ Editor::post_zoom () } void -Editor::queue_visual_change (nframes_t where) +Editor::queue_visual_change (nframes64_t where) { pending_visual_change.pending = VisualChange::Type (pending_visual_change.pending | VisualChange::TimeOrigin); pending_visual_change.time_origin = where; - + if (pending_visual_change.idle_handler_id < 0) { pending_visual_change.idle_handler_id = g_idle_add (_idle_visual_changer, this); } @@ -4456,6 +4606,12 @@ int Editor::idle_visual_changer () { VisualChange::Type p = pending_visual_change.pending; + nframes64_t csf, cef; + + if (session) { + csf = session->current_start_frame(); + cef = session->current_end_frame() + (current_page_frames() / 24);// Add a little extra so we can see the end marker + } pending_visual_change.pending = (VisualChange::Type) 0; @@ -4469,17 +4625,26 @@ Editor::idle_visual_changer () } if (p & VisualChange::TimeOrigin) { - nframes_t time_origin = (nframes_t) floor (horizontal_adjustment.get_value() * frames_per_unit); + nframes64_t time_origin = (nframes64_t) floor (horizontal_adjustment.get_value() * frames_per_unit); + + /* if we seek beyond the current end of the canvas, move the end */ if (time_origin != pending_visual_change.time_origin) { + + if (horizontal_adjustment.get_upper() < pending_visual_change.time_origin) { + last_canvas_frame = (cef > (pending_visual_change.time_origin + current_page_frames())) ? cef : pending_visual_change.time_origin + current_page_frames(); + horizontal_adjustment.set_upper ((cef - csf) / frames_per_unit); + reset_scrolling_region (); + } + horizontal_adjustment.set_value (pending_visual_change.time_origin/frames_per_unit); } else { update_fixed_rulers(); redisplay_tempo (true); } } - pending_visual_change.idle_handler_id = -1; + pending_visual_change.idle_handler_id = -1; return 0; /* this is always a one-shot call */ } @@ -4550,7 +4715,7 @@ Editor::get_preferred_edit_position (bool ignore_playhead) } void -Editor::set_loop_range (nframes_t start, nframes_t end, string cmd) +Editor::set_loop_range (nframes64_t start, nframes64_t end, string cmd) { if (!session) return; @@ -4577,7 +4742,7 @@ Editor::set_loop_range (nframes_t start, nframes_t end, string cmd) } void -Editor::set_punch_range (nframes_t start, nframes_t end, string cmd) +Editor::set_punch_range (nframes64_t start, nframes64_t end, string cmd) { if (!session) return; @@ -4625,14 +4790,14 @@ Editor::get_regions_at (RegionSelection& rs, nframes64_t where, const TrackSelec if ((ds = atv->get_diskstream()) && ((pl = ds->playlist()))) { - Playlist::RegionList* regions = pl->regions_at ((nframes_t) floor ( (double)where * ds->speed())); + Playlist::RegionList* regions = pl->regions_at ((nframes64_t) floor ( (double)where * ds->speed())); for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { RegionView* rv = atv->audio_view()->find_view (*i); if (rv) { - rs.push_back (rv); + rs.add (rv); } } @@ -4663,7 +4828,7 @@ Editor::get_regions_after (RegionSelection& rs, nframes64_t where, const TrackSe if ((ds = atv->get_diskstream()) && ((pl = ds->playlist()))) { - Playlist::RegionList* regions = pl->regions_touched ((nframes_t) floor ( (double)where * ds->speed()), max_frames); + Playlist::RegionList* regions = pl->regions_touched ((nframes64_t) floor ( (double)where * ds->speed()), max_frames); for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { @@ -4809,3 +4974,170 @@ Editor::first_idle () _have_idled = true; } + +void +Editor::start_resize_line_ops () +{ +#if 0 + old_resize_line_y = -1; + resize_line_y = -1; + need_resize_line = true; +#endif +} + +void +Editor::end_resize_line_ops () +{ +#if 0 + need_resize_line = false; + + if (old_resize_line_y >= 0) { + Gdk::Rectangle r (0, old_resize_line_y, (int) canvas_width, 3); + Glib::RefPtr win = get_window(); + cerr << "Final invalidation at " << old_resize_line_y << endl; + win->invalidate_rect (r, false); + } +#endif +} + +void +Editor::queue_draw_resize_line (int at) +{ +#if 0 + Glib::RefPtr win = get_window(); + + resize_line_y = at; + + if (win && canvas_width) { + + int controls_width = controls_layout.get_width(); + int xroot, discard; + + controls_layout.get_window()->get_origin (xroot, discard); + + if (old_resize_line_y >= 0) { + + /* redraw where it used to be */ + + + Gdk::Rectangle r (xroot, old_resize_line_y - 1, controls_width + (int) canvas_width, 3); + win->invalidate_rect (r, true); + cerr << "invalidate " << xroot << "," << old_resize_line_y - 1 << ' ' + << controls_width + canvas_width << " x 3\n"; + } + + /* draw where it is */ + + Gdk::Rectangle r (xroot, at - 1, controls_width + (int) canvas_width, 3); + win->invalidate_rect (r, true); + } +#endif +} + +bool +Editor::on_expose_event (GdkEventExpose* ev) +{ + /* cerr << "+++ editor expose " + << ev->area.x << ',' << ev->area.y + << ' ' + << ev->area.width << " x " << ev->area.height + << " need reize ? " << need_resize_line + << endl; + */ + bool ret = Window::on_expose_event (ev); + +#if 0 + if (need_resize_line) { + + int xroot, yroot, discard; + int controls_width; + + /* Our root coordinates for drawing the line will be the left edge + of the track controls, and the upper left edge of our own window. + */ + + get_window()->get_origin (discard, yroot); + controls_layout.get_window()->get_origin (xroot, discard); + controls_width = controls_layout.get_width(); + + GdkRectangle lr; + GdkRectangle intersection; + + lr.x = xroot; + lr.y = resize_line_y; + lr.width = controls_width + (int) canvas_width; + lr.height = 3; + + if (gdk_rectangle_intersect (&lr, &ev->area, &intersection)) { + + Glib::RefPtr style (get_style()); + Glib::RefPtr black_gc (style->get_black_gc ()); + Glib::RefPtr gc = wrap (black_gc->gobj_copy(), false); + + /* draw on root window */ + + GdkWindow* win = gdk_get_default_root_window(); + + gc->set_subwindow (Gdk::INCLUDE_INFERIORS); + gc->set_line_attributes (3, Gdk::LINE_SOLID, + Gdk::CAP_NOT_LAST, + Gdk::JOIN_MITER); + + gdk_draw_line (win, gc->gobj(), + xroot, + yroot + resize_line_y, + xroot + (int) canvas_width + controls_width, + yroot + resize_line_y); + cerr << "drew line @ " << xroot << ", " << yroot + resize_line_y + << " to " << xroot + (int) canvas_width + controls_width + << ", " << yroot + resize_line_y + << endl; + old_resize_line_y = yroot + resize_line_y; + cerr << "NEXT EXPOSE SHOULD BE AT " << old_resize_line_y << endl; + } else { + cerr << "no intersect with " + << lr.x << ',' << lr.y + << ' ' + << lr.width << " x " << lr.height + << endl; + } + } + + //cerr << "--- editor expose\n"; +#endif + + return ret; +} + +static gboolean +_idle_resizer (gpointer arg) +{ + return ((Editor*)arg)->idle_resize (); +} + +void +Editor::add_to_idle_resize (TimeAxisView* view, uint32_t h) +{ + if (resize_idle_id < 0) { + resize_idle_id = g_idle_add (_idle_resizer, this); + } + + resize_idle_target = h; + + pending_resizes.push_back (view); + + if (selection->selected (view) && !selection->tracks.empty()) { + pending_resizes.insert (pending_resizes.end(), selection->tracks.begin(), selection->tracks.end()); + } +} + +bool +Editor::idle_resize () +{ + for (vector::iterator i = pending_resizes.begin(); i != pending_resizes.end(); ++i) { + (*i)->idle_resize (resize_idle_target); + } + pending_resizes.clear(); + resize_idle_id = -1; + return false; +} diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index 2c7e32d19e..e8af889ad1 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -136,9 +136,9 @@ class Editor : public PublicEditor void first_idle (); virtual bool have_idled() const { return _have_idled; } - nframes_t leftmost_position() const { return leftmost_frame; } - nframes_t current_page_frames() const { - return (nframes_t) floor (canvas_width * frames_per_unit); + nframes64_t leftmost_position() const { return leftmost_frame; } + nframes64_t current_page_frames() const { + return (nframes64_t) floor (canvas_width * frames_per_unit); } void cycle_snap_mode (); @@ -170,6 +170,7 @@ class Editor : public PublicEditor TimeAxisView* get_named_time_axis(const std::string & name) ; void foreach_time_axis_view (sigc::slot); + void add_to_idle_resize (TimeAxisView*, uint32_t); RouteTimeAxisView* get_route_view_by_id (PBD::ID& id); @@ -204,11 +205,11 @@ class Editor : public PublicEditor /* undo related */ - nframes_t unit_to_frame (double unit) const { - return (nframes_t) rint (unit * frames_per_unit); + nframes64_t unit_to_frame (double unit) const { + return (nframes64_t) rint (unit * frames_per_unit); } - double frame_to_unit (nframes_t frame) const { + double frame_to_unit (nframes64_t frame) const { return rint ((double) frame / (double) frames_per_unit); } @@ -232,7 +233,7 @@ class Editor : public PublicEditor */ if (pixel >= 0) { - return (nframes_t) rint (pixel * frames_per_unit * GNOME_CANVAS(track_canvas->gobj())->pixels_per_unit); + return (nframes64_t) rint (pixel * frames_per_unit * GNOME_CANVAS(track_canvas->gobj())->pixels_per_unit); } else { return 0; } @@ -304,7 +305,7 @@ class Editor : public PublicEditor void show_editor_mixer (bool yn); void show_editor_list (bool yn); void set_selected_mixer_strip (TimeAxisView&); - void hide_track_in_display (TimeAxisView& tv); + void hide_track_in_display (TimeAxisView& tv, bool temporary = false); void show_track_in_display (TimeAxisView& tv); /* nudge is initiated by transport controls owned by ARDOUR_UI */ @@ -370,13 +371,14 @@ class Editor : public PublicEditor bool new_regionviews_display_gain () { return _new_regionviews_show_envelope; } void prepare_for_cleanup (); + void finish_cleanup (); void maximise_editing_space(); void restore_editing_space(); - void reset_x_origin (nframes_t); + void reset_x_origin (nframes64_t); void reset_zoom (double); - void reposition_and_zoom (nframes_t, double); + void reposition_and_zoom (nframes64_t, double); nframes64_t get_preferred_edit_position (bool ignore_playhead = false); @@ -387,11 +389,19 @@ class Editor : public PublicEditor void show_rhythm_ferret(); + void goto_visual_state (uint32_t); + void save_visual_state (uint32_t); + + void queue_draw_resize_line (int at); + void start_resize_line_ops (); + void end_resize_line_ops (); + protected: void map_transport_state (); - void map_position_change (nframes_t); + void map_position_change (nframes64_t); void on_realize(); + bool on_expose_event (GdkEventExpose*); private: @@ -401,25 +411,41 @@ class Editor : public PublicEditor bool constructed; // to keep track of the playhead position for control_scroll - boost::optional _control_scroll_target; + boost::optional _control_scroll_target; PlaylistSelector* _playlist_selector; + typedef std::pair TAVState; + struct VisualState { - double frames_per_unit; - nframes_t leftmost_frame; - Editing::ZoomFocus zoom_focus; + double y_position; + double frames_per_unit; + nframes64_t leftmost_frame; + Editing::ZoomFocus zoom_focus; + bool zoomed_to_region; + std::list track_states; }; - VisualState last_visual_state; + std::list undo_visual_stack; + std::list redo_visual_stack; + VisualState* current_visual_state (bool with_tracks = true); + void undo_visual_state (); + void redo_visual_state (); + void use_visual_state (VisualState&); + bool no_save_visual; + void swap_visual_state (); + + std::vector visual_states; + sigc::connection visual_state_op_connection; + void start_visual_state_op (uint32_t n); + void cancel_visual_state_op (uint32_t n); + bool end_visual_state_op (uint32_t n); - nframes_t leftmost_frame; + nframes64_t leftmost_frame; double frames_per_unit; Editing::ZoomFocus zoom_focus; - void use_visual_state (const VisualState&); void set_frames_per_unit (double); - void swap_visual_state (); void post_zoom (); Editing::MouseMode mouse_mode; @@ -469,7 +495,7 @@ class Editor : public PublicEditor void hide(); void show (); void set_name (const string&); - void set_position (nframes_t start, nframes_t end = 0); + void set_position (nframes64_t start, nframes64_t end = 0); void set_color_rgba (uint32_t); }; @@ -482,7 +508,8 @@ class Editor : public PublicEditor void hide_marker (ArdourCanvas::Item*, GdkEvent*); void clear_marker_display (); - void mouse_add_new_marker (nframes_t where, bool is_cd=false, bool is_xrun=false); + void mouse_add_new_marker (nframes64_t where, bool is_cd=false, bool is_xrun=false); + bool choose_new_marker_name(string &name); void update_cd_marker_display (); void ensure_cd_marker_updated (LocationMarkers * lam, ARDOUR::Location * location); @@ -542,12 +569,12 @@ class Editor : public PublicEditor Gtk::Menu * track_edit_playlist_submenu; Gtk::Menu * track_selection_edit_playlist_submenu; - void popup_track_context_menu (int, int, ItemType, bool, nframes_t); - Gtk::Menu* build_track_context_menu (nframes_t); - Gtk::Menu* build_track_bus_context_menu (nframes_t); - Gtk::Menu* build_track_region_context_menu (nframes_t frame); - Gtk::Menu* build_track_crossfade_context_menu (nframes_t); - Gtk::Menu* build_track_selection_context_menu (nframes_t); + void popup_track_context_menu (int, int, ItemType, bool, nframes64_t); + Gtk::Menu* build_track_context_menu (nframes64_t); + Gtk::Menu* build_track_bus_context_menu (nframes64_t); + Gtk::Menu* build_track_region_context_menu (nframes64_t frame); + Gtk::Menu* build_track_crossfade_context_menu (nframes64_t); + Gtk::Menu* build_track_selection_context_menu (nframes64_t); void add_dstream_context_items (Gtk::Menu_Helpers::MenuList&); void add_bus_context_items (Gtk::Menu_Helpers::MenuList&); void add_region_context_items (StreamView*, boost::shared_ptr, Gtk::Menu_Helpers::MenuList&); @@ -564,6 +591,10 @@ class Editor : public PublicEditor Gtk::VBox global_vpacker; Gtk::VBox vpacker; + bool need_resize_line; + int resize_line_y; + int old_resize_line_y; + Gdk::Cursor* current_canvas_cursor; void set_canvas_cursor (); Gdk::Cursor* which_grabber_cursor (); @@ -643,7 +674,7 @@ class Editor : public PublicEditor void compute_fixed_ruler_scale (); //calculates the RulerScale of the fixed rulers void update_fixed_rulers (); void update_tempo_based_rulers (); - void popup_ruler_menu (nframes_t where = 0, ItemType type = RegionItem); + void popup_ruler_menu (nframes64_t where = 0, ItemType type = RegionItem); void update_ruler_visibility (); void set_ruler_visible (RulerType, bool); void toggle_ruler_visibility (RulerType rt); @@ -704,7 +735,7 @@ class Editor : public PublicEditor gint bbt_nmarks; uint32_t bbt_bar_helper_on; uint32_t bbt_accent_modulo; - void compute_bbt_ruler_scale (nframes_t lower, nframes_t upper); + void compute_bbt_ruler_scale (nframes64_t lower, nframes64_t upper); gint metric_get_smpte (GtkCustomRulerMark **, gdouble, gdouble, gint); gint metric_get_bbt (GtkCustomRulerMark **, gdouble, gdouble, gint); @@ -752,13 +783,13 @@ class Editor : public PublicEditor Editor& editor; ArdourCanvas::Points points; ArdourCanvas::Line canvas_item; - nframes_t current_frame; + nframes64_t current_frame; double length; Cursor (Editor&, bool (Editor::*)(GdkEvent*,ArdourCanvas::Item*)); ~Cursor (); - void set_position (nframes_t); + void set_position (nframes64_t); void set_length (double units); void set_y_axis (double position); }; @@ -793,14 +824,12 @@ class Editor : public PublicEditor void select_all_selectables_between (bool within); void select_range_between (); - boost::shared_ptr find_next_region (nframes_t, ARDOUR::RegionPoint, int32_t dir, TrackViewList&, TimeAxisView ** = 0); + boost::shared_ptr find_next_region (nframes64_t, ARDOUR::RegionPoint, int32_t dir, TrackViewList&, TimeAxisView ** = 0); nframes64_t find_next_region_boundary (nframes64_t, int32_t dir, const TrackViewList&); - vector region_boundary_cache; + vector region_boundary_cache; void build_region_boundary_cache (); - Gtk::VBox trackview_vpacker; - Gtk::HBox top_hbox; Gtk::HBox bottom_hbox; @@ -826,7 +855,7 @@ class Editor : public PublicEditor double canvas_width; double canvas_height; double full_canvas_height; - nframes_t last_canvas_frame; + nframes64_t last_canvas_frame; bool track_canvas_map_handler (GdkEventAny*); bool time_canvas_map_handler (GdkEventAny*); @@ -841,7 +870,8 @@ class Editor : public PublicEditor Gtk::HBox edit_controls_hbox; void control_scroll (float); - bool deferred_control_scroll (nframes_t); + void access_action (std::string,std::string); + bool deferred_control_scroll (nframes64_t); sigc::connection control_scroll_connection; void tie_vertical_scrolling (); @@ -855,7 +885,7 @@ class Editor : public PublicEditor }; Type pending; - nframes_t time_origin; + nframes64_t time_origin; double frames_per_unit; int idle_handler_id; @@ -869,7 +899,7 @@ class Editor : public PublicEditor static int _idle_visual_changer (void *arg); int idle_visual_changer (); - void queue_visual_change (nframes_t); + void queue_visual_change (nframes64_t); void queue_visual_change (double); void end_location_changed (ARDOUR::Location*); @@ -999,16 +1029,16 @@ class Editor : public PublicEditor static void build_cursors (); sigc::connection scroll_connection; - nframes_t last_update_frame; - void center_screen (nframes_t); - void center_screen_internal (nframes_t, float); + nframes64_t last_update_frame; + void center_screen (nframes64_t); + void center_screen_internal (nframes64_t, float); void update_current_screen (); void session_going_away (); - nframes_t cut_buffer_start; - nframes_t cut_buffer_length; + nframes64_t cut_buffer_start; + nframes64_t cut_buffer_length; bool typed_event (ArdourCanvas::Item*, GdkEvent*, ItemType); bool button_press_handler (ArdourCanvas::Item*, GdkEvent*, ItemType); @@ -1021,7 +1051,7 @@ class Editor : public PublicEditor void register_actions (); - int ensure_cursor (nframes_t* pos); + int ensure_cursor (nframes64_t* pos); void handle_new_region (boost::weak_ptr); void handle_new_regions (vector >& ); @@ -1030,6 +1060,7 @@ class Editor : public PublicEditor void add_regions_to_region_display (std::vector > & ); void region_hidden (boost::shared_ptr); void redisplay_regions (); + bool no_region_list_redisplay; void insert_into_tmp_regionlist(boost::shared_ptr); list > tmp_region_list; @@ -1041,7 +1072,7 @@ class Editor : public PublicEditor void cut_copy_ranges (Editing::CutCopyOp); void mouse_paste (); - void paste_internal (nframes_t position, float times); + void paste_internal (nframes64_t position, float times); /* EDITING OPERATIONS */ @@ -1055,19 +1086,19 @@ class Editor : public PublicEditor void lower_region (); void lower_region_to_bottom (); void split_region (); - void split_region_at (nframes_t); - void split_regions_at (nframes_t, RegionSelection&); + void split_region_at (nframes64_t); + void split_regions_at (nframes64_t, RegionSelection&); void split_region_at_transients (); void split_region_at_points (boost::shared_ptr, ARDOUR::AnalysisFeatureList&, bool can_ferret); void crop_region_to_selection (); - void crop_region_to (nframes_t start, nframes_t end); + void crop_region_to (nframes64_t start, nframes64_t end); void set_sync_point (nframes64_t, const RegionSelection&); void set_region_sync_from_edit_point (); void remove_region_sync(); - void align_selection (ARDOUR::RegionPoint, nframes_t position, const RegionSelection&); - void align_selection_relative (ARDOUR::RegionPoint point, nframes_t position, const RegionSelection&); - void align_region (boost::shared_ptr, ARDOUR::RegionPoint point, nframes_t position); - void align_region_internal (boost::shared_ptr, ARDOUR::RegionPoint point, nframes_t position); + void align_selection (ARDOUR::RegionPoint, nframes64_t position, const RegionSelection&); + void align_selection_relative (ARDOUR::RegionPoint point, nframes64_t position, const RegionSelection&); + void align_region (boost::shared_ptr, ARDOUR::RegionPoint point, nframes64_t position); + void align_region_internal (boost::shared_ptr, ARDOUR::RegionPoint point, nframes64_t position); void remove_selected_regions (); void remove_clicked_region (); void edit_region (); @@ -1087,7 +1118,7 @@ class Editor : public PublicEditor void quantize_region (); void do_insert_time (); - void insert_time (nframes64_t pos, nframes64_t distance, Editing::InsertTimeOption opt, bool ignore_music_glue); + void insert_time (nframes64_t pos, nframes64_t distance, Editing::InsertTimeOption opt, bool ignore_music_glue, bool markers_too); void tab_to_transient (bool forward); @@ -1130,13 +1161,13 @@ class Editor : public PublicEditor void loop_location (ARDOUR::Location&); void temporal_zoom_selection (); - void temporal_zoom_region (); - void toggle_zoom_region (); + void temporal_zoom_region (bool both_axes); + void toggle_zoom_region (bool both_axes); bool zoomed_to_region; void temporal_zoom_session (); void temporal_zoom (gdouble scale); - void temporal_zoom_by_frame (nframes_t start, nframes_t end, const string & op); - void temporal_zoom_to_frame (bool coarser, nframes_t frame); + void temporal_zoom_by_frame (nframes64_t start, nframes64_t end, const string & op); + void temporal_zoom_to_frame (bool coarser, nframes64_t frame); void amplitude_zoom (gdouble scale); void amplitude_zoom_step (bool in); @@ -1259,8 +1290,8 @@ class Editor : public PublicEditor void set_loop_from_region (bool play); void set_punch_from_edit_range (); - void set_loop_range (nframes_t start, nframes_t end, std::string cmd); - void set_punch_range (nframes_t start, nframes_t end, std::string cmd); + void set_loop_range (nframes64_t start, nframes64_t end, std::string cmd); + void set_punch_range (nframes64_t start, nframes64_t end, std::string cmd); void add_location_from_playhead_cursor (); bool select_new_marker; @@ -1281,7 +1312,7 @@ class Editor : public PublicEditor void keyboard_selection_begin (); void keyboard_selection_finish (bool add); bool have_pending_keyboard_selection; - nframes_t pending_keyboard_selection_start; + nframes64_t pending_keyboard_selection_start; boost::shared_ptr select_region_for_operation (int dir, TimeAxisView **tv); void extend_selection_to_end_of_region (bool next); @@ -1375,11 +1406,11 @@ class Editor : public PublicEditor void remove_gain_control_point (ArdourCanvas::Item*, GdkEvent*); void remove_control_point (ArdourCanvas::Item*, GdkEvent*); - void mouse_brush_insert_region (RegionView*, nframes_t pos); - void brush (nframes_t); + void mouse_brush_insert_region (RegionView*, nframes64_t pos); + void brush (nframes64_t); - void show_verbose_time_cursor (nframes_t frame, double offset = 0, double xpos=-1, double ypos=-1); - void show_verbose_duration_cursor (nframes_t start, nframes_t end, double offset = 0, double xpos=-1, double ypos=-1); + void show_verbose_time_cursor (nframes64_t frame, double offset = 0, double xpos=-1, double ypos=-1); + void show_verbose_duration_cursor (nframes64_t start, nframes64_t end, double offset = 0, double xpos=-1, double ypos=-1); double clamp_verbose_cursor_x (double); double clamp_verbose_cursor_y (double); @@ -1486,8 +1517,8 @@ public: void new_tempo_section (); - void mouse_add_new_tempo_event (nframes_t where); - void mouse_add_new_meter_event (nframes_t where); + void mouse_add_new_tempo_event (nframes64_t where); + void mouse_add_new_meter_event (nframes64_t where); void remove_tempo_marker (ArdourCanvas::Item*); void remove_meter_marker (ArdourCanvas::Item*); @@ -1513,6 +1544,8 @@ public: void marker_menu_set_playhead (); void marker_menu_set_from_playhead (); void marker_menu_set_from_selection (); + void marker_menu_range_to_next (); + void marker_menu_export_range (); void new_transport_marker_menu_set_loop (); void new_transport_marker_menu_set_punch (); void update_loop_range_view (bool visibility=false); @@ -1548,14 +1581,8 @@ public: void redisplay_tempo (bool immediate_redraw); void snap_to (nframes64_t& first, int32_t direction = 0, bool for_mark = false); - void snap_to (nframes_t& first, int32_t direction = 0, bool for_mark = false) { - /* XXX remove this function when everything moves to 64 bit frame counts */ - nframes64_t first64 = first; - snap_to (first64, direction, for_mark); - first = (nframes_t) first64; - } - double snap_length_beats (nframes_t start); + double snap_length_beats (nframes64_t start); uint32_t bbt_beat_subdivision; @@ -1690,7 +1717,7 @@ public: void region_selection_op (void (ARDOUR::Region::*pmf)(void*), void*); void region_selection_op (void (ARDOUR::Region::*pmf)(bool), bool); - bool audio_region_selection_covers (nframes_t where); + bool audio_region_selection_covers (nframes64_t where); /* transport range select process */ enum RangeMarkerOp { @@ -1733,7 +1760,7 @@ public: void drag_rubberband_select (ArdourCanvas::Item* item, GdkEvent* event); void end_rubberband_select (ArdourCanvas::Item* item, GdkEvent* event); - bool select_all_within (nframes_t start, nframes_t end, gdouble topy, gdouble boty, const TrackViewList&, Selection::Operation op); + bool select_all_within (nframes64_t start, nframes64_t end, gdouble topy, gdouble boty, const TrackViewList&, Selection::Operation op); ArdourCanvas::SimpleRect *rubberband_rect; @@ -1744,7 +1771,7 @@ public: void end_mouse_zoom (ArdourCanvas::Item* item, GdkEvent* event); ArdourCanvas::SimpleRect *zoom_rect; - void reposition_zoom_rect (nframes_t start, nframes_t end); + void reposition_zoom_rect (nframes64_t start, nframes64_t end); /* diskstream/route display management */ @@ -1752,11 +1779,13 @@ public: RouteDisplayModelColumns() { add (text); add (visible); + add (temporary_visible); add (tv); add (route); } Gtk::TreeModelColumn text; Gtk::TreeModelColumn visible; + Gtk::TreeModelColumn temporary_visible; Gtk::TreeModelColumn tv; Gtk::TreeModelColumn > route; }; @@ -1769,6 +1798,8 @@ public: Gtk::ScrolledWindow route_list_scroller; Gtk::Menu* route_list_menu; + void update_route_visibility (); + void sync_order_keys (); bool ignore_route_order_sync; @@ -1854,7 +1885,7 @@ public: int last_autoscroll_x; int last_autoscroll_y; uint32_t autoscroll_cnt; - nframes_t autoscroll_x_distance; + nframes64_t autoscroll_x_distance; double autoscroll_y_distance; static gint _autoscroll_canvas (void *); @@ -1862,6 +1893,7 @@ public: void start_canvas_autoscroll (int x, int y); void stop_canvas_autoscroll (); void maybe_autoscroll (GdkEventMotion*); + bool allow_vertical_scroll; /* trimming */ enum TrimOp { @@ -1873,9 +1905,9 @@ public: void start_trim (ArdourCanvas::Item*, GdkEvent*); void point_trim (GdkEvent*); void trim_motion_callback (ArdourCanvas::Item*, GdkEvent*); - void single_contents_trim (RegionView&, nframes_t, bool, bool, bool); - void single_start_trim (RegionView&, nframes_t, bool, bool); - void single_end_trim (RegionView&, nframes_t, bool, bool); + void single_contents_trim (RegionView&, nframes64_t, bool, bool, bool); + void single_start_trim (RegionView&, nframes64_t, bool, bool); + void single_end_trim (RegionView&, nframes64_t, bool, bool); void trim_finished_callback (ArdourCanvas::Item*, GdkEvent*); void thaw_region_after_trim (RegionView& rv); @@ -1943,14 +1975,14 @@ public: ExportDialog *export_dialog; ExportDialog *export_range_markers_dialog; - void export_range (nframes_t start, nframes_t end); + void export_range (nframes64_t start, nframes64_t end); void export_range_markers (); int write_region_selection(RegionSelection&); bool write_region (string path, boost::shared_ptr); void export_region (); void bounce_region_selection (); - void bounce_range_selection (); + void bounce_range_selection (bool replace); void external_edit_region (); int write_audio_selection (TimeSelection&); @@ -1967,12 +1999,6 @@ public: void begin_reversible_command (string cmd_name); void commit_reversible_command (); - /* visual history */ - - UndoHistory visual_history; - UndoTransaction current_visual_command; - - void update_title (); void update_title_s (const string & snapshot_name); @@ -2151,7 +2177,7 @@ public: Gtk::VBox nudge_vbox; AudioClock nudge_clock; - nframes_t get_nudge_distance (nframes_t pos, nframes_t& next); + nframes64_t get_nudge_distance (nframes64_t pos, nframes64_t& next); bool nudge_forward_release (GdkEventButton*); bool nudge_backward_release (GdkEventButton*); @@ -2169,7 +2195,7 @@ public: /* tracking step changes of track height */ TimeAxisView* current_stepping_trackview; - struct timeval last_track_height_step_timestamp; + ARDOUR::microseconds_t last_track_height_step_timestamp; gint track_height_step_timeout(); sigc::connection step_timeout; @@ -2240,7 +2266,8 @@ public: RhythmFerret* rhythm_ferret; - void set_track_height (TimeAxisView::TrackHeight h); + void fit_tracks (); + void set_track_height (uint32_t h); void set_track_height_largest (); void set_track_height_large (); void set_track_height_larger (); @@ -2253,6 +2280,11 @@ public: void waveform_scale_chosen (Editing::WaveformScale); bool _have_idled; + int resize_idle_id; + int32_t resize_idle_target; + bool idle_resize(); + friend gboolean _idle_resize (gpointer); + std::vector pending_resizes; }; #endif /* __ardour_editor_h__ */ diff --git a/gtk2_ardour/editor_actions.cc b/gtk2_ardour/editor_actions.cc index 0d859985a2..a1a7092eb0 100644 --- a/gtk2_ardour/editor_actions.cc +++ b/gtk2_ardour/editor_actions.cc @@ -73,6 +73,7 @@ Editor::register_actions () ActionManager::register_action (editor_actions, X_("RegionEditOps"), _("Region operations")); ActionManager::register_action (editor_actions, X_("RegionGainMenu"), _("Gain")); ActionManager::register_action (editor_actions, X_("RulerMenu"), _("Rulers")); + ActionManager::register_action (editor_actions, X_("SavedViewMenu"), _("Views")); ActionManager::register_action (editor_actions, X_("ScrollMenu"), _("Scroll")); ActionManager::register_action (editor_actions, X_("SecondaryClockMenu"), _("Secondary Clock")); ActionManager::register_action (editor_actions, X_("Select"), _("Select")); @@ -91,10 +92,8 @@ Editor::register_actions () ActionManager::register_action (editor_actions, X_("TrimMenu"), _("Trim")); ActionManager::register_action (editor_actions, X_("View"), _("View")); ActionManager::register_action (editor_actions, X_("WaveformMenu"), _("Waveforms")); - ActionManager::register_action (editor_actions, X_("ZoomFocus"), _("Zoom")); + ActionManager::register_action (editor_actions, X_("ZoomFocus"), _("Zoom Focus")); ActionManager::register_action (editor_actions, X_("ZoomMenu"), _("Zoom")); - ActionManager::register_action (editor_actions, X_("ZoomFocusMenu"), _("Zoom Focus")); - /* add named actions for the editor */ @@ -198,6 +197,56 @@ Editor::register_actions () ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-1", _("Save View 1"), bind (mem_fun (*this, &Editor::start_visual_state_op), 0)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-1", _("Goto View 1"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 0)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-2", _("Save View 2"), bind (mem_fun (*this, &Editor::start_visual_state_op), 1)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-2", _("Goto View 2"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 1)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-3", _("Save View 3"), bind (mem_fun (*this, &Editor::start_visual_state_op), 2)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-3", _("Goto View 3"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 2)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-4", _("Save View 4"), bind (mem_fun (*this, &Editor::start_visual_state_op), 3)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-4", _("Goto View 4"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 3)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-5", _("Save View 5"), bind (mem_fun (*this, &Editor::start_visual_state_op), 4)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-5", _("Goto View 5"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 4)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-6", _("Save View 6"), bind (mem_fun (*this, &Editor::start_visual_state_op), 5)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-6", _("Goto View 6"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 5)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-7", _("Save View 7"), bind (mem_fun (*this, &Editor::start_visual_state_op), 6)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-7", _("Goto View 7"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 6)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-8", _("Save View 8"), bind (mem_fun (*this, &Editor::start_visual_state_op), 7)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-8", _("Goto View 8"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 7)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-9", _("Save View 9"), bind (mem_fun (*this, &Editor::start_visual_state_op), 8)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-9", _("Goto View 9"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 8)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-10", _("Save View 10"), bind (mem_fun (*this, &Editor::start_visual_state_op), 9)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-10", _("Goto View 10"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 9)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-11", _("Save View 11"), bind (mem_fun (*this, &Editor::start_visual_state_op), 10)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-11", _("Goto View 11"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 10)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "save-visual-state-12", _("Save View 12"), bind (mem_fun (*this, &Editor::start_visual_state_op), 11)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "goto-visual-state-12", _("Goto View 12"), bind (mem_fun (*this, &Editor::cancel_visual_state_op), 11)); + ActionManager::session_sensitive_actions.push_back (act); + + act = ActionManager::register_action (editor_actions, "goto-mark-1", _("Locate to Mark 1"), bind (mem_fun (*this, &Editor::goto_nth_marker), 0)); ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_action (editor_actions, "goto-mark-2", _("Locate to Mark 2"), bind (mem_fun (*this, &Editor::goto_nth_marker), 1)); @@ -249,7 +298,9 @@ Editor::register_actions () ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_action (editor_actions, "zoom-to-session", _("Zoom to Session"), mem_fun(*this, &Editor::temporal_zoom_session)); ActionManager::session_sensitive_actions.push_back (act); - act = ActionManager::register_action (editor_actions, "zoom-to-region", _("Zoom to Region"), mem_fun(*this, &Editor::toggle_zoom_region)); + act = ActionManager::register_action (editor_actions, "zoom-to-region", _("Zoom to Region"), bind (mem_fun(*this, &Editor::toggle_zoom_region), false)); + ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "zoom-to-region-both-axes", _("Zoom to Region (W&H)"), bind (mem_fun(*this, &Editor::toggle_zoom_region), true)); ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_action (editor_actions, "toggle-zoom", _("Toggle Zoom State"), mem_fun(*this, &Editor::swap_visual_state)); ActionManager::session_sensitive_actions.push_back (act); @@ -319,6 +370,9 @@ Editor::register_actions () act = ActionManager::register_action (editor_actions, "pitch-shift-region", _("Transpose"), mem_fun(*this, &Editor::pitch_shift_regions)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::region_selection_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "toggle-opaque-region", _("Toggle Opaque"), mem_fun(*this, &Editor::toggle_region_opaque)); + ActionManager::session_sensitive_actions.push_back (act); + ActionManager::region_selection_sensitive_actions.push_back (act); act = ActionManager::register_action (editor_actions, "set-fade-in-length", _("Set Fade In Length"), bind (mem_fun(*this, &Editor::set_fade_length), true)); ActionManager::session_sensitive_actions.push_back (act); @@ -467,7 +521,8 @@ Editor::register_actions () act = ActionManager::register_action (editor_actions, "quantize-region", _("Quantize Region"), mem_fun(*this, &Editor::quantize_region)); ActionManager::session_sensitive_actions.push_back (act); - + ActionManager::region_selection_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "set-tempo-from-region", _("Set Tempo from Region=Bar"), mem_fun(*this, &Editor::use_region_as_bar)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::region_selection_sensitive_actions.push_back (act); @@ -521,6 +576,8 @@ Editor::register_actions () ActionManager::session_sensitive_actions.push_back (act); ActionManager::track_selection_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, "fit-tracks", _("Fit Selected Tracks"), (mem_fun(*this, &Editor::fit_tracks))); + ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_action (editor_actions, "track-height-largest", _("Largest"), (mem_fun(*this, &Editor::set_track_height_largest))); ActionManager::session_sensitive_actions.push_back (act); ActionManager::track_selection_sensitive_actions.push_back (act); @@ -693,9 +750,10 @@ Editor::register_actions () /* the next two are duplicate items with different names for use in two different contexts */ - act = ActionManager::register_action (editor_actions, X_("addExistingAudioFiles"), _("Import"), mem_fun (*this, &Editor::external_audio_dialog)); ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, X_("addExternalAudioToRegionList"), _("Import to Region List"), bind (mem_fun(*this, &Editor::add_external_audio_action), ImportAsRegion)); + ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_toggle_action (editor_actions, X_("toggle-waveform-visible"), _("Show Waveforms"), mem_fun (*this, &Editor::toggle_waveform_visibility)); ActionManager::track_selection_sensitive_actions.push_back (act); diff --git a/gtk2_ardour/editor_audio_import.cc b/gtk2_ardour/editor_audio_import.cc index 61d0a22882..b3b710f990 100644 --- a/gtk2_ardour/editor_audio_import.cc +++ b/gtk2_ardour/editor_audio_import.cc @@ -74,7 +74,7 @@ void Editor::add_external_audio_action (ImportMode mode_hint) { if (session == 0) { - MessageDialog msg (0, _("You can't import or embed a file until you have a session loaded.")); + MessageDialog msg (_("You can't import or embed an audiofile until you have a session loaded.")); msg.run (); return; } @@ -95,7 +95,7 @@ Editor::external_audio_dialog () uint32_t track_cnt; if (session == 0) { - MessageDialog msg (0, _("You can't import or embed a file until you have a session loaded.")); + MessageDialog msg (_("You can't import or embed an audiofile until you have a session loaded.")); msg.run (); return; } diff --git a/gtk2_ardour/editor_audiotrack.cc b/gtk2_ardour/editor_audiotrack.cc index cfb8f0a557..7e821f0e5e 100644 --- a/gtk2_ardour/editor_audiotrack.cc +++ b/gtk2_ardour/editor_audiotrack.cc @@ -111,6 +111,7 @@ Editor::toggle_meter_updating() } else { stop_updating (); } + track_canvas_allocate(track_canvas->get_allocation()); } void diff --git a/gtk2_ardour/editor_canvas.cc b/gtk2_ardour/editor_canvas.cc index 516443e012..0be64cc80f 100644 --- a/gtk2_ardour/editor_canvas.cc +++ b/gtk2_ardour/editor_canvas.cc @@ -55,7 +55,7 @@ using namespace Glib; using namespace Gtkmm2ext; using namespace Editing; -/* XXX this is a hack. it ought to be the maximum value of an nframes_t */ +/* XXX this is a hack. it ought to be the maximum value of an nframes64_t */ const double max_canvas_coordinate = (double) JACK_MAX_FRAMES; @@ -181,7 +181,6 @@ Editor::initialize_canvas () marker_time_line_group = new ArdourCanvas::Group (*time_canvas->root(), 0.0, 0.0); marker_tempo_lines = new TempoLines(*time_canvas, marker_time_line_group); - meter_group = new ArdourCanvas::Group (*time_canvas->root(), 0.0, 0.0); tempo_group = new ArdourCanvas::Group (*time_canvas->root(), 0.0, timebar_height); range_marker_group = new ArdourCanvas::Group (*time_canvas->root(), 0.0, timebar_height * 2.0); @@ -190,23 +189,27 @@ Editor::initialize_canvas () cd_marker_group = new ArdourCanvas::Group (*time_canvas->root(), 0.0, timebar_height * 5.0); tempo_bar = new ArdourCanvas::SimpleRect (*tempo_group, 0.0, 0.0, max_canvas_coordinate, timebar_height-1.0); + tempo_bar->property_outline_what() = (0x1 | 0x8); tempo_bar->property_outline_pixels() = 1; - meter_bar = new ArdourCanvas::SimpleRect (*meter_group, 0.0, 0.0, max_canvas_coordinate, timebar_height-1.0); + meter_bar->property_outline_what() = (0x1 | 0x8); meter_bar->property_outline_pixels() = 1; marker_bar = new ArdourCanvas::SimpleRect (*marker_group, 0.0, 0.0, max_canvas_coordinate, timebar_height-1.0); + marker_bar->property_outline_what() = (0x1 | 0x8); marker_bar->property_outline_pixels() = 1; cd_marker_bar = new ArdourCanvas::SimpleRect (*cd_marker_group, 0.0, 0.0, max_canvas_coordinate, timebar_height-1.0); + cd_marker_bar->property_outline_what() = (0x1 | 0x8); cd_marker_bar->property_outline_pixels() = 1; range_marker_bar = new ArdourCanvas::SimpleRect (*range_marker_group, 0.0, 0.0, max_canvas_coordinate, timebar_height-1.0); + range_marker_bar->property_outline_what() = (0x1 | 0x8); range_marker_bar->property_outline_pixels() = 1; @@ -220,7 +223,7 @@ Editor::initialize_canvas () range_bar_drag_rect = new ArdourCanvas::SimpleRect (*range_marker_group, 0.0, 0.0, max_canvas_coordinate, timebar_height-1.0); range_bar_drag_rect->property_outline_pixels() = 0; - + transport_bar_drag_rect = new ArdourCanvas::SimpleRect (*transport_marker_group, 0.0, 0.0, max_canvas_coordinate, timebar_height-1.0); transport_bar_drag_rect->property_outline_pixels() = 0; transport_bar_drag_rect->hide (); @@ -343,7 +346,7 @@ Editor::track_canvas_size_allocated () full_canvas_height = height; } - zoom_range_clock.set ((nframes_t) floor ((canvas_width * frames_per_unit))); + zoom_range_clock.set ((nframes64_t) floor ((canvas_width * frames_per_unit))); playhead_cursor->set_position (playhead_cursor->current_frame); reset_hscrollbar_stepping (); @@ -391,7 +394,7 @@ Editor::reset_scrolling_region (Gtk::Allocation* alloc) } double last_canvas_unit = max ((last_canvas_frame / frames_per_unit), canvas_width); - + //cerr << "Editor::reset_scrolling_region () lcf:fpu:cw:lcu " << last_canvas_frame << ":" << frames_per_unit << ":" << canvas_width << ":" << last_canvas_unit << endl;//DEBUG track_canvas->set_scroll_region (0.0, 0.0, last_canvas_unit, pos); // XXX what is the correct height value for the time canvas ? this overstates it @@ -521,6 +524,8 @@ Editor::drop_paths (const RefPtr& context, /* drop onto canvas background: create new tracks */ + frame = 0; + if (Profile->get_sae() || Config->get_only_copy_imported_files()) { do_import (paths, Editing::ImportDistinctFiles, Editing::ImportAsTrack, SrcBest, frame); } else { @@ -587,8 +592,8 @@ Editor::drop_routes (const Glib::RefPtr& context, void Editor::maybe_autoscroll (GdkEventMotion* event) { - nframes_t rightmost_frame = leftmost_frame + current_page_frames(); - nframes_t frame = drag_info.current_pointer_frame; + nframes64_t rightmost_frame = leftmost_frame + current_page_frames(); + nframes64_t frame = drag_info.current_pointer_frame; bool startit = false; double vertical_pos = vertical_adjustment.get_value(); @@ -621,6 +626,10 @@ Editor::maybe_autoscroll (GdkEventMotion* event) } + if (!allow_vertical_scroll) { + autoscroll_y = 0; + } + if ((autoscroll_x != last_autoscroll_x) || (autoscroll_y != last_autoscroll_y) || (autoscroll_x == 0 && autoscroll_y == 0)) { stop_canvas_autoscroll (); } @@ -642,10 +651,10 @@ Editor::_autoscroll_canvas (void *arg) bool Editor::autoscroll_canvas () { - nframes_t new_frame; - nframes_t limit = max_frames - current_page_frames(); + nframes64_t new_frame; + nframes64_t limit = max_frames - current_page_frames(); GdkEventMotion ev; - nframes_t target_frame; + nframes64_t target_frame; double new_pixel; double target_pixel; @@ -742,17 +751,17 @@ Editor::autoscroll_canvas () /* after about a while, speed up a bit by changing the timeout interval */ - autoscroll_x_distance = (nframes_t) floor (current_page_frames()/30.0f); + autoscroll_x_distance = (nframes64_t) floor (current_page_frames()/30.0f); } else if (autoscroll_cnt == 150) { /* 1.0 seconds */ - autoscroll_x_distance = (nframes_t) floor (current_page_frames()/20.0f); + autoscroll_x_distance = (nframes64_t) floor (current_page_frames()/20.0f); } else if (autoscroll_cnt == 300) { /* 1.5 seconds */ /* after about another while, speed up by increasing the shift per callback */ - autoscroll_x_distance = (nframes_t) floor (current_page_frames()/10.0f); + autoscroll_x_distance = (nframes64_t) floor (current_page_frames()/10.0f); } } @@ -792,7 +801,7 @@ Editor::start_canvas_autoscroll (int dx, int dy) autoscroll_active = true; autoscroll_x = dx; autoscroll_y = dy; - autoscroll_x_distance = (nframes_t) floor (current_page_frames()/50.0); + autoscroll_x_distance = (nframes64_t) floor (current_page_frames()/50.0); autoscroll_y_distance = fabs (dy * 5); /* pixels */ autoscroll_cnt = 0; @@ -864,7 +873,7 @@ Editor::tie_vertical_scrolling () void Editor::canvas_horizontally_scrolled () { - nframes64_t time_origin = (nframes_t) floor (horizontal_adjustment.get_value() * frames_per_unit); + nframes64_t time_origin = (nframes64_t) floor (horizontal_adjustment.get_value() * frames_per_unit); if (time_origin != leftmost_frame) { canvas_scroll_to (time_origin); @@ -874,8 +883,9 @@ Editor::canvas_horizontally_scrolled () void Editor::canvas_scroll_to (nframes64_t time_origin) { - leftmost_frame = time_origin; - nframes_t rightmost_frame = leftmost_frame + current_page_frames (); + leftmost_frame = time_origin; + + nframes64_t rightmost_frame = leftmost_frame + current_page_frames (); if (rightmost_frame > last_canvas_frame) { last_canvas_frame = rightmost_frame; diff --git a/gtk2_ardour/editor_canvas_events.cc b/gtk2_ardour/editor_canvas_events.cc index 0da0bfc487..dd107d8d02 100644 --- a/gtk2_ardour/editor_canvas_events.cc +++ b/gtk2_ardour/editor_canvas_events.cc @@ -56,7 +56,7 @@ Editor::track_canvas_scroll (GdkEventScroll* ev) { int x, y; double wx, wy; - nframes_t xdelta; + nframes64_t xdelta; int direction = ev->direction; CanvasNoteEvent *midi_event = dynamic_cast(track_canvas->get_item_at(ev->x, ev->y)); @@ -80,7 +80,7 @@ Editor::track_canvas_scroll (GdkEventScroll* ev) event.button.x = wx; event.button.y = wy; - nframes_t where = event_frame (&event, 0, 0); + nframes64_t where = event_frame (&event, 0, 0); temporal_zoom_to_frame (false, where); return true; } else if (Keyboard::modifier_state_equals (ev->state, Keyboard::SecondaryModifier)) { @@ -93,7 +93,7 @@ Editor::track_canvas_scroll (GdkEventScroll* ev) return false; } } - gettimeofday (&last_track_height_step_timestamp, 0); + last_track_height_step_timestamp = get_microseconds(); current_stepping_trackview->step_height (true); return true; } else { @@ -118,7 +118,7 @@ Editor::track_canvas_scroll (GdkEventScroll* ev) event.button.x = wx; event.button.y = wy; - nframes_t where = event_frame (&event, 0, 0); + nframes64_t where = event_frame (&event, 0, 0); temporal_zoom_to_frame (true, where); return true; } else if (Keyboard::modifier_state_equals (ev->state, Keyboard::SecondaryModifier)) { @@ -131,7 +131,7 @@ Editor::track_canvas_scroll (GdkEventScroll* ev) return false; } } - gettimeofday (&last_track_height_step_timestamp, 0); + last_track_height_step_timestamp = get_microseconds(); current_stepping_trackview->step_height (false); return true; } else { @@ -180,7 +180,7 @@ Editor::track_canvas_scroll_event (GdkEventScroll *event) bool Editor::time_canvas_scroll (GdkEventScroll* ev) { - nframes_t xdelta; + nframes64_t xdelta; int direction = ev->direction; switch (direction) { diff --git a/gtk2_ardour/editor_cursors.cc b/gtk2_ardour/editor_cursors.cc index 239d27d4f9..54786bcebf 100644 --- a/gtk2_ardour/editor_cursors.cc +++ b/gtk2_ardour/editor_cursors.cc @@ -61,7 +61,7 @@ Editor::Cursor::~Cursor () } void -Editor::Cursor::set_position (nframes_t frame) +Editor::Cursor::set_position (nframes64_t frame) { double new_pos = editor.frame_to_unit (frame); diff --git a/gtk2_ardour/editor_export_audio.cc b/gtk2_ardour/editor_export_audio.cc index 157494b846..c1d0c56833 100644 --- a/gtk2_ardour/editor_export_audio.cc +++ b/gtk2_ardour/editor_export_audio.cc @@ -77,7 +77,7 @@ Editor::export_selection () } void -Editor::export_range (nframes_t start, nframes_t end) +Editor::export_range (nframes64_t start, nframes64_t end) { if (session) { if (export_dialog == 0) { @@ -157,7 +157,12 @@ Editor::bounce_region_selection () itt.cancel = false; itt.progress = 0.0f; - track->bounce_range (region->position(), region->position() + region->length(), itt); + boost::shared_ptr r = track->bounce_range (region->position(), region->position() + region->length(), itt); + cerr << "Result of bounce of " + << region->name() << " len = " << region->length() + << " was " + << r->name() << " len = " << r->length() + << endl; } } @@ -165,11 +170,11 @@ bool Editor::write_region (string path, boost::shared_ptr region) { boost::shared_ptr fs; - const nframes_t chunk_size = 4096; - nframes_t to_read; + const nframes64_t chunk_size = 4096; + nframes64_t to_read; Sample buf[chunk_size]; gain_t gain_buffer[chunk_size]; - nframes_t pos; + nframes64_t pos; char s[PATH_MAX+1]; uint32_t cnt; vector > sources; @@ -234,7 +239,7 @@ Editor::write_region (string path, boost::shared_ptr region) pos = region->position(); while (to_read) { - nframes_t this_time; + nframes64_t this_time; this_time = min (to_read, chunk_size); @@ -312,11 +317,11 @@ bool Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list& range) { boost::shared_ptr fs; - const nframes_t chunk_size = 4096; - nframes_t nframes; + const nframes64_t chunk_size = 4096; + nframes64_t nframes; Sample buf[chunk_size]; gain_t gain_buffer[chunk_size]; - nframes_t pos; + nframes64_t pos; char s[PATH_MAX+1]; uint32_t cnt; string path; @@ -369,7 +374,7 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list pos = (*i).start; while (nframes) { - nframes_t this_time; + nframes64_t this_time; this_time = min (nframes, chunk_size); @@ -401,7 +406,7 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list while (nframes) { - nframes_t this_time = min (nframes, chunk_size); + nframes64_t this_time = min (nframes, chunk_size); memset (buf, 0, sizeof (Sample) * this_time); for (uint32_t n=0; n < channels; ++n) { diff --git a/gtk2_ardour/editor_imageframe.cc b/gtk2_ardour/editor_imageframe.cc index daba2496a0..d4bf497591 100644 --- a/gtk2_ardour/editor_imageframe.cc +++ b/gtk2_ardour/editor_imageframe.cc @@ -95,10 +95,10 @@ void Editor::scroll_timeaxis_to_imageframe_item(const TimeAxisViewItem* item) { // GTK2FIX - //nframes_t offset = static_cast(frames_per_unit * (edit_hscroll_slider_width/2)) ; - nframes_t offset = 0; + //nframes64_t offset = static_cast(frames_per_unit * (edit_hscroll_slider_width/2)) ; + nframes64_t offset = 0; - nframes_t x_pos = 0 ; + nframes64_t x_pos = 0 ; if (item->get_position() < offset) { x_pos = 0 ; @@ -493,14 +493,14 @@ Editor::markerview_drag_motion_callback(ArdourCanvas::Item*, GdkEvent* event) double cx, cy ; MarkerView* mv = reinterpret_cast(drag_info.data) ; - nframes_t pending_region_position ; - nframes_t pointer_frame ; + nframes64_t pending_region_position ; + nframes64_t pointer_frame ; pointer_frame = event_frame(event, &cx, &cy) ; snap_to(pointer_frame) ; - if (pointer_frame > (nframes_t) drag_info.pointer_frame_offset) + if (pointer_frame > (nframes64_t) drag_info.pointer_frame_offset) { pending_region_position = pointer_frame - drag_info.pointer_frame_offset ; snap_to(pending_region_position) ; @@ -541,14 +541,14 @@ Editor::imageframe_drag_motion_callback(ArdourCanvas::Item*, GdkEvent* event) ImageFrameView* ifv = reinterpret_cast(drag_info.data) ; - nframes_t pending_region_position; - nframes_t pointer_frame; + nframes64_t pending_region_position; + nframes64_t pointer_frame; pointer_frame = event_frame(event, &cx, &cy) ; snap_to(pointer_frame) ; - if (pointer_frame > (nframes_t) drag_info.pointer_frame_offset) + if (pointer_frame > (nframes64_t) drag_info.pointer_frame_offset) { pending_region_position = pointer_frame - drag_info.pointer_frame_offset ; snap_to(pending_region_position) ; @@ -576,7 +576,7 @@ Editor::imageframe_drag_motion_callback(ArdourCanvas::Item*, GdkEvent* event) void Editor::timeaxis_item_drag_finished_callback(ArdourCanvas::Item*, GdkEvent* event) { - nframes_t where ; + nframes64_t where ; TimeAxisViewItem* tavi = reinterpret_cast(drag_info.data) ; bool item_x_movement = (drag_info.last_frame_position != tavi->get_position()) ; @@ -674,9 +674,9 @@ Editor::imageframe_start_handle_trim_motion(ArdourCanvas::Item* item, GdkEvent* { ImageFrameView* ifv = reinterpret_cast (drag_info.data) ; - nframes_t start = 0 ; - nframes_t end = 0 ; - nframes_t pointer_frame = event_frame(event) ; + nframes64_t start = 0 ; + nframes64_t end = 0 ; + nframes64_t pointer_frame = event_frame(event) ; // chekc th eposition of the item is not locked if(!ifv->get_position_locked()) { @@ -693,7 +693,7 @@ Editor::imageframe_start_handle_trim_motion(ArdourCanvas::Item* item, GdkEvent* } // are we getting bigger or smaller? - nframes_t new_dur_val = end - start ; + nframes64_t new_dur_val = end - start ; // start handle, so a smaller pointer frame increases our component size if(pointer_frame <= drag_info.grab_frame) @@ -751,10 +751,10 @@ Editor::imageframe_start_handle_end_trim(ArdourCanvas::Item* item, GdkEvent* eve } else { - nframes_t temp = ifv->get_position() + ifv->get_duration() ; + nframes64_t temp = ifv->get_position() + ifv->get_duration() ; - ifv->set_position((nframes_t) (temp - drag_info.cumulative_x_drag), this) ; - ifv->set_duration((nframes_t) drag_info.cumulative_x_drag, this) ; + ifv->set_position((nframes64_t) (temp - drag_info.cumulative_x_drag), this) ; + ifv->set_duration((nframes64_t) drag_info.cumulative_x_drag, this) ; } } @@ -763,10 +763,10 @@ Editor::imageframe_end_handle_trim_motion(ArdourCanvas::Item* item, GdkEvent* ev { ImageFrameView* ifv = reinterpret_cast (drag_info.data) ; - nframes_t start = 0 ; - nframes_t end = 0 ; - nframes_t pointer_frame = event_frame(event) ; - nframes_t new_dur_val = 0 ; + nframes64_t start = 0 ; + nframes64_t end = 0 ; + nframes64_t pointer_frame = event_frame(event) ; + nframes64_t new_dur_val = 0 ; snap_to(pointer_frame) ; @@ -828,7 +828,7 @@ Editor::imageframe_end_handle_end_trim (ArdourCanvas::Item* item, GdkEvent* even } else { - nframes_t new_duration = (nframes_t)drag_info.cumulative_x_drag ; + nframes64_t new_duration = (nframes64_t)drag_info.cumulative_x_drag ; if((new_duration <= ifv->get_max_duration()) && (new_duration >= ifv->get_min_duration())) { ifv->set_duration(new_duration, this) ; @@ -888,9 +888,9 @@ Editor::markerview_start_handle_trim_motion(ArdourCanvas::Item* item, GdkEvent* { MarkerView* mv = reinterpret_cast (drag_info.data) ; - nframes_t start = 0 ; - nframes_t end = 0 ; - nframes_t pointer_frame = event_frame(event) ; + nframes64_t start = 0 ; + nframes64_t end = 0 ; + nframes64_t pointer_frame = event_frame(event) ; // chekc th eposition of the item is not locked if(!mv->get_position_locked()) @@ -911,7 +911,7 @@ Editor::markerview_start_handle_trim_motion(ArdourCanvas::Item* item, GdkEvent* } // are we getting bigger or smaller? - nframes_t new_dur_val = end - start ; + nframes64_t new_dur_val = end - start ; if(pointer_frame <= drag_info.grab_frame) { @@ -968,10 +968,10 @@ Editor::markerview_start_handle_end_trim(ArdourCanvas::Item* item, GdkEvent* eve } else { - nframes_t temp = mv->get_position() + mv->get_duration() ; + nframes64_t temp = mv->get_position() + mv->get_duration() ; - mv->set_position((nframes_t) (temp - drag_info.cumulative_x_drag), this) ; - mv->set_duration((nframes_t) drag_info.cumulative_x_drag, this) ; + mv->set_position((nframes64_t) (temp - drag_info.cumulative_x_drag), this) ; + mv->set_duration((nframes64_t) drag_info.cumulative_x_drag, this) ; } } @@ -980,10 +980,10 @@ Editor::markerview_end_handle_trim_motion(ArdourCanvas::Item* item, GdkEvent* ev { MarkerView* mv = reinterpret_cast (drag_info.data) ; - nframes_t start = 0 ; - nframes_t end = 0 ; - nframes_t pointer_frame = event_frame(event) ; - nframes_t new_dur_val = 0 ; + nframes64_t start = 0 ; + nframes64_t end = 0 ; + nframes64_t pointer_frame = event_frame(event) ; + nframes64_t new_dur_val = 0 ; snap_to(pointer_frame) ; @@ -1008,7 +1008,7 @@ Editor::markerview_end_handle_trim_motion(ArdourCanvas::Item* item, GdkEvent* ev { // we cant extend beyond the item we are marking ImageFrameView* marked_item = mv->get_marked_item() ; - nframes_t marked_end = marked_item->get_position() + marked_item->get_duration() ; + nframes64_t marked_end = marked_item->get_position() + marked_item->get_duration() ; if(mv->get_max_duration_active() && (new_dur_val > mv->get_max_duration())) { @@ -1062,7 +1062,7 @@ Editor::markerview_end_handle_end_trim (ArdourCanvas::Item* item, GdkEvent* even } else { - nframes_t new_duration = (nframes_t)drag_info.cumulative_x_drag ; + nframes64_t new_duration = (nframes64_t)drag_info.cumulative_x_drag ; mv->set_duration(new_duration, this) ; } } diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index 60f838f06a..059855ccf5 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -375,8 +375,8 @@ Editor::LocationMarkers::set_name (const string& str) } void -Editor::LocationMarkers::set_position (nframes_t startf, - nframes_t endf) +Editor::LocationMarkers::set_position (nframes64_t startf, + nframes64_t endf) { start->set_position (startf); if (end) { end->set_position (endf); } @@ -390,7 +390,7 @@ Editor::LocationMarkers::set_color_rgba (uint32_t rgba) } void -Editor::mouse_add_new_marker (nframes_t where, bool is_cd, bool is_xrun) +Editor::mouse_add_new_marker (nframes64_t where, bool is_cd, bool is_xrun) { string markername, markerprefix; int flags = (is_cd ? Location::IsCDMarker|Location::IsMark : Location::IsMark); @@ -404,6 +404,9 @@ Editor::mouse_add_new_marker (nframes_t where, bool is_cd, bool is_xrun) if (session) { session->locations()->next_available_name(markername, markerprefix); + if (!is_xrun && !choose_new_marker_name(markername)) { + return; + } Location *location = new Location (where, where, markername, (Location::Flags) flags); session->begin_reversible_command (_("add marker")); XMLNode &before = session->locations()->get_state(); @@ -594,6 +597,8 @@ Editor::build_marker_menu (bool start_or_end) items.push_back (SeparatorElem()); + items.push_back (MenuElem (_("Create range to next marker"), mem_fun(*this, &Editor::marker_menu_range_to_next))); + items.push_back (MenuElem (_("Hide"), mem_fun(*this, &Editor::marker_menu_hide))); if (start_or_end) return; items.push_back (MenuElem (_("Rename"), mem_fun(*this, &Editor::marker_menu_rename))); @@ -630,9 +635,11 @@ Editor::build_range_marker_menu (bool loop_or_punch) items.push_back (MenuElem (_("Set Range from Range Selection"), mem_fun(*this, &Editor::marker_menu_set_from_selection))); } + items.push_back (SeparatorElem()); + items.push_back (MenuElem (_("Export Range"), mem_fun(*this, &Editor::marker_menu_export_range))); items.push_back (SeparatorElem()); - if (! loop_or_punch) { + if (!loop_or_punch) { items.push_back (MenuElem (_("Hide Range"), mem_fun(*this, &Editor::marker_menu_hide))); items.push_back (MenuElem (_("Rename Range"), mem_fun(*this, &Editor::marker_menu_rename))); items.push_back (MenuElem (_("Remove Range"), mem_fun(*this, &Editor::marker_menu_remove))); @@ -807,6 +814,57 @@ Editor::marker_menu_set_playhead () } } +void +Editor::marker_menu_export_range () +{ + Marker* marker; + + if ((marker = reinterpret_cast (marker_menu_item->get_data ("marker"))) == 0) { + fatal << _("programming error: marker canvas item has no marker object pointer!") << endmsg; + /*NOTREACHED*/ + } + + Location* l; + bool is_start; + + if ((l = find_location_from_marker (marker, is_start)) != 0) { + if (l->is_range_marker()) { + export_range (l->start(), l->end()); + } + } +} + +void +Editor::marker_menu_range_to_next () +{ + Marker* marker; + if (!session) { + return; + } + + if ((marker = reinterpret_cast (marker_menu_item->get_data ("marker"))) == 0) { + fatal << _("programming error: marker canvas item has no marker object pointer!") << endmsg; + /*NOTREACHED*/ + } + + Location* l; + bool is_start; + + if ((l = find_location_from_marker (marker, is_start)) == 0) { + return; + } + + nframes_t end = session->locations()->first_mark_after (marker->position()); + + if (end != max_frames) { + string range_name = l->name(); + range_name += "-range"; + + Location* newrange = new Location (marker->position(), end, range_name, Location::IsRangeMarker); + session->locations()->add (newrange); + } +} + void Editor::marker_menu_set_from_playhead () { diff --git a/gtk2_ardour/editor_mixer.cc b/gtk2_ardour/editor_mixer.cc index b732487740..5c9208fcfb 100644 --- a/gtk2_ardour/editor_mixer.cc +++ b/gtk2_ardour/editor_mixer.cc @@ -191,7 +191,7 @@ Editor::update_current_screen () { if (session && session->engine().running()) { - nframes_t frame; + nframes64_t frame; frame = session->audible_frame(); @@ -253,11 +253,7 @@ Editor::update_current_screen () } else { if (frame != last_update_frame) { - if (frame < leftmost_frame || frame > leftmost_frame + current_page_frames()) { - playhead_cursor->canvas_item.hide(); - } else { - playhead_cursor->set_position (frame); - } + playhead_cursor->set_position (frame); } } diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc index e1d320e386..384f40fdf6 100644 --- a/gtk2_ardour/editor_mouse.cc +++ b/gtk2_ardour/editor_mouse.cc @@ -598,6 +598,25 @@ Editor::button_selection (ArdourCanvas::Item* item, GdkEvent* event, ItemType it bool Editor::button_press_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_type) { + Glib::RefPtr canvas_window = const_cast(this)->track_canvas->get_window(); + + if (canvas_window) { + Glib::RefPtr pointer_window; + int x, y; + double wx, wy; + Gdk::ModifierType mask; + + pointer_window = canvas_window->get_pointer (x, y, mask); + + if (pointer_window == track_canvas->get_bin_window()) { + + track_canvas->window_to_world (x, y, wx, wy); + allow_vertical_scroll = true; + } else { + allow_vertical_scroll = false; + } + } + track_canvas->grab_focus(); if (session && session->actively_recording()) { @@ -959,7 +978,7 @@ Editor::button_press_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemTyp bool Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_type) { - nframes_t where = event_frame (event, 0, 0); + nframes64_t where = event_frame (event, 0, 0); AutomationTimeAxisView* atv = 0; /* no action if we're recording */ @@ -1705,7 +1724,7 @@ Editor::motion_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item track_canvas->get_pointer (x, y); } - + if (current_stepping_trackview) { /* don't keep the persistent stepped trackview if the mouse moves */ current_stepping_trackview = 0; @@ -1993,15 +2012,16 @@ Editor::start_fade_in_grab (ArdourCanvas::Item* item, GdkEvent* event) AudioRegionView* arv = static_cast(drag_info.data); - drag_info.pointer_frame_offset = drag_info.grab_frame - ((nframes_t) arv->audio_region()->fade_in()->back()->when + arv->region()->position()); + + drag_info.pointer_frame_offset = drag_info.grab_frame - ((nframes64_t) arv->audio_region()->fade_in()->back()->when + arv->region()->position()); } void Editor::fade_in_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { AudioRegionView* arv = static_cast(drag_info.data); - nframes_t pos; - nframes_t fade_length; + nframes64_t pos; + nframes64_t fade_length; if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { pos = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -2043,8 +2063,8 @@ void Editor::fade_in_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event) { AudioRegionView* arv = static_cast(drag_info.data); - nframes_t pos; - nframes_t fade_length; + nframes64_t pos; + nframes64_t fade_length; if (drag_info.first_move) return; @@ -2101,15 +2121,15 @@ Editor::start_fade_out_grab (ArdourCanvas::Item* item, GdkEvent* event) AudioRegionView* arv = static_cast(drag_info.data); - drag_info.pointer_frame_offset = drag_info.grab_frame - (arv->region()->length() - (nframes_t) arv->audio_region()->fade_out()->back()->when + arv->region()->position()); + drag_info.pointer_frame_offset = drag_info.grab_frame - (arv->region()->length() - (nframes64_t) arv->audio_region()->fade_out()->back()->when + arv->region()->position()); } void Editor::fade_out_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { AudioRegionView* arv = static_cast(drag_info.data); - nframes_t pos; - nframes_t fade_length; + nframes64_t pos; + nframes64_t fade_length; if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { pos = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -2155,8 +2175,8 @@ Editor::fade_out_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* eve if (drag_info.first_move) return; AudioRegionView* arv = static_cast(drag_info.data); - nframes_t pos; - nframes_t fade_length; + nframes64_t pos; + nframes64_t fade_length; if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { pos = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -2239,7 +2259,7 @@ void Editor::cursor_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { Cursor* cursor = (Cursor *) drag_info.data; - nframes_t adjusted_frame; + nframes64_t adjusted_frame; if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { adjusted_frame = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -2362,21 +2382,21 @@ Editor::start_marker_grab (ArdourCanvas::Item* item, GdkEvent* event) void Editor::marker_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { - nframes_t f_delta; + nframes64_t f_delta; Marker* marker = (Marker *) drag_info.data; Location *real_location; Location *copy_location; bool is_start; bool move_both = false; - nframes_t newframe; + nframes64_t newframe; if (drag_info.pointer_frame_offset <= drag_info.current_pointer_frame) { newframe = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; } else { newframe = 0; } - nframes_t next = newframe; + nframes64_t next = newframe; if (!Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier())) { snap_to (newframe, 0, true); @@ -2562,7 +2582,7 @@ void Editor::meter_marker_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { MeterMarker* marker = (MeterMarker *) drag_info.data; - nframes_t adjusted_frame; + nframes64_t adjusted_frame; if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { adjusted_frame = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -2694,7 +2714,7 @@ void Editor::tempo_marker_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { TempoMarker* marker = (TempoMarker *) drag_info.data; - nframes_t adjusted_frame; + nframes64_t adjusted_frame; if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { adjusted_frame = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -2866,7 +2886,7 @@ Editor::control_point_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* cy = min ((double) (cp->line().y_position() + cp->line().height()), cy); //translate cx to frames - nframes_t cx_frames = unit_to_frame (cx); + nframes64_t cx_frames = unit_to_frame (cx); if (!Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier()) && !drag_info.x_constrained) { snap_to (cx_frames); @@ -2939,7 +2959,7 @@ Editor::start_line_grab (AutomationLine* line, GdkEvent* event) { double cx; double cy; - nframes_t frame_within_region; + nframes64_t frame_within_region; /* need to get x coordinate in terms of parent (TimeAxisItemView) origin. @@ -2948,7 +2968,7 @@ Editor::start_line_grab (AutomationLine* line, GdkEvent* event) cx = event->button.x; cy = event->button.y; line->parent_group().w2i (cx, cy); - frame_within_region = (nframes_t) floor (cx * frames_per_unit); + frame_within_region = (nframes64_t) floor (cx * frames_per_unit); if (!line->control_points_adjacent (frame_within_region, current_line_drag_info.before, current_line_drag_info.after)) { @@ -3057,7 +3077,7 @@ Editor::start_region_grab (ArdourCanvas::Item* item, GdkEvent* event) speed = tv->get_diskstream()->speed(); } - drag_info.last_frame_position = (nframes_t) (clicked_regionview->region()->position() / speed); + drag_info.last_frame_position = (nframes64_t) (clicked_regionview->region()->position() / speed); drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position; drag_info.source_trackview = &clicked_regionview->get_time_axis_view(); drag_info.dest_trackview = drag_info.source_trackview; @@ -3106,7 +3126,7 @@ Editor::start_region_copy_grab (ArdourCanvas::Item* item, GdkEvent* event) drag_info.source_trackview = &clicked_regionview->get_time_axis_view(); drag_info.dest_trackview = drag_info.source_trackview; - drag_info.last_frame_position = (nframes_t) (clicked_regionview->region()->position() / speed); + drag_info.last_frame_position = (nframes64_t) (clicked_regionview->region()->position() / speed); drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position; // we want a move threshold drag_info.want_move_threshold = true; @@ -3138,7 +3158,7 @@ Editor::start_region_brush_grab (ArdourCanvas::Item* item, GdkEvent* event) speed = tv->get_diskstream()->speed(); } - drag_info.last_frame_position = (nframes_t) (clicked_regionview->region()->position() / speed); + drag_info.last_frame_position = (nframes64_t) (clicked_regionview->region()->position() / speed); drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position; drag_info.source_trackview = &clicked_regionview->get_time_axis_view(); drag_info.dest_trackview = drag_info.source_trackview; @@ -3164,7 +3184,7 @@ Editor::possibly_copy_regions_during_grab (GdkEvent* event) RegionView* rv; RegionView* nrv; - + rv = (*i); AudioRegionView* arv = dynamic_cast(rv); @@ -3309,7 +3329,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) double x_delta; double y_delta = 0; RegionView* rv = reinterpret_cast (drag_info.data); - nframes_t pending_region_position = 0; + nframes64_t pending_region_position = 0; int32_t pointer_y_span = 0, canvas_pointer_y_span = 0, original_pointer_order; int32_t visible_y_high = 0, visible_y_low = 512; //high meaning higher numbered.. not the height on the screen bool clamp_y_axis = false; @@ -3363,12 +3383,13 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) tracks = tracks |= (0x01 << rtv2->order); } - height_list[rtv2->order] = (*i)->height; + height_list[rtv2->order] = (*i)->current_height(); children = 1; + if ((children_list = rtv2->get_child_list()).size() > 0) { for (TimeAxisView::Children::iterator j = children_list.begin(); j != children_list.end(); ++j) { tracks = tracks |= (0x01 << (rtv2->order + children)); - height_list[rtv2->order + children] = (*j)->height; + height_list[rtv2->order + children] = (*j)->current_height(); numtracks++; children++; } @@ -3496,8 +3517,8 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { - nframes_t sync_frame; - nframes_t sync_offset; + nframes64_t sync_frame; + nframes64_t sync_offset; int32_t sync_dir; pending_region_position = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -3685,7 +3706,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) tvp2 = trackview_by_y_position (iy1 + y_delta); temp_rtv = dynamic_cast(tvp2); - rv->set_y_position_and_height (0, temp_rtv->height); + rv->set_y_position_and_height (0, temp_rtv->current_height()); /* if you un-comment the following, the region colours will follow the track colours whilst dragging, personally, i think this can confuse things, but never mind. @@ -3837,7 +3858,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event double speed; bool changed_tracks; bool changed_position; - nframes_t where; + nframes64_t where; if (rv->region()->locked()) { ++i; @@ -3852,11 +3873,11 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event speed = dest_rtv->get_diskstream()->speed(); } - changed_position = (drag_info.last_frame_position != (nframes_t) (rv->region()->position()/speed)); + changed_position = (drag_info.last_frame_position != (nframes64_t) (rv->region()->position()/speed)); changed_tracks = (dest_tv != &rv->get_time_axis_view()); if (changed_position && !drag_info.x_constrained) { - where = (nframes_t) (unit_to_frame (ix1) * speed); + where = (nframes64_t) (unit_to_frame (ix1) * speed); } else { where = rv->region()->position(); } @@ -3869,6 +3890,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event boost::shared_ptr new_region; + if (drag_info.copy) { /* we already made a copy */ new_region = rv->region(); @@ -3918,7 +3940,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event /* get the playlist where this drag started. we can't use rv->region()->playlist() because we may have copied the region and it has not been attached to a playlist. */ - + assert ((source_tv = dynamic_cast (&rv->get_time_axis_view()))); assert ((ds = source_tv->get_diskstream())); assert ((from_playlist = ds->playlist())); @@ -4036,7 +4058,7 @@ Editor::create_region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent begin_reversible_command (_("create region")); XMLNode &before = mtv->playlist()->get_state(); - nframes_t start = drag_info.grab_frame; + nframes64_t start = drag_info.grab_frame; snap_to (start, -1); const Meter& m = session->tempo_map().meter_at(start); const Tempo& t = session->tempo_map().tempo_at(start); @@ -4078,28 +4100,28 @@ Editor::region_view_item_click (AudioRegionView& rv, GdkEventButton* event) if (Keyboard::modifier_state_equals (event->state, Keyboard::ModifierMask (Keyboard::PrimaryModifier|Keyboard::SecondaryModifier))) { - align_region (rv.region(), SyncPoint, (nframes_t) (where * speed)); + align_region (rv.region(), SyncPoint, (nframes64_t) (where * speed)); } else if (Keyboard::modifier_state_equals (event->state, Keyboard::ModifierMask (Keyboard::PrimaryModifier|Keyboard::TertiaryModifier))) { - align_region (rv.region(), End, (nframes_t) (where * speed)); + align_region (rv.region(), End, (nframes64_t) (where * speed)); } else { - align_region (rv.region(), Start, (nframes_t) (where * speed)); + align_region (rv.region(), Start, (nframes64_t) (where * speed)); } } } } void -Editor::show_verbose_time_cursor (nframes_t frame, double offset, double xpos, double ypos) +Editor::show_verbose_time_cursor (nframes64_t frame, double offset, double xpos, double ypos) { char buf[128]; SMPTE::Time smpte; BBT_Time bbt; int hours, mins; - nframes_t frame_rate; + nframes64_t frame_rate; float secs; if (session == 0) { @@ -4137,7 +4159,7 @@ Editor::show_verbose_time_cursor (nframes_t frame, double offset, double xpos, d break; default: - snprintf (buf, sizeof(buf), "%u", frame); + snprintf (buf, sizeof(buf), "%" PRIi64, frame); break; } @@ -4151,14 +4173,14 @@ Editor::show_verbose_time_cursor (nframes_t frame, double offset, double xpos, d } void -Editor::show_verbose_duration_cursor (nframes_t start, nframes_t end, double offset, double xpos, double ypos) +Editor::show_verbose_duration_cursor (nframes64_t start, nframes64_t end, double offset, double xpos, double ypos) { char buf[128]; SMPTE::Time smpte; BBT_Time sbbt; BBT_Time ebbt; int hours, mins; - nframes_t distance, frame_rate; + nframes64_t distance, frame_rate; float secs; Meter meter_at_start(session->tempo_map().meter_at(start)); @@ -4219,7 +4241,7 @@ Editor::show_verbose_duration_cursor (nframes_t start, nframes_t end, double off break; default: - snprintf (buf, sizeof(buf), "%u", end - start); + snprintf (buf, sizeof(buf), "%" PRIi64, end - start); break; } @@ -4331,8 +4353,8 @@ Editor::cancel_selection () void Editor::start_selection_op (ArdourCanvas::Item* item, GdkEvent* event, SelectionOp op) { - nframes_t start = 0; - nframes_t end = 0; + nframes64_t start = 0; + nframes64_t end = 0; if (session == 0) { return; @@ -4389,10 +4411,10 @@ Editor::start_selection_op (ArdourCanvas::Item* item, GdkEvent* event, Selection void Editor::drag_selection (ArdourCanvas::Item* item, GdkEvent* event) { - nframes_t start = 0; - nframes_t end = 0; - nframes_t length; - nframes_t pending_position; + nframes64_t start = 0; + nframes64_t end = 0; + nframes64_t length; + nframes64_t pending_position; if (drag_info.current_pointer_frame > drag_info.pointer_frame_offset) { pending_position = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; @@ -4550,9 +4572,9 @@ Editor::start_trim (ArdourCanvas::Item* item, GdkEvent* event) speed = tv->get_diskstream()->speed(); } - nframes_t region_start = (nframes_t) (clicked_regionview->region()->position() / speed); - nframes_t region_end = (nframes_t) (clicked_regionview->region()->last_frame() / speed); - nframes_t region_length = (nframes_t) (clicked_regionview->region()->length() / speed); + nframes64_t region_start = (nframes64_t) (clicked_regionview->region()->position() / speed); + nframes64_t region_end = (nframes64_t) (clicked_regionview->region()->last_frame() / speed); + nframes64_t region_length = (nframes64_t) (clicked_regionview->region()->length() / speed); //drag_info.item = clicked_regionview->get_name_highlight(); drag_info.item = item; @@ -4591,7 +4613,7 @@ void Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { RegionView* rv = clicked_regionview; - nframes_t frame_delta = 0; + nframes64_t frame_delta = 0; bool left_direction; bool obey_snap = !Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier()); @@ -4676,7 +4698,7 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) } case EndTrim: - if ((left_direction == true) && (drag_info.current_pointer_frame > (nframes_t) (rv->region()->last_frame()/speed))) { + if ((left_direction == true) && (drag_info.current_pointer_frame > (nframes64_t) (rv->region()->last_frame()/speed))) { break; } else { for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { @@ -4704,10 +4726,10 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) switch (trim_op) { case StartTrim: - show_verbose_time_cursor((nframes_t) (rv->region()->position()/speed), 10); + show_verbose_time_cursor((nframes64_t) (rv->region()->position()/speed), 10); break; case EndTrim: - show_verbose_time_cursor((nframes_t) (rv->region()->last_frame()/speed), 10); + show_verbose_time_cursor((nframes64_t) (rv->region()->last_frame()/speed), 10); break; case ContentsTrim: show_verbose_time_cursor(drag_info.current_pointer_frame, 10); @@ -4719,7 +4741,7 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) } void -Editor::single_contents_trim (RegionView& rv, nframes_t frame_delta, bool left_direction, bool swap_direction, bool obey_snap) +Editor::single_contents_trim (RegionView& rv, nframes64_t frame_delta, bool left_direction, bool swap_direction, bool obey_snap) { boost::shared_ptr region (rv.region()); @@ -4727,7 +4749,7 @@ Editor::single_contents_trim (RegionView& rv, nframes_t frame_delta, bool left_d return; } - nframes_t new_bound; + nframes64_t new_bound; double speed = 1.0; TimeAxisView* tvp = clicked_axisview; @@ -4739,27 +4761,27 @@ Editor::single_contents_trim (RegionView& rv, nframes_t frame_delta, bool left_d if (left_direction) { if (swap_direction) { - new_bound = (nframes_t) (region->position()/speed) + frame_delta; + new_bound = (nframes64_t) (region->position()/speed) + frame_delta; } else { - new_bound = (nframes_t) (region->position()/speed) - frame_delta; + new_bound = (nframes64_t) (region->position()/speed) - frame_delta; } } else { if (swap_direction) { - new_bound = (nframes_t) (region->position()/speed) - frame_delta; + new_bound = (nframes64_t) (region->position()/speed) - frame_delta; } else { - new_bound = (nframes_t) (region->position()/speed) + frame_delta; + new_bound = (nframes64_t) (region->position()/speed) + frame_delta; } } if (obey_snap) { snap_to (new_bound); } - region->trim_start ((nframes_t) (new_bound * speed), this); + region->trim_start ((nframes64_t) (new_bound * speed), this); rv.region_changed (StartChanged); } void -Editor::single_start_trim (RegionView& rv, nframes_t frame_delta, bool left_direction, bool obey_snap) +Editor::single_start_trim (RegionView& rv, nframes64_t frame_delta, bool left_direction, bool obey_snap) { boost::shared_ptr region (rv.region()); @@ -4767,7 +4789,7 @@ Editor::single_start_trim (RegionView& rv, nframes_t frame_delta, bool left_dire return; } - nframes_t new_bound; + nframes64_t new_bound; double speed = 1.0; TimeAxisView* tvp = clicked_axisview; @@ -4778,22 +4800,22 @@ Editor::single_start_trim (RegionView& rv, nframes_t frame_delta, bool left_dire } if (left_direction) { - new_bound = (nframes_t) (region->position()/speed) - frame_delta; + new_bound = (nframes64_t) (region->position()/speed) - frame_delta; } else { - new_bound = (nframes_t) (region->position()/speed) + frame_delta; + new_bound = (nframes64_t) (region->position()/speed) + frame_delta; } if (obey_snap) { snap_to (new_bound, (left_direction ? 0 : 1)); } - region->trim_front ((nframes_t) (new_bound * speed), this); + region->trim_front ((nframes64_t) (new_bound * speed), this); rv.region_changed (Change (LengthChanged|PositionChanged|StartChanged)); } void -Editor::single_end_trim (RegionView& rv, nframes_t frame_delta, bool left_direction, bool obey_snap) +Editor::single_end_trim (RegionView& rv, nframes64_t frame_delta, bool left_direction, bool obey_snap) { boost::shared_ptr region (rv.region()); @@ -4801,7 +4823,7 @@ Editor::single_end_trim (RegionView& rv, nframes_t frame_delta, bool left_direct return; } - nframes_t new_bound; + nframes64_t new_bound; double speed = 1.0; TimeAxisView* tvp = clicked_axisview; @@ -4812,15 +4834,15 @@ Editor::single_end_trim (RegionView& rv, nframes_t frame_delta, bool left_direct } if (left_direction) { - new_bound = (nframes_t) ((region->last_frame() + 1)/speed) - frame_delta; + new_bound = (nframes64_t) ((region->last_frame() + 1)/speed) - frame_delta; } else { - new_bound = (nframes_t) ((region->last_frame() + 1)/speed) + frame_delta; + new_bound = (nframes64_t) ((region->last_frame() + 1)/speed) + frame_delta; } if (obey_snap) { snap_to (new_bound); } - region->trim_end ((nframes_t) (new_bound * speed), this); + region->trim_end ((nframes64_t) (new_bound * speed), this); rv.region_changed (LengthChanged); } @@ -4860,7 +4882,7 @@ void Editor::point_trim (GdkEvent* event) { RegionView* rv = clicked_regionview; - nframes_t new_bound = drag_info.current_pointer_frame; + nframes64_t new_bound = drag_info.current_pointer_frame; if (!Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier())) { snap_to (new_bound); @@ -5008,8 +5030,8 @@ Editor::start_range_markerbar_op (ArdourCanvas::Item* item, GdkEvent* event, Ran void Editor::drag_range_markerbar_op (ArdourCanvas::Item* item, GdkEvent* event) { - nframes_t start = 0; - nframes_t end = 0; + nframes64_t start = 0; + nframes64_t end = 0; ArdourCanvas::SimpleRect *crect; switch (range_marker_op) { @@ -5140,8 +5162,8 @@ Editor::end_range_markerbar_op (ArdourCanvas::Item* item, GdkEvent* event) if (Keyboard::no_modifier_keys_pressed (&event->button) && range_marker_op != CreateCDMarker) { - nframes_t start; - nframes_t end; + nframes64_t start; + nframes64_t end; start = session->locations()->first_mark_before (drag_info.grab_frame); end = session->locations()->first_mark_after (drag_info.grab_frame); @@ -5191,8 +5213,8 @@ Editor::start_mouse_zoom (ArdourCanvas::Item* item, GdkEvent* event) void Editor::drag_mouse_zoom (ArdourCanvas::Item* item, GdkEvent* event) { - nframes_t start; - nframes_t end; + nframes64_t start; + nframes64_t end; if (!Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier())) { snap_to (drag_info.current_pointer_frame); @@ -5252,7 +5274,7 @@ Editor::end_mouse_zoom (ArdourCanvas::Item* item, GdkEvent* event) } void -Editor::reposition_zoom_rect (nframes_t start, nframes_t end) +Editor::reposition_zoom_rect (nframes64_t start, nframes64_t end) { double x1 = frame_to_pixel (start); double x2 = frame_to_pixel (end); @@ -5279,8 +5301,8 @@ Editor::start_rubberband_select (ArdourCanvas::Item* item, GdkEvent* event) void Editor::drag_rubberband_select (ArdourCanvas::Item* item, GdkEvent* event) { - nframes_t start; - nframes_t end; + nframes64_t start; + nframes64_t end; double y1; double y2; @@ -5453,7 +5475,7 @@ Editor::end_time_fx (ArdourCanvas::Item* item, GdkEvent* event) return; } - nframes_t newlen = drag_info.last_pointer_frame - clicked_regionview->region()->position(); + nframes64_t newlen = drag_info.last_pointer_frame - clicked_regionview->region()->position(); float percentage = (double) newlen / (double) clicked_regionview->region()->length(); @@ -5477,7 +5499,7 @@ Editor::end_time_fx (ArdourCanvas::Item* item, GdkEvent* event) } void -Editor::mouse_brush_insert_region (RegionView* rv, nframes_t pos) +Editor::mouse_brush_insert_region (RegionView* rv, nframes64_t pos) { /* no brushing without a useful snap setting */ @@ -5516,7 +5538,7 @@ Editor::mouse_brush_insert_region (RegionView* rv, nframes_t pos) double speed = rtv->get_diskstream()->speed(); XMLNode &before = playlist->get_state(); - playlist->add_region (boost::dynamic_pointer_cast (RegionFactory::create (arv->audio_region())), (nframes_t) (pos * speed)); + playlist->add_region (boost::dynamic_pointer_cast (RegionFactory::create (arv->audio_region())), (nframes64_t) (pos * speed)); XMLNode &after = playlist->get_state(); session->add_command(new MementoCommand(*playlist.get(), &before, &after)); @@ -5528,13 +5550,7 @@ Editor::mouse_brush_insert_region (RegionView* rv, nframes_t pos) gint Editor::track_height_step_timeout () { - struct timeval now; - struct timeval delta; - - gettimeofday (&now, 0); - timersub (&now, &last_track_height_step_timestamp, &delta); - - if (delta.tv_sec * 1000000 + delta.tv_usec > 250000) { /* milliseconds */ + if (get_microseconds() - last_track_height_step_timestamp < 250000) { current_stepping_trackview = 0; return false; } diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index ffe7c1fe16..fd482a9dd6 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -25,6 +25,7 @@ #include #include #include +#include #include #include @@ -35,6 +36,8 @@ #include #include #include +#include + #include #include @@ -109,7 +112,7 @@ Editor::split_region () } void -Editor::split_region_at (nframes_t where) +Editor::split_region_at (nframes64_t where) { RegionSelection rs; @@ -118,7 +121,7 @@ Editor::split_region_at (nframes_t where) } void -Editor::split_regions_at (nframes_t where, RegionSelection& regions) +Editor::split_regions_at (nframes64_t where, RegionSelection& regions) { list > used_playlists; @@ -144,6 +147,8 @@ Editor::split_regions_at (nframes_t where, RegionSelection& regions) snap_to (where); } + cerr << "Split " << regions.size() << " at " << where << endl; + for (RegionSelection::iterator a = regions.begin(); a != regions.end(); ) { RegionSelection::iterator tmp; @@ -219,21 +224,44 @@ Editor::remove_clicked_region () void Editor::remove_selected_regions () { - if (selection->regions.empty()) { + RegionSelection rs; + get_regions_for_action (rs); + + if (!session) { + return; + } + + if (rs.empty()) { return; } - /* XXX: should be called remove regions if we're removing more than one */ begin_reversible_command (_("remove region")); - - while (!selection->regions.empty()) { - boost::shared_ptr region = selection->regions.front()->region (); - boost::shared_ptr playlist = region->playlist (); + list > regions_to_remove; - XMLNode &before = playlist->get_state(); - playlist->remove_region (region); - XMLNode &after = playlist->get_state(); + for (RegionSelection::iterator i = rs.begin(); i != rs.end(); ++i) { + // we can't just remove the region(s) in this loop because + // this removes them from the RegionSelection, and they thus + // disappear from underneath the iterator, and the ++i above + // SEGVs in a puzzling fashion. + + // so, first iterate over the regions to be removed from rs and + // add them to the regions_to_remove list, and then + // iterate over the list to actually remove them. + + regions_to_remove.push_back ((*i)->region()); + } + + for (list >::iterator rl = regions_to_remove.begin(); rl != regions_to_remove.end(); ++rl) { + boost::shared_ptr playlist = (*rl)->playlist(); + if (!playlist) { + // is this check necessary? + continue; + } + + XMLNode &before = playlist->get_state(); + playlist->remove_region (*rl); + XMLNode &after = playlist->get_state(); session->add_command(new MementoCommand(*playlist, &before, &after)); } @@ -245,7 +273,7 @@ Editor::select_region_for_operation (int dir, TimeAxisView **tv) { RegionView* rv; boost::shared_ptr region; - nframes_t start = 0; + nframes64_t start = 0; if (selection->time.start () == selection->time.end_frame ()) { @@ -288,7 +316,7 @@ Editor::extend_selection_to_end_of_region (bool next) { TimeAxisView *tv; boost::shared_ptr region; - nframes_t start; + nframes64_t start; if ((region = select_region_for_operation (next ? 1 : 0, &tv)) == 0) { return; @@ -316,7 +344,7 @@ Editor::extend_selection_to_start_of_region (bool previous) { TimeAxisView *tv; boost::shared_ptr region; - nframes_t end; + nframes64_t end; if ((region = select_region_for_operation (previous ? -1 : 0, &tv)) == 0) { return; @@ -365,8 +393,8 @@ Editor::nudge_backward_release (GdkEventButton* ev) void Editor::nudge_forward (bool next, bool force_playhead) { - nframes_t distance; - nframes_t next_distance; + nframes64_t distance; + nframes64_t next_distance; RegionSelection rs; get_regions_for_action (rs); @@ -441,8 +469,8 @@ Editor::nudge_forward (bool next, bool force_playhead) void Editor::nudge_backward (bool next, bool force_playhead) { - nframes_t distance; - nframes_t next_distance; + nframes64_t distance; + nframes64_t next_distance; RegionSelection rs; get_regions_for_action (rs); @@ -528,7 +556,7 @@ Editor::nudge_backward (bool next, bool force_playhead) void Editor::nudge_forward_capture_offset () { - nframes_t distance; + nframes64_t distance; RegionSelection rs; get_regions_for_action (rs); @@ -558,7 +586,7 @@ Editor::nudge_forward_capture_offset () void Editor::nudge_backward_capture_offset () { - nframes_t distance; + nframes64_t distance; RegionSelection rs; get_regions_for_action (rs); @@ -607,7 +635,7 @@ Editor::move_to_end () void Editor::build_region_boundary_cache () { - nframes_t pos = 0; + nframes64_t pos = 0; vector interesting_points; boost::shared_ptr r; TrackViewList tracks; @@ -650,8 +678,8 @@ Editor::build_region_boundary_cache () while (pos < session->current_end_frame() && !at_end) { - nframes_t rpos; - nframes_t lpos = max_frames; + nframes64_t rpos; + nframes64_t lpos = max_frames; for (vector::iterator p = interesting_points.begin(); p != interesting_points.end(); ++p) { @@ -699,7 +727,7 @@ Editor::build_region_boundary_cache () to sort later. */ - vector::iterator ri; + vector::iterator ri; for (ri = region_boundary_cache.begin(); ri != region_boundary_cache.end(); ++ri) { if (*ri == rpos) { @@ -721,20 +749,20 @@ Editor::build_region_boundary_cache () } boost::shared_ptr -Editor::find_next_region (nframes_t frame, RegionPoint point, int32_t dir, TrackViewList& tracks, TimeAxisView **ontrack) +Editor::find_next_region (nframes64_t frame, RegionPoint point, int32_t dir, TrackViewList& tracks, TimeAxisView **ontrack) { TrackViewList::iterator i; - nframes_t closest = max_frames; + nframes64_t closest = max_frames; boost::shared_ptr ret; - nframes_t rpos = 0; + nframes64_t rpos = 0; float track_speed; - nframes_t track_frame; + nframes64_t track_frame; RouteTimeAxisView *rtav; for (i = tracks.begin(); i != tracks.end(); ++i) { - nframes_t distance; + nframes64_t distance; boost::shared_ptr r; track_speed = 1.0f; @@ -866,7 +894,7 @@ void Editor::cursor_to_region_point (Cursor* cursor, RegionPoint point, int32_t dir) { boost::shared_ptr r; - nframes_t pos = cursor->current_frame; + nframes64_t pos = cursor->current_frame; if (!session) { return; @@ -945,7 +973,7 @@ Editor::cursor_to_previous_region_point (Cursor* cursor, RegionPoint point) void Editor::cursor_to_selection_start (Cursor *cursor) { - nframes_t pos = 0; + nframes64_t pos = 0; RegionSelection rs; get_regions_for_action (rs); @@ -977,7 +1005,7 @@ Editor::cursor_to_selection_start (Cursor *cursor) void Editor::cursor_to_selection_end (Cursor *cursor) { - nframes_t pos = 0; + nframes64_t pos = 0; RegionSelection rs; get_regions_for_action (rs); @@ -1071,7 +1099,7 @@ void Editor::selected_marker_to_region_point (RegionPoint point, int32_t dir) { boost::shared_ptr r; - nframes_t pos; + nframes64_t pos; Location* loc; bool ignored; @@ -1147,7 +1175,7 @@ Editor::selected_marker_to_previous_region_point (RegionPoint point) void Editor::selected_marker_to_selection_start () { - nframes_t pos = 0; + nframes64_t pos = 0; Location* loc; bool ignored; @@ -1186,7 +1214,7 @@ Editor::selected_marker_to_selection_start () void Editor::selected_marker_to_selection_end () { - nframes_t pos = 0; + nframes64_t pos = 0; Location* loc; bool ignored; @@ -1225,8 +1253,8 @@ Editor::selected_marker_to_selection_end () void Editor::scroll_playhead (bool forward) { - nframes_t pos = playhead_cursor->current_frame; - nframes_t delta = (nframes_t) floor (current_page_frames() / 0.8); + nframes64_t pos = playhead_cursor->current_frame; + nframes64_t delta = (nframes64_t) floor (current_page_frames() / 0.8); if (forward) { if (pos == max_frames) { @@ -1258,8 +1286,8 @@ Editor::scroll_playhead (bool forward) void Editor::playhead_backward () { - nframes_t pos; - nframes_t cnt; + nframes64_t pos; + nframes64_t cnt; float prefix; bool was_floating; @@ -1267,15 +1295,15 @@ Editor::playhead_backward () cnt = 1; } else { if (was_floating) { - cnt = (nframes_t) floor (prefix * session->frame_rate ()); + cnt = (nframes64_t) floor (prefix * session->frame_rate ()); } else { - cnt = (nframes_t) prefix; + cnt = (nframes64_t) prefix; } } pos = playhead_cursor->current_frame; - if ((nframes_t) pos < cnt) { + if ((nframes64_t) pos < cnt) { pos = 0; } else { pos -= cnt; @@ -1292,8 +1320,8 @@ Editor::playhead_backward () void Editor::playhead_forward () { - nframes_t pos; - nframes_t cnt; + nframes64_t pos; + nframes64_t cnt; bool was_floating; float prefix; @@ -1301,9 +1329,9 @@ Editor::playhead_forward () cnt = 1; } else { if (was_floating) { - cnt = (nframes_t) floor (prefix * session->frame_rate ()); + cnt = (nframes64_t) floor (prefix * session->frame_rate ()); } else { - cnt = (nframes_t) floor (prefix); + cnt = (nframes64_t) floor (prefix); } } @@ -1362,9 +1390,9 @@ Editor::edit_cursor_backward () cnt = 1; } else { if (was_floating) { - cnt = (nframes_t) floor (prefix * session->frame_rate ()); + cnt = (nframes64_t) floor (prefix * session->frame_rate ()); } else { - cnt = (nframes_t) prefix; + cnt = (nframes64_t) prefix; } } @@ -1384,8 +1412,8 @@ Editor::edit_cursor_backward () void Editor::edit_cursor_forward () { - //nframes_t pos; - nframes_t cnt; + //nframes64_t pos; + nframes64_t cnt; bool was_floating; float prefix; @@ -1393,9 +1421,9 @@ Editor::edit_cursor_forward () cnt = 1; } else { if (was_floating) { - cnt = (nframes_t) floor (prefix * session->frame_rate ()); + cnt = (nframes64_t) floor (prefix * session->frame_rate ()); } else { - cnt = (nframes_t) floor (prefix); + cnt = (nframes64_t) floor (prefix); } } @@ -1408,16 +1436,16 @@ Editor::goto_frame () { float prefix; bool was_floating; - nframes_t frame; + nframes64_t frame; if (get_prefix (prefix, was_floating)) { return; } if (was_floating) { - frame = (nframes_t) floor (prefix * session->frame_rate()); + frame = (nframes64_t) floor (prefix * session->frame_rate()); } else { - frame = (nframes_t) floor (prefix); + frame = (nframes64_t) floor (prefix); } session->request_locate (frame); @@ -1426,19 +1454,19 @@ Editor::goto_frame () void Editor::scroll_backward (float pages) { - nframes_t frame; - nframes_t one_page = (nframes_t) rint (canvas_width * frames_per_unit); + nframes64_t frame; + nframes64_t one_page = (nframes64_t) rint (canvas_width * frames_per_unit); bool was_floating; float prefix; - nframes_t cnt; + nframes64_t cnt; if (get_prefix (prefix, was_floating)) { - cnt = (nframes_t) floor (pages * one_page); + cnt = (nframes64_t) floor (pages * one_page); } else { if (was_floating) { - cnt = (nframes_t) floor (prefix * session->frame_rate()); + cnt = (nframes64_t) floor (prefix * session->frame_rate()); } else { - cnt = (nframes_t) floor (prefix * one_page); + cnt = (nframes64_t) floor (prefix * one_page); } } @@ -1454,19 +1482,19 @@ Editor::scroll_backward (float pages) void Editor::scroll_forward (float pages) { - nframes_t frame; - nframes_t one_page = (nframes_t) rint (canvas_width * frames_per_unit); + nframes64_t frame; + nframes64_t one_page = (nframes64_t) rint (canvas_width * frames_per_unit); bool was_floating; float prefix; - nframes_t cnt; + nframes64_t cnt; if (get_prefix (prefix, was_floating)) { - cnt = (nframes_t) floor (pages * one_page); + cnt = (nframes64_t) floor (pages * one_page); } else { if (was_floating) { - cnt = (nframes_t) floor (prefix * session->frame_rate()); + cnt = (nframes64_t) floor (prefix * session->frame_rate()); } else { - cnt = (nframes_t) floor (prefix * one_page); + cnt = (nframes64_t) floor (prefix * one_page); } } @@ -1581,7 +1609,7 @@ Editor::temporal_zoom (gdouble fpu) nfpu = fpu; - new_page_size = (nframes_t) floor (canvas_width * nfpu); + new_page_size = (nframes64_t) floor (canvas_width * nfpu); half_page_size = new_page_size / 2; switch (zoom_focus) { @@ -1681,12 +1709,14 @@ Editor::temporal_zoom (gdouble fpu) } void -Editor::temporal_zoom_region () +Editor::temporal_zoom_region (bool both_axes) { nframes64_t start = max_frames; nframes64_t end = 0; RegionSelection rs; + set tracks; + double top_y_position = DBL_MAX; get_regions_for_action (rs); @@ -1695,12 +1725,20 @@ Editor::temporal_zoom_region () } for (RegionSelection::iterator i = rs.begin(); i != rs.end(); ++i) { + if ((*i)->region()->position() < start) { start = (*i)->region()->position(); } + if ((*i)->region()->last_frame() + 1 > end) { end = (*i)->region()->last_frame() + 1; } + + tracks.insert (&((*i)->get_time_axis_view())); + + if ((*i)->get_time_axis_view().y_position < top_y_position) { + top_y_position = (*i)->get_time_axis_view().y_position; + } } /* now comes an "interesting" hack ... make sure we leave a little space @@ -1713,8 +1751,15 @@ Editor::temporal_zoom_region () gint mmwidth = gdk_screen_get_width_mm (screen); double pix_per_mm = (double) pixwidth/ (double) mmwidth; double one_centimeter_in_pixels = pix_per_mm * 10.0; - nframes_t extra_samples = unit_to_frame (one_centimeter_in_pixels); - + + if ((start == 0 && end == 0) || end < start) { + return; + } + + nframes64_t range = end - start; + double new_fpu = (double)range / (double)canvas_width; + nframes64_t extra_samples = (nframes64_t) floor (one_centimeter_in_pixels * new_fpu); + if (start > extra_samples) { start -= extra_samples; } else { @@ -1727,17 +1772,53 @@ Editor::temporal_zoom_region () end = max_frames; } + if (both_axes) { + /* save visual state with track states included, and prevent + set_frames_per_unit() from doing it again. + */ + undo_visual_stack.push_back (current_visual_state(true)); + no_save_visual = true; + } + temporal_zoom_by_frame (start, end, "zoom to region"); + + if (both_axes) { + uint32_t per_track_height = (uint32_t) floor ((canvas_height - 10.0) / tracks.size()); + + /* set visible track heights appropriately */ + + for (set::iterator t = tracks.begin(); t != tracks.end(); ++t) { + (*t)->set_height (per_track_height); + } + + /* hide irrelevant tracks */ + + no_route_list_redisplay = true; + + for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) { + if (find (tracks.begin(), tracks.end(), (*i)) == tracks.end()) { + hide_track_in_display (**i, true); + } + } + + no_route_list_redisplay = false; + redisplay_route_list (); + + vertical_adjustment.set_value (std::max (top_y_position - 5.0, 0.0)); + no_save_visual = false; + } + zoomed_to_region = true; + redo_visual_stack.push_back (current_visual_state()); } void -Editor::toggle_zoom_region () +Editor::toggle_zoom_region (bool both_axes) { if (zoomed_to_region) { swap_visual_state (); } else { - temporal_zoom_region (); + temporal_zoom_region (both_axes); } } @@ -1750,8 +1831,8 @@ Editor::temporal_zoom_selection () return; } - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; temporal_zoom_by_frame (start, end, "zoom to selection"); } @@ -1762,12 +1843,13 @@ Editor::temporal_zoom_session () ENSURE_GUI_THREAD (mem_fun (*this, &Editor::temporal_zoom_session)); if (session) { + last_canvas_frame = ((session->current_end_frame() - session->current_start_frame()) + (current_page_frames() / 24)); temporal_zoom_by_frame (session->current_start_frame(), session->current_end_frame(), "zoom to session"); } } void -Editor::temporal_zoom_by_frame (nframes_t start, nframes_t end, const string & op) +Editor::temporal_zoom_by_frame (nframes64_t start, nframes64_t end, const string & op) { if (!session) return; @@ -1775,32 +1857,23 @@ Editor::temporal_zoom_by_frame (nframes_t start, nframes_t end, const string & o return; } - nframes_t range = end - start; + nframes64_t range = end - start; double new_fpu = (double)range / (double)canvas_width; -// double p2 = 1.0; - -// while (p2 < new_fpu) { -// p2 *= 2.0; -// } -// new_fpu = p2; - nframes_t new_page = (nframes_t) floor (canvas_width * new_fpu); - nframes_t middle = (nframes_t) floor( (double)start + ((double)range / 2.0f )); - nframes_t new_leftmost = (nframes_t) floor( (double)middle - ((double)new_page/2.0f)); + nframes64_t new_page = (nframes64_t) floor (canvas_width * new_fpu); + nframes64_t middle = (nframes64_t) floor( (double)start + ((double)range / 2.0f )); + nframes64_t new_leftmost = (nframes64_t) floor( (double)middle - ((double)new_page/2.0f)); - if (new_leftmost > middle) new_leftmost = 0; - -// begin_reversible_command (op); -// session->add_undo (bind (mem_fun(*this, &Editor::reposition_and_zoom), leftmost_frame, frames_per_unit)); -// session->add_redo (bind (mem_fun(*this, &Editor::reposition_and_zoom), new_leftmost, new_fpu)); -// commit_reversible_command (); + if (new_leftmost > middle) { + new_leftmost = 0; + } reposition_and_zoom (new_leftmost, new_fpu); } void -Editor::temporal_zoom_to_frame (bool coarser, nframes_t frame) +Editor::temporal_zoom_to_frame (bool coarser, nframes64_t frame) { if (!session) return; @@ -1819,7 +1892,7 @@ Editor::temporal_zoom_to_frame (bool coarser, nframes_t frame) if (new_fpu == frames_per_unit) return; - nframes_t new_leftmost = frame - (nframes_t)range_before; + nframes64_t new_leftmost = frame - (nframes64_t)range_before; if (new_leftmost > frame) new_leftmost = 0; @@ -1831,6 +1904,46 @@ Editor::temporal_zoom_to_frame (bool coarser, nframes_t frame) reposition_and_zoom (new_leftmost, new_fpu); } + +bool +Editor::choose_new_marker_name(string &name) { + + if (!Config->get_name_new_markers()) { + /* don't prompt user for a new name */ + return true; + } + + ArdourPrompter dialog (true); + + dialog.set_prompt (_("New Name:")); + + WindowTitle title(Glib::get_application_name()); + title += _("Name New Location Marker"); + + dialog.set_title(title.get_string()); + + dialog.set_name ("MarkNameWindow"); + dialog.set_size_request (250, -1); + dialog.set_position (Gtk::WIN_POS_MOUSE); + + dialog.add_button (Stock::OK, RESPONSE_ACCEPT); + dialog.set_initial_text (name); + + dialog.show (); + + switch (dialog.run ()) { + case RESPONSE_ACCEPT: + break; + default: + return false; + } + + dialog.get_result(name); + return true; + +} + + void Editor::add_location_from_selection () { @@ -1844,8 +1957,8 @@ Editor::add_location_from_selection () return; } - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; session->locations()->next_available_name(rangename,"selection"); Location *location = new Location (start, end, rangename, Location::IsRangeMarker); @@ -1866,6 +1979,9 @@ Editor::add_location_mark (nframes64_t where) select_new_marker = true; session->locations()->next_available_name(markername,"mark"); + if (!choose_new_marker_name(markername)) { + return; + } Location *location = new Location (where, where, markername, Location::IsMark); session->begin_reversible_command (_("add marker")); XMLNode &before = session->locations()->get_state(); @@ -1994,7 +2110,7 @@ Editor::jump_backward_to_mark () void Editor::set_mark () { - nframes_t pos; + nframes64_t pos; float prefix; bool was_floating; string markername; @@ -2003,13 +2119,16 @@ Editor::set_mark () pos = session->audible_frame (); } else { if (was_floating) { - pos = (nframes_t) floor (prefix * session->frame_rate ()); + pos = (nframes64_t) floor (prefix * session->frame_rate ()); } else { - pos = (nframes_t) floor (prefix); + pos = (nframes64_t) floor (prefix); } } session->locations()->next_available_name(markername,"mark"); + if (!choose_new_marker_name(markername)) { + return; + } session->locations()->add (new Location (pos, 0, markername, Location::IsMark), true); } @@ -2089,7 +2208,7 @@ Editor::insert_region_list_drag (boost::shared_ptr region, int x, int y) double wx, wy; double cx, cy; TimeAxisView *tv; - nframes_t where; + nframes64_t where; RouteTimeAxisView *rtv = 0; boost::shared_ptr playlist; @@ -2545,6 +2664,11 @@ Editor::build_interthread_progress_window () interthread_progress_bar.set_orientation (Gtk::PROGRESS_LEFT_TO_RIGHT); + interthread_progress_window->set_border_width (12); + interthread_progress_window->get_vbox()->set_spacing (6); + + interthread_progress_label.set_alignment (0.5, 0.5); + interthread_progress_window->get_vbox()->pack_start (interthread_progress_label, false, false); interthread_progress_window->get_vbox()->pack_start (interthread_progress_bar,false, false); @@ -2577,17 +2701,17 @@ Editor::region_from_selection () return; } - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; - nframes_t selection_cnt = end - start + 1; + nframes64_t selection_cnt = end - start + 1; for (TrackSelection::iterator i = selection->tracks.begin(); i != selection->tracks.end(); ++i) { boost::shared_ptr current; boost::shared_ptr current_r; boost::shared_ptr pl; - nframes_t internal_start; + nframes64_t internal_start; string new_name; if ((pl = (*i)->playlist()) == 0) { @@ -2615,8 +2739,8 @@ Editor::create_region_from_selection (vector >& new_re return; } - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; sort_track_selection (); @@ -2625,7 +2749,7 @@ Editor::create_region_from_selection (vector >& new_re boost::shared_ptr current; boost::shared_ptr current_r; boost::shared_ptr playlist; - nframes_t internal_start; + nframes64_t internal_start; string new_name; if ((playlist = (*i)->playlist()) == 0) { @@ -2762,7 +2886,7 @@ Editor::separate_regions_between (const TimeSelection& ts) sigc::connection c = rtv->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); latest_regionviews.clear (); - playlist->partition ((nframes_t)((*t).start * speed), (nframes_t)((*t).end * speed), true); + playlist->partition ((nframes64_t)((*t).start * speed), (nframes64_t)((*t).end * speed), true); c.disconnect (); @@ -2879,7 +3003,7 @@ Editor::crop_region_to_selection () } void -Editor::crop_region_to (nframes_t start, nframes_t end) +Editor::crop_region_to (nframes64_t start, nframes64_t end) { vector > playlists; boost::shared_ptr playlist; @@ -2913,9 +3037,9 @@ Editor::crop_region_to (nframes_t start, nframes_t end) return; } - nframes_t the_start; - nframes_t the_end; - nframes_t cnt; + nframes64_t the_start; + nframes64_t the_end; + nframes64_t cnt; begin_reversible_command (_("trim to selection")); @@ -2933,7 +3057,7 @@ Editor::crop_region_to (nframes_t start, nframes_t end) if the selection extends beyond the region */ - the_start = max (the_start, region->position()); + the_start = max (the_start, (nframes64_t) region->position()); if (max_frames - the_start < region->length()) { the_end = the_start + region->length() - 1; } else { @@ -2954,7 +3078,7 @@ Editor::crop_region_to (nframes_t start, nframes_t end) void Editor::region_fill_track () { - nframes_t end; + nframes64_t end; RegionSelection rs; get_regions_for_action (rs); @@ -3016,8 +3140,8 @@ Editor::region_fill_selection () TreeModel::iterator i = region_list_display.get_selection()->get_selected(); boost::shared_ptr region = (*i)[region_list_columns.region]; - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; boost::shared_ptr playlist; @@ -3025,7 +3149,7 @@ Editor::region_fill_selection () return; } - nframes_t selection_length = end - start; + nframes64_t selection_length = end - start; float times = (float)selection_length / region->length(); begin_reversible_command (_("fill selection")); @@ -3086,16 +3210,22 @@ Editor::set_sync_point (nframes64_t where, const RegionSelection& rs) void Editor::remove_region_sync () { - begin_reversible_command (_("remove sync")); + RegionSelection rs; - for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { - boost::shared_ptr r = (*i)->region(); - XMLNode &before = r->playlist()->get_state(); - r->clear_sync_position (); - XMLNode &after = r->playlist()->get_state(); - session->add_command(new MementoCommand(*(r->playlist()), &before, &after)); + get_regions_for_action (rs); + + if (rs.empty()) { + return; } + begin_reversible_command (_("remove sync")); + for (RegionSelection::iterator i = rs.begin(); i != rs.end(); ++i) { + + XMLNode &before = (*i)->region()->playlist()->get_state(); + (*i)->region()->clear_sync_position (); + XMLNode &after = (*i)->region()->playlist()->get_state(); + session->add_command(new MementoCommand(*((*i)->region()->playlist()), &before, &after)); + } commit_reversible_command (); } @@ -3158,18 +3288,19 @@ struct RegionSortByTime { }; void -Editor::align_selection_relative (RegionPoint point, nframes_t position, const RegionSelection& rs) +Editor::align_selection_relative (RegionPoint point, nframes64_t position, const RegionSelection& rs) { if (rs.empty()) { return; } - nframes_t distance = 0; - nframes_t pos = 0; + nframes64_t distance; + nframes64_t pos = 0; int dir = 0; list sorted; rs.by_position (sorted); + boost::shared_ptr r ((*sorted.begin())->region()); switch (point) { @@ -3246,7 +3377,7 @@ Editor::align_selection_relative (RegionPoint point, nframes_t position, const R } void -Editor::align_selection (RegionPoint point, nframes_t position, const RegionSelection& rs) +Editor::align_selection (RegionPoint point, nframes64_t position, const RegionSelection& rs) { if (rs.empty()) { return; @@ -3262,7 +3393,7 @@ Editor::align_selection (RegionPoint point, nframes_t position, const RegionSele } void -Editor::align_region (boost::shared_ptr region, RegionPoint point, nframes_t position) +Editor::align_region (boost::shared_ptr region, RegionPoint point, nframes64_t position) { begin_reversible_command (_("align region")); align_region_internal (region, point, position); @@ -3270,7 +3401,7 @@ Editor::align_region (boost::shared_ptr region, RegionPoint point, nfram } void -Editor::align_region_internal (boost::shared_ptr region, RegionPoint point, nframes_t position) +Editor::align_region_internal (boost::shared_ptr region, RegionPoint point, nframes64_t position) { XMLNode &before = region->playlist()->get_state(); @@ -3346,8 +3477,8 @@ Editor::trim_region_to_location (const Location& loc, const char* str) } float speed = 1.0; - nframes_t start; - nframes_t end; + nframes64_t start; + nframes64_t end; if (atav->get_diskstream() != 0) { speed = atav->get_diskstream()->speed(); @@ -3537,7 +3668,7 @@ Editor::freeze_route () } void -Editor::bounce_range_selection () +Editor::bounce_range_selection (bool replace) { if (selection->time.empty()) { return; @@ -3545,9 +3676,9 @@ Editor::bounce_range_selection () TrackSelection views = selection->tracks; - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; - nframes_t cnt = end - start + 1; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; + nframes64_t cnt = end - start + 1; begin_reversible_command (_("bounce range")); @@ -3571,9 +3702,17 @@ Editor::bounce_range_selection () itt.cancel = false; itt.progress = false; - XMLNode &before = playlist->get_state(); - rtv->track()->bounce_range (start, cnt, itt); - XMLNode &after = playlist->get_state(); + XMLNode &before = playlist->get_state(); + boost::shared_ptr r = rtv->track()->bounce_range (start, start+cnt, itt); + + if (replace) { + list ranges; + ranges.push_back (AudioRange (start, start+cnt, 0)); + playlist->cut (ranges); // discard result + playlist->add_region (r, start); + } + + XMLNode &after = playlist->get_state(); session->add_command (new MementoCommand (*playlist, &before, &after)); } @@ -3642,6 +3781,19 @@ Editor::cut_copy (CutCopyOp op) opname = _("clear"); break; } + + /* if we're deleting something, and the mouse is still pressed, + the thing we started a drag for will be gone when we release + the mouse button(s). avoid this. see part 2 at the end of + this function. + */ + + if (op == Cut || op == Clear) { + if (drag_info.item) { + drag_info.item->ungrab (0); + drag_info.item = 0; + } + } cut_buffer->clear (); @@ -3656,6 +3808,8 @@ Editor::cut_copy (CutCopyOp op) Glib::signal_idle().connect (bind (mem_fun(*this, &Editor::really_remove_marker), loc)); } + break_drag (); + return; } @@ -3720,6 +3874,11 @@ Editor::cut_copy (CutCopyOp op) default: break; } + + + if (op == Cut || op == Clear) { + break_drag (); + } } /** Cut, copy or clear selected automation points. @@ -3769,7 +3928,7 @@ Editor::cut_copy_regions (CutCopyOp op, RegionSelection& rs) vector pmap; - nframes_t first_position = max_frames; + nframes64_t first_position = max_frames; set freezelist; pair::iterator,bool> insert_result; @@ -3780,7 +3939,7 @@ Editor::cut_copy_regions (CutCopyOp op, RegionSelection& rs) for (RegionSelection::iterator x = rs.begin(); x != rs.end(); ++x) { - first_position = min ((*x)->region()->position(), first_position); + first_position = min ((nframes64_t) (*x)->region()->position(), first_position); if (op == Cut || op == Clear) { boost::shared_ptr pl = (*x)->region()->playlist(); @@ -3934,7 +4093,7 @@ Editor::mouse_paste () } void -Editor::paste_internal (nframes_t position, float times) +Editor::paste_internal (nframes64_t position, float times) { bool commit = false; @@ -4152,9 +4311,9 @@ void Editor::nudge_track (bool use_edit, bool forwards) { boost::shared_ptr playlist; - nframes_t distance; - nframes_t next_distance; - nframes_t start; + nframes64_t distance; + nframes64_t next_distance; + nframes64_t start; if (use_edit) { start = get_preferred_edit_position(); @@ -4442,7 +4601,7 @@ Editor::external_edit_region () } void -Editor::brush (nframes_t pos) +Editor::brush (nframes64_t pos) { RegionSelection sel; RegionSelection rs; @@ -4586,7 +4745,7 @@ Editor::set_fade_length (bool in) } nframes64_t pos = get_preferred_edit_position(); - nframes_t len; + nframes64_t len; char* cmd; if (pos > rv->region()->last_frame() || pos < rv->region()->first_frame()) { @@ -5029,8 +5188,8 @@ Editor::set_loop_from_selection (bool play) return; } - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; set_loop_range (start, end, _("set loop range from selection")); @@ -5100,8 +5259,8 @@ Editor::set_punch_from_selection () return; } - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; set_punch_range (start, end, _("set punch range from selection")); } @@ -5517,14 +5676,13 @@ Editor::tab_to_transient (bool forward) } } } - void Editor::playhead_forward_to_grid () { if (!session) return; nframes64_t pos = playhead_cursor->current_frame; - if (pos < max_frames) { - pos++; + if (pos < max_frames - 1) { + pos += 2; snap_to_internal (pos, 1, false); session->request_locate (pos); } @@ -5536,15 +5694,15 @@ Editor::playhead_backward_to_grid () { if (!session) return; nframes64_t pos = playhead_cursor->current_frame; - if (pos > 1) { - pos--; + if (pos > 2) { + pos -= 2; snap_to_internal (pos, -1, false); session->request_locate (pos); } } void -Editor::set_track_height (TimeAxisView::TrackHeight h) +Editor::set_track_height (uint32_t h) { TrackSelection& ts (selection->tracks); @@ -5560,32 +5718,32 @@ Editor::set_track_height (TimeAxisView::TrackHeight h) void Editor::set_track_height_largest () { - set_track_height (TimeAxisView::Largest); + set_track_height (TimeAxisView::hLargest); } void Editor::set_track_height_large () { - set_track_height (TimeAxisView::Large); + set_track_height (TimeAxisView::hLarge); } void Editor::set_track_height_larger () { - set_track_height (TimeAxisView::Larger); + set_track_height (TimeAxisView::hLarger); } void Editor::set_track_height_normal () { - set_track_height (TimeAxisView::Normal); + set_track_height (TimeAxisView::hNormal); } void Editor::set_track_height_smaller () { - set_track_height (TimeAxisView::Smaller); + set_track_height (TimeAxisView::hSmaller); } void Editor::set_track_height_small () { - set_track_height (TimeAxisView::Small); + set_track_height (TimeAxisView::hSmall); } void @@ -5725,7 +5883,8 @@ Editor::do_insert_time () RadioButton move_button (group, _("Move")); RadioButton split_button (group, _("Split & Later Section Moves")); Label intersect_option_label (_("Intersected regions should:")); - ToggleButton glue_button (_("Move Glued Regions")); + CheckButton glue_button (_("Move Glued Regions")); + CheckButton marker_button (_("Move Markers")); AudioClock clock ("insertTimeClock", true, X_("InsertTimeClock"), true, true, true); HBox clock_box; @@ -5739,6 +5898,7 @@ Editor::do_insert_time () option_box.pack_start (intersect_option_label, false, false); option_box.pack_start (button_box, false, false); option_box.pack_start (glue_button, false, false); + option_box.pack_start (marker_button, false, false); button_box.pack_start (leave_button, false, false); button_box.pack_start (move_button, false, false); @@ -5757,6 +5917,7 @@ Editor::do_insert_time () glue_button.show (); clock.show_all(); clock_box.show (); + marker_button.show (); d.add_button (Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL); d.add_button (Gtk::Stock::OK, Gtk::RESPONSE_OK); @@ -5768,7 +5929,7 @@ Editor::do_insert_time () return; } - nframes_t distance = clock.current_duration (pos); + nframes64_t distance = clock.current_duration (pos); if (distance == 0) { return; @@ -5784,11 +5945,12 @@ Editor::do_insert_time () opt = SplitIntersected; } - insert_time (pos, distance, opt, glue_button.get_active()); + insert_time (pos, distance, opt, glue_button.get_active(), marker_button.get_active()); } - + void -Editor::insert_time (nframes64_t pos, nframes64_t frames, InsertTimeOption opt, bool ignore_music_glue) +Editor::insert_time (nframes64_t pos, nframes64_t frames, InsertTimeOption opt, + bool ignore_music_glue, bool markers_too) { bool commit = false; @@ -5819,7 +5981,130 @@ Editor::insert_time (nframes64_t pos, nframes64_t frames, InsertTimeOption opt, commit = true; } + if (markers_too) { + bool moved = false; + XMLNode& before (session->locations()->get_state()); + Locations::LocationList copy (session->locations()->list()); + + for (Locations::LocationList::iterator i = copy.begin(); i != copy.end(); ++i) { + + Locations::LocationList::const_iterator tmp; + + if ((*i)->start() >= pos) { + (*i)->set_start ((*i)->start() + frames); + if (!(*i)->is_mark()) { + (*i)->set_end ((*i)->end() + frames); + } + moved = true; + } + } + + if (moved) { + XMLNode& after (session->locations()->get_state()); + session->add_command (new MementoCommand(*session->locations(), &before, &after)); + } + } + if (commit) { commit_reversible_command (); } } + +void +Editor::fit_tracks () +{ + if (selection->tracks.empty()) { + return; + } + + uint32_t child_heights = 0; + + for (TrackSelection::iterator t = selection->tracks.begin(); t != selection->tracks.end(); ++t) { + + if (!(*t)->marked_for_display()) { + continue; + } + + child_heights += ((*t)->effective_height - (*t)->current_height()); + } + + uint32_t h = (uint32_t) floor ((canvas_height - child_heights)/selection->tracks.size()); + double first_y_pos = DBL_MAX; + + undo_visual_stack.push_back (current_visual_state()); + + for (TrackSelection::iterator t = selection->tracks.begin(); t != selection->tracks.end(); ++t) { + (*t)->set_height (h); + first_y_pos = std::min ((*t)->y_position, first_y_pos); + } + + + vertical_adjustment.set_value (first_y_pos); + + redo_visual_stack.push_back (current_visual_state()); +} + +void +Editor::save_visual_state (uint32_t n) +{ + while (visual_states.size() <= n) { + visual_states.push_back (0); + } + + if (visual_states[n] != 0) { + delete visual_states[n]; + } + + visual_states[n] = current_visual_state (true); + gdk_beep (); +} + +void +Editor::goto_visual_state (uint32_t n) +{ + if (visual_states.size() <= n) { + return; + } + + if (visual_states[n] == 0) { + return; + } + + use_visual_state (*visual_states[n]); +} + +void +Editor::start_visual_state_op (uint32_t n) +{ + cerr << "Start\n"; + if (visual_state_op_connection.empty()) { + cerr << "\tqueue\n"; + visual_state_op_connection = Glib::signal_timeout().connect (bind (mem_fun (*this, &Editor::end_visual_state_op), n), 1000); + } +} + +void +Editor::cancel_visual_state_op (uint32_t n) +{ + cerr << "Cancel\n"; + if (!visual_state_op_connection.empty()) { + cerr << "\tgoto\n"; + visual_state_op_connection.disconnect(); + goto_visual_state (n); + } +} + +bool +Editor::end_visual_state_op (uint32_t n) +{ + visual_state_op_connection.disconnect(); + save_visual_state (n); + + PopUp* pup = new PopUp (WIN_POS_MOUSE, 1000, true); + char buf[32]; + snprintf (buf, sizeof (buf), _("Saved view %u"), n+1); + pup->set_text (buf); + pup->touch(); + + return false; // do not call again +} diff --git a/gtk2_ardour/editor_region_list.cc b/gtk2_ardour/editor_region_list.cc index c9067cacfe..54bc71e074 100644 --- a/gtk2_ardour/editor_region_list.cc +++ b/gtk2_ardour/editor_region_list.cc @@ -134,6 +134,18 @@ Editor::add_region_to_region_display (boost::shared_ptr region) } else if (region->whole_file()) { + TreeModel::iterator i; + TreeModel::Children rows = region_list_model->children(); + + for (i = rows.begin(); i != rows.end(); ++i) { + + boost::shared_ptr rr = (*i)[region_list_columns.region]; + + if (region->region_list_equivalent (rr)) { + return; + } + } + row = *(region_list_model->append()); if (missing_source) { c.set_rgb(65535,0,0); // FIXME: error color from style @@ -203,6 +215,18 @@ Editor::add_region_to_region_display (boost::shared_ptr region) break; } } + + TreeModel::iterator ii; + TreeModel::Children subrows = (*i).children(); + + for (ii = subrows.begin(); ii != subrows.end(); ++ii) { + + boost::shared_ptr rrr = (*ii)[region_list_columns.region]; + + if (region->region_list_equivalent (rrr)) { + return; + } + } } if (!found_parent) { @@ -307,6 +331,10 @@ Editor::insert_into_tmp_regionlist(boost::shared_ptr region) void Editor::redisplay_regions () { + if (no_region_list_redisplay) { + return; + } + if (session) { region_list_display.set_model (Glib::RefPtr(0)); diff --git a/gtk2_ardour/editor_route_list.cc b/gtk2_ardour/editor_route_list.cc index 65202cb0db..c12a30ca73 100644 --- a/gtk2_ardour/editor_route_list.cc +++ b/gtk2_ardour/editor_route_list.cc @@ -148,10 +148,17 @@ Editor::handle_gui_changes (const string & what, void *src) ENSURE_GUI_THREAD(bind (mem_fun(*this, &Editor::handle_gui_changes), what, src)); if (what == "track_height") { + /* make tracks change height while it happens, instead + of on first-idle + */ + track_canvas->update_now (); redisplay_route_list (); } -} + if (what == "visible_tracks") { + redisplay_route_list (); + } +} void Editor::remove_route (TimeAxisView *tv) @@ -162,6 +169,10 @@ Editor::remove_route (TimeAxisView *tv) TreeModel::Children rows = route_display_model->children(); TreeModel::Children::iterator ri; + if (tv == entered_track) { + entered_track = 0; + } + /* Decrement old order keys for tracks `above' the one that is being removed */ for (ri = rows.begin(); ri != rows.end(); ++ri) { TimeAxisView* v = (*ri)[route_display_columns.tv]; @@ -209,11 +220,27 @@ Editor::route_name_changed (TimeAxisView *tv) break; } } +} + +void +Editor::update_route_visibility () +{ + TreeModel::Children rows = route_display_model->children(); + TreeModel::Children::iterator i; + + no_route_list_redisplay = true; + for (i = rows.begin(); i != rows.end(); ++i) { + TimeAxisView *tv = (*i)[route_display_columns.tv]; + (*i)[route_display_columns.visible] = tv->marked_for_display (); + } + + no_route_list_redisplay = false; + redisplay_route_list (); } void -Editor::hide_track_in_display (TimeAxisView& tv) +Editor::hide_track_in_display (TimeAxisView& tv, bool temponly) { TreeModel::Children rows = route_display_model->children(); TreeModel::Children::iterator i; @@ -221,6 +248,9 @@ Editor::hide_track_in_display (TimeAxisView& tv) for (i = rows.begin(); i != rows.end(); ++i) { if ((*i)[route_display_columns.tv] == &tv) { (*i)[route_display_columns.visible] = false; + // if (temponly) { + tv.set_marked_for_display (false); + // } break; } } @@ -598,7 +628,6 @@ Editor::route_list_delete (const Gtk::TreeModel::Path& path) redisplay_route_list (); } - void Editor::route_list_display_drag_data_received (const RefPtr& context, int x, int y, @@ -616,7 +645,6 @@ Editor::route_list_display_drag_data_received (const RefPtr& c context->drag_finish (true, false, time); } - RouteTimeAxisView* Editor::get_route_view_by_id (PBD::ID& id) { diff --git a/gtk2_ardour/editor_rulers.cc b/gtk2_ardour/editor_rulers.cc index 02e8f70727..dc62f669f8 100644 --- a/gtk2_ardour/editor_rulers.cc +++ b/gtk2_ardour/editor_rulers.cc @@ -95,7 +95,7 @@ Editor::initialize_rulers () bool Editor::ruler_scroll (GdkEventScroll* event) { - nframes_t xdelta; + nframes64_t xdelta; int direction = event->direction; bool handled = false; @@ -168,7 +168,7 @@ Editor::ruler_button_press (GdkEventButton* ev) /* need to use the correct x,y, the event lies */ time_canvas_event_box.get_window()->get_pointer (x, y, state); - nframes_t where = leftmost_frame + pixel_to_frame (x); + nframes64_t where = leftmost_frame + pixel_to_frame (x); switch (ev->button) { case 1: @@ -212,7 +212,7 @@ Editor::ruler_button_release (GdkEventButton* ev) stop_canvas_autoscroll(); - nframes_t where = leftmost_frame + pixel_to_frame (x); + nframes64_t where = leftmost_frame + pixel_to_frame (x); switch (ev->button) { case 1: @@ -280,10 +280,10 @@ Editor::ruler_mouse_motion (GdkEventMotion* ev) track_canvas->c2w (x, y, wcx, wcy); track_canvas->w2c (wcx, wcy, cx, cy); - nframes_t where = leftmost_frame + pixel_to_frame (x); + nframes64_t where = leftmost_frame + pixel_to_frame (x); /// ripped from maybe_autoscroll, and adapted to work here - nframes_t rightmost_frame = leftmost_frame + current_page_frames (); + nframes64_t rightmost_frame = leftmost_frame + current_page_frames (); jack_nframes_t frame = pixel_to_frame (cx); @@ -336,7 +336,7 @@ Editor::ruler_mouse_motion (GdkEventMotion* ev) void -Editor::popup_ruler_menu (nframes_t where, ItemType t) +Editor::popup_ruler_menu (nframes64_t where, ItemType t) { using namespace Menu_Helpers; @@ -750,8 +750,8 @@ Editor::update_ruler_visibility () time_canvas_event_box.show_all(); time_button_frame.show_all(); - compute_current_bbt_points (leftmost_frame, leftmost_frame + (nframes_t)(edit_packer.get_width() * frames_per_unit)); - compute_bbt_ruler_scale (leftmost_frame, leftmost_frame + (nframes_t)(edit_packer.get_width() * frames_per_unit)); + compute_current_bbt_points (leftmost_frame, leftmost_frame + (nframes64_t)(edit_packer.get_width() * frames_per_unit)); + compute_bbt_ruler_scale (leftmost_frame, leftmost_frame + (nframes64_t)(edit_packer.get_width() * frames_per_unit)); redisplay_tempo (false); } @@ -765,7 +765,7 @@ Editor::update_just_smpte () return; } - nframes_t rightmost_frame = leftmost_frame + current_page_frames(); + nframes64_t rightmost_frame = leftmost_frame + current_page_frames(); if (ruler_timecode_action->get_active()) { gtk_custom_ruler_set_range (GTK_CUSTOM_RULER(_smpte_ruler), leftmost_frame, rightmost_frame, @@ -792,7 +792,7 @@ Editor::compute_fixed_ruler_scale () void Editor::update_fixed_rulers () { - nframes_t rightmost_frame; + nframes64_t rightmost_frame; if (session == 0) { return; @@ -868,9 +868,9 @@ Editor::_metric_get_minsec (GtkCustomRulerMark **marks, gdouble lower, gdouble u void Editor::set_smpte_ruler_scale (gdouble lower, gdouble upper) { - nframes_t range; - nframes_t spacer; - nframes_t fr; + nframes64_t range; + nframes64_t spacer; + nframes64_t fr; if (session == 0) { return; @@ -878,13 +878,13 @@ Editor::set_smpte_ruler_scale (gdouble lower, gdouble upper) fr = session->frame_rate(); - if (lower > (spacer = (nframes_t)(128 * Editor::get_current_zoom ()))) { + if (lower > (spacer = (nframes64_t)(128 * Editor::get_current_zoom ()))) { lower = lower - spacer; } else { lower = 0; } upper = upper + spacer; - range = (nframes_t) floor (upper - lower); + range = (nframes64_t) floor (upper - lower); if (range < (2 * session->frames_per_smpte_frame())) { /* 0 - 2 frames */ smpte_ruler_scale = smpte_show_bits; @@ -893,19 +893,19 @@ Editor::set_smpte_ruler_scale (gdouble lower, gdouble upper) } else if (range <= (fr / 4)) { /* 2 frames - 0.250 second */ smpte_ruler_scale = smpte_show_frames; smpte_mark_modulo = 1; - smpte_nmarks = 2 + (range / (nframes_t)session->frames_per_smpte_frame()); + smpte_nmarks = 2 + (range / (nframes64_t)session->frames_per_smpte_frame()); } else if (range <= (fr / 2)) { /* 0.25-0.5 second */ smpte_ruler_scale = smpte_show_frames; smpte_mark_modulo = 2; - smpte_nmarks = 2 + (range / (nframes_t)session->frames_per_smpte_frame()); + smpte_nmarks = 2 + (range / (nframes64_t)session->frames_per_smpte_frame()); } else if (range <= fr) { /* 0.5-1 second */ smpte_ruler_scale = smpte_show_frames; smpte_mark_modulo = 5; - smpte_nmarks = 2 + (range / (nframes_t)session->frames_per_smpte_frame()); + smpte_nmarks = 2 + (range / (nframes64_t)session->frames_per_smpte_frame()); } else if (range <= 2 * fr) { /* 1-2 seconds */ smpte_ruler_scale = smpte_show_frames; smpte_mark_modulo = 10; - smpte_nmarks = 2 + (range / (nframes_t)session->frames_per_smpte_frame()); + smpte_nmarks = 2 + (range / (nframes64_t)session->frames_per_smpte_frame()); } else if (range <= 8 * fr) { /* 2-8 seconds */ smpte_ruler_scale = smpte_show_seconds; smpte_mark_modulo = 1; @@ -956,7 +956,7 @@ Editor::set_smpte_ruler_scale (gdouble lower, gdouble upper) smpte_nmarks = 2 + 24; } else { - /* not possible if nframes_t is a 32 bit quantity */ + /* not possible if nframes64_t is a 32 bit quantity */ smpte_ruler_scale = smpte_show_hours; smpte_mark_modulo = 4; @@ -969,7 +969,7 @@ gint Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upper, gint maxchars) { nframes_t pos; - nframes_t spacer; + nframes64_t spacer; SMPTE::Time smpte; gchar buf[16]; gint n; @@ -978,7 +978,7 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp return 0; } - if (lower > (spacer = (nframes_t)(128 * Editor::get_current_zoom ()))) { + if (lower > (spacer = (nframes64_t)(128 * Editor::get_current_zoom ()))) { lower = lower - spacer; } else { lower = 0; @@ -1124,7 +1124,7 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp void -Editor::compute_bbt_ruler_scale (nframes_t lower, nframes_t upper) +Editor::compute_bbt_ruler_scale (nframes64_t lower, nframes64_t upper) { if (session == 0) { return; @@ -1219,15 +1219,15 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper char buf[64]; gint n = 0; - nframes_t pos; + nframes64_t pos; BBT_Time next_beat; - nframes_t next_beat_pos; + nframes64_t next_beat_pos; uint32_t beats = 0; uint32_t tick = 0; uint32_t skip; uint32_t t; - nframes_t frame_skip; + nframes64_t frame_skip; double frame_skip_error; double bbt_position_of_helper; double accumulated_error; @@ -1330,7 +1330,7 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper next_beat_pos = session->tempo_map().frame_time(next_beat); - frame_skip = (nframes_t) floor (frame_skip_error = (session->frame_rate() * 60) / (bbt_beat_subdivision * (*i).tempo->beats_per_minute())); + frame_skip = (nframes64_t) floor (frame_skip_error = (session->frame_rate() * 60) / (bbt_beat_subdivision * (*i).tempo->beats_per_minute())); frame_skip_error -= frame_skip; skip = (uint32_t) (Meter::ticks_per_beat / bbt_beat_subdivision); @@ -1348,7 +1348,7 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper snprintf (buf, sizeof(buf), " "); (*marks)[n].label = g_strdup (buf); - /* Error compensation for float to nframes_t*/ + /* Error compensation for float to nframes64_t*/ accumulated_error += frame_skip_error; if (accumulated_error > 1) { pos += 1; @@ -1422,7 +1422,7 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper next_beat_pos = session->tempo_map().frame_time(next_beat); - frame_skip = (nframes_t) floor (frame_skip_error = (session->frame_rate() * 60) / (bbt_beat_subdivision * (*i).tempo->beats_per_minute())); + frame_skip = (nframes64_t) floor (frame_skip_error = (session->frame_rate() * 60) / (bbt_beat_subdivision * (*i).tempo->beats_per_minute())); frame_skip_error -= frame_skip; skip = (uint32_t) (Meter::ticks_per_beat / bbt_beat_subdivision); @@ -1445,7 +1445,7 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper (*marks)[n].label = g_strdup (buf); - /* Error compensation for float to nframes_t*/ + /* Error compensation for float to nframes64_t*/ accumulated_error += frame_skip_error; if (accumulated_error > 1) { pos += 1; @@ -1519,7 +1519,7 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper next_beat_pos = session->tempo_map().frame_time(next_beat); - frame_skip = (nframes_t) floor (frame_skip_error = (session->frame_rate() * 60) / (bbt_beat_subdivision * (*i).tempo->beats_per_minute())); + frame_skip = (nframes64_t) floor (frame_skip_error = (session->frame_rate() * 60) / (bbt_beat_subdivision * (*i).tempo->beats_per_minute())); frame_skip_error -= frame_skip; skip = (uint32_t) (Meter::ticks_per_beat / bbt_beat_subdivision); @@ -1542,7 +1542,7 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper (*marks)[n].label = g_strdup (buf); - /* Error compensation for float to nframes_t*/ + /* Error compensation for float to nframes64_t*/ accumulated_error += frame_skip_error; if (accumulated_error > 1) { pos += 1; @@ -1683,10 +1683,10 @@ Editor::metric_get_bbt (GtkCustomRulerMark **marks, gdouble lower, gdouble upper gint Editor::metric_get_frames (GtkCustomRulerMark **marks, gdouble lower, gdouble upper, gint maxchars) { - nframes_t mark_interval; - nframes_t pos; - nframes_t ilower = (nframes_t) floor (lower); - nframes_t iupper = (nframes_t) floor (upper); + nframes64_t mark_interval; + nframes64_t pos; + nframes64_t ilower = (nframes64_t) floor (lower); + nframes64_t iupper = (nframes64_t) floor (upper); gchar buf[16]; gint nmarks; gint n; @@ -1714,15 +1714,15 @@ Editor::metric_get_frames (GtkCustomRulerMark **marks, gdouble lower, gdouble up } static void -sample_to_clock_parts ( nframes_t sample, - nframes_t sample_rate, +sample_to_clock_parts ( nframes64_t sample, + nframes64_t sample_rate, long *hrs_p, long *mins_p, long *secs_p, long *millisecs_p) { - nframes_t left; + nframes64_t left; long hrs; long mins; long secs; @@ -1748,9 +1748,9 @@ sample_to_clock_parts ( nframes_t sample, void Editor::set_minsec_ruler_scale (gdouble lower, gdouble upper) { - nframes_t range; - nframes_t fr; - nframes_t spacer; + nframes64_t range; + nframes64_t fr; + nframes64_t spacer; if (session == 0) { return; @@ -1759,13 +1759,13 @@ Editor::set_minsec_ruler_scale (gdouble lower, gdouble upper) fr = session->frame_rate(); /* to prevent 'flashing' */ - if (lower > (spacer = (nframes_t)(128 * Editor::get_current_zoom ()))) { + if (lower > (spacer = (nframes64_t)(128 * Editor::get_current_zoom ()))) { lower -= spacer; } else { lower = 0; } upper += spacer; - range = (nframes_t) (upper - lower); + range = (nframes64_t) (upper - lower); if (range < (fr / 50)) { minsec_mark_interval = fr / 1000; /* show 1/1000 seconds */ @@ -1837,7 +1837,7 @@ Editor::set_minsec_ruler_scale (gdouble lower, gdouble upper) minsec_mark_modulo = 2; } else { - /* not possible if nframes_t is a 32 bit quantity */ + /* not possible if nframes64_t is a 32 bit quantity */ minsec_mark_interval = 4 * 60 * 60 * fr; /* show 4 hrs */ } @@ -1847,8 +1847,8 @@ Editor::set_minsec_ruler_scale (gdouble lower, gdouble upper) gint Editor::metric_get_minsec (GtkCustomRulerMark **marks, gdouble lower, gdouble upper, gint maxchars) { - nframes_t pos; - nframes_t spacer; + nframes64_t pos; + nframes64_t spacer; long hrs, mins, secs, millisecs; gchar buf[16]; gint n; @@ -1858,14 +1858,14 @@ Editor::metric_get_minsec (GtkCustomRulerMark **marks, gdouble lower, gdouble up } /* to prevent 'flashing' */ - if (lower > (spacer = (nframes_t)(128 * Editor::get_current_zoom ()))) { + if (lower > (spacer = (nframes64_t)(128 * Editor::get_current_zoom ()))) { lower = lower - spacer; } else { lower = 0; } *marks = (GtkCustomRulerMark *) g_malloc (sizeof(GtkCustomRulerMark) * minsec_nmarks); - pos = ((((nframes_t) floor(lower)) + (minsec_mark_interval/2))/minsec_mark_interval) * minsec_mark_interval; + pos = ((((nframes64_t) floor(lower)) + (minsec_mark_interval/2))/minsec_mark_interval) * minsec_mark_interval; switch (minsec_ruler_scale) { case minsec_show_seconds: for (n = 0; n < minsec_nmarks; pos += minsec_mark_interval, ++n) { diff --git a/gtk2_ardour/editor_selection.cc b/gtk2_ardour/editor_selection.cc index 9d0347e0e2..f35391cff5 100644 --- a/gtk2_ardour/editor_selection.cc +++ b/gtk2_ardour/editor_selection.cc @@ -18,7 +18,7 @@ */ #include -#include +#include #include @@ -235,7 +235,7 @@ Editor::set_selected_control_point_from_click (Selection::Operation op, bool no_ /* select this point and any others that it represents */ double y1, y2; - nframes_t x1, x2; + nframes64_t x1, x2; x1 = pixel_to_frame (clicked_control_point->get_x() - 10); x2 = pixel_to_frame (clicked_control_point->get_x() + 10); @@ -449,8 +449,8 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op, } else if (op == Selection::Extend) { list results; - nframes_t last_frame; - nframes_t first_frame; + nframes64_t last_frame; + nframes64_t first_frame; bool same_track = false; /* 1. find the last selected regionview in the track that was clicked in */ @@ -909,7 +909,7 @@ Editor::invert_selection () } bool -Editor::select_all_within (nframes_t start, nframes_t end, double top, double bot, const TrackViewList& tracklist, Selection::Operation op) +Editor::select_all_within (nframes64_t start, nframes64_t end, double top, double bot, const TrackViewList& tracklist, Selection::Operation op) { list touched; list::size_type n = 0; @@ -1029,8 +1029,8 @@ Editor::select_all_selectables_using_time_selection () return; } - nframes_t start = selection->time[clicked_selection].start; - nframes_t end = selection->time[clicked_selection].end; + nframes64_t start = selection->time[clicked_selection].start; + nframes64_t end = selection->time[clicked_selection].end; if (end - start < 1) { return; @@ -1122,8 +1122,8 @@ Editor::select_all_selectables_using_loop() void Editor::select_all_selectables_using_cursor (Cursor *cursor, bool after) { - nframes_t start; - nframes_t end; + nframes64_t start; + nframes64_t end; list touched; if (after) { @@ -1162,8 +1162,8 @@ Editor::select_all_selectables_using_cursor (Cursor *cursor, bool after) void Editor::select_all_selectables_using_edit (bool after) { - nframes_t start; - nframes_t end; + nframes64_t start; + nframes64_t end; list touched; if (after) { diff --git a/gtk2_ardour/editor_tempodisplay.cc b/gtk2_ardour/editor_tempodisplay.cc index c9bd50607b..1e5c02f5d8 100644 --- a/gtk2_ardour/editor_tempodisplay.cc +++ b/gtk2_ardour/editor_tempodisplay.cc @@ -210,7 +210,7 @@ Editor::draw_measures () } void -Editor::mouse_add_new_tempo_event (nframes_t frame) +Editor::mouse_add_new_tempo_event (nframes64_t frame) { if (session == 0) { return; @@ -252,7 +252,7 @@ Editor::mouse_add_new_tempo_event (nframes_t frame) } void -Editor::mouse_add_new_meter_event (nframes_t frame) +Editor::mouse_add_new_meter_event (nframes64_t frame) { if (session == 0) { return; diff --git a/gtk2_ardour/editor_timefx.cc b/gtk2_ardour/editor_timefx.cc index 652973ca26..6628be7116 100644 --- a/gtk2_ardour/editor_timefx.cc +++ b/gtk2_ardour/editor_timefx.cc @@ -279,7 +279,6 @@ Editor::time_fx (RegionSelection& regions, float val, bool pitching) bool realtime = false; bool precise = false; bool peaklock = true; - bool softening = true; bool longwin = false; bool shortwin = false; string txt; @@ -314,7 +313,6 @@ Editor::time_fx (RegionSelection& regions, float val, bool pitching) if (realtime) options |= RubberBandStretcher::OptionProcessRealTime; if (precise) options |= RubberBandStretcher::OptionStretchPrecise; if (!peaklock) options |= RubberBandStretcher::OptionPhaseIndependent; - if (!softening) options |= RubberBandStretcher::OptionPhasePeakLocked; if (longwin) options |= RubberBandStretcher::OptionWindowLong; if (shortwin) options |= RubberBandStretcher::OptionWindowShort; diff --git a/gtk2_ardour/engine_dialog.cc b/gtk2_ardour/engine_dialog.cc index ab02a051c2..7d8f29cce4 100644 --- a/gtk2_ardour/engine_dialog.cc +++ b/gtk2_ardour/engine_dialog.cc @@ -452,11 +452,19 @@ EngineControl::build_command_line (vector& cmd) } else if (str == _("Playback/Recording on 2 Devices")) { + string input_device = get_device_name (driver, input_device_combo.get_active_text()); + string output_device = get_device_name (driver, output_device_combo.get_active_text()); + + if (input_device.empty() || output_device.empty()) { + cmd.clear (); + return; + } + cmd.push_back ("-C"); - cmd.push_back (get_device_name (driver, input_device_combo.get_active_text())); + cmd.push_back (input_device); cmd.push_back ("-P"); - cmd.push_back (get_device_name (driver, output_device_combo.get_active_text())); - + cmd.push_back (output_device); + } else if (str == _("Playback only")) { cmd.push_back ("-P"); } else if (str == _("Recording only")) { @@ -478,8 +486,15 @@ EngineControl::build_command_line (vector& cmd) if (using_alsa) { if (audio_mode_combo.get_active_text() != _("Playback/Recording on 2 Devices")) { + + string device = get_device_name (driver, interface_combo.get_active_text()); + if (device.empty()) { + cmd.clear (); + return; + } + cmd.push_back ("-d"); - cmd.push_back (get_device_name (driver, interface_combo.get_active_text())); + cmd.push_back (device); } if (hw_meter_button.get_active()) { @@ -513,8 +528,15 @@ EngineControl::build_command_line (vector& cmd) #ifdef __APPLE__ // note: older versions of the CoreAudio JACK backend use -n instead of -d here + + string device = get_device_name (driver, interface_combo.get_active_text()); + if (device.empty()) { + cmd.clear (); + return; + } + cmd.push_back ("-d"); - cmd.push_back (get_device_name (driver, interface_combo.get_active_text())); + cmd.push_back (device); #endif } else if (using_oss) { @@ -544,6 +566,10 @@ EngineControl::setup_engine () std::string cwd = "/tmp"; build_command_line (args); + + if (args.empty()) { + return 1; // try again + } Glib::ustring jackdrc_path = Glib::get_home_dir(); jackdrc_path += "/.jackdrc"; @@ -990,6 +1016,15 @@ EngineControl::get_device_name (const string& driver, const string& human_readab vector::iterator n; vector::iterator i; + if (human_readable.empty()) { + /* this can happen if the user's .ardourrc file has a device name from + another computer system in it + */ + MessageDialog msg (_("You need to choose an audio device first.")); + msg.run (); + return string(); + } + if (backend_devs.empty()) { return human_readable; } @@ -1001,12 +1036,9 @@ EngineControl::get_device_name (const string& driver, const string& human_readab } if (i == devices[driver].end()) { - fatal << string_compose (_("programming error: %1"), "true hardware name for ID missing") << endmsg; - /*NOTREACHED*/ + warning << string_compose (_("Audio device \"%1\" not known on this computer."), human_readable) << endmsg; } - /* keep gcc happy */ - return string(); } diff --git a/gtk2_ardour/export_dialog.cc b/gtk2_ardour/export_dialog.cc index db741d66ed..ef99bf43bf 100644 --- a/gtk2_ardour/export_dialog.cc +++ b/gtk2_ardour/export_dialog.cc @@ -975,8 +975,9 @@ ExportDialog::do_export () progress_connection = Glib::signal_timeout().connect (mem_fun(*this, &ExportDialog::progress_timeout), 100); cancel_label.set_text (_("Stop Export")); + session->pre_export (); export_data(); - + progress_connection.disconnect (); end_dialog (); } @@ -996,7 +997,7 @@ ExportDialog::end_dialog () } } - session->finalize_audio_export (); + session->finalize_export (); hide_all (); @@ -1017,6 +1018,7 @@ ExportDialog::start_export () */ if (file_entry.get_text().length() == 0) { + sys::path export_file_path = session->session_directory().export_path(); if (!wants_dir()) { @@ -1229,7 +1231,7 @@ ExportDialog::initSpec(string &filepath) { spec.path = filepath; spec.progress = 0; - spec.running = true; + spec.running = false; spec.stop = false; spec.port_map.clear(); diff --git a/gtk2_ardour/export_range_markers_dialog.cc b/gtk2_ardour/export_range_markers_dialog.cc index 8bb93eb4aa..bf2f0e3989 100644 --- a/gtk2_ardour/export_range_markers_dialog.cc +++ b/gtk2_ardour/export_range_markers_dialog.cc @@ -81,8 +81,6 @@ ExportRangeMarkersDialog::process_range_markers_export(Locations::LocationList& spec.start_frame = currentLocation->start(); spec.end_frame = currentLocation->end(); - getSession().request_locate(spec.start_frame, false); - if (getSession().start_export(spec)){ // if export fails return; @@ -100,6 +98,8 @@ ExportRangeMarkersDialog::process_range_markers_export(Locations::LocationList& } current_range_marker_index++; + + getSession().stop_export (spec); } } diff --git a/gtk2_ardour/gain_meter.cc b/gtk2_ardour/gain_meter.cc index 0e51b7a68c..107b0eedfc 100644 --- a/gtk2_ardour/gain_meter.cc +++ b/gtk2_ardour/gain_meter.cc @@ -57,42 +57,49 @@ using namespace Gtk; using namespace sigc; using namespace std; -sigc::signal GainMeter::ResetAllPeakDisplays; -sigc::signal GainMeter::ResetGroupPeakDisplays; -Glib::RefPtr GainMeter::slider; -Glib::RefPtr GainMeter::rail; +sigc::signal GainMeterBase::ResetAllPeakDisplays; +sigc::signal GainMeterBase::ResetGroupPeakDisplays; + map > GainMeter::metric_pixmaps; +Glib::RefPtr GainMeter::slider; -int + +void GainMeter::setup_slider_pix () { - slider = ::get_icon ("fader_belt"); - return 0; + if ((slider = ::get_icon ("fader_belt")) == 0) { + throw failed_constructor(); + } } -GainMeter::GainMeter (boost::shared_ptr io, Session& s) +GainMeterBase::GainMeterBase (boost::shared_ptr io, Session& s, + const Glib::RefPtr& pix, + bool horizontal) : _io (io), _session (s), - gain_slider (0), // 0.781787 is the value needed for gain to be set to 0. gain_adjustment (0.781787, 0.0, 1.0, 0.01, 0.1), gain_automation_style_button (""), gain_automation_state_button ("") { - if (slider == 0) { - setup_slider_pix (); - } - ignore_toggle = false; meter_menu = 0; next_release_selects = false; style_changed = true; + _width = Wide; - gain_slider = manage (new VSliderController (slider, - &gain_adjustment, - *_io->gain_control().get(), - false)); + if (horizontal) { + gain_slider = manage (new HSliderController (pix, + &gain_adjustment, + _io->gain_control(), + false)); + } else { + gain_slider = manage (new VSliderController (pix, + &gain_adjustment, + _io->gain_control(), + false)); + } level_meter = new LevelMeter(_io, _session); @@ -107,11 +114,6 @@ GainMeter::GainMeter (boost::shared_ptr io, Session& s) gain_display.signal_focus_in_event().connect (mem_fun (*this, &GainMeter::gain_focused), false); gain_display.signal_focus_out_event().connect (mem_fun (*this, &GainMeter::gain_focused), false); - gain_display_box.set_name ("MeterMetricsStrip"); - gain_display_box.set_homogeneous (true); - gain_display_box.set_spacing (2); - gain_display_box.pack_start (gain_display, true, true); - peak_display.set_name ("MixerStripPeakDisplay"); // peak_display.set_has_frame (false); // peak_display.set_editable (false); @@ -120,9 +122,6 @@ GainMeter::GainMeter (boost::shared_ptr io, Session& s) peak_display.set_label (_("-inf")); peak_display.unset_flags (Gtk::CAN_FOCUS); - meter_metric_area.set_name ("MeterMetricsStrip"); - set_size_request_to_display_given_text (meter_metric_area, "-50", 0, 0); - gain_automation_style_button.set_name ("MixerAutomationModeButton"); gain_automation_state_button.set_name ("MixerAutomationPlaybackButton"); @@ -135,193 +134,67 @@ GainMeter::GainMeter (boost::shared_ptr io, Session& s) gain_automation_state_button.set_size_request(15, 15); gain_automation_style_button.set_size_request(15, 15); - HBox* fader_centering_box = manage (new HBox); - fader_centering_box->pack_start (*gain_slider, true, false); - - fader_vbox = manage (new Gtk::VBox()); - fader_vbox->set_spacing (0); - fader_vbox->pack_start (*fader_centering_box, false, false, 0); - hbox.set_spacing (2); - if (_io->default_type() == ARDOUR::DataType::AUDIO) { - hbox.pack_start (*fader_vbox, true, true); - } - - set_width (Narrow); - Route* r; - if ((r = dynamic_cast (_io.get())) != 0) { + boost::shared_ptr r; - /* - if we have a non-hidden route (ie. we're not the click or the auditioner), - pack some route-dependent stuff. - */ + if ((r = boost::dynamic_pointer_cast (_io)) != 0) { - gain_display_box.pack_end (peak_display, true, true); - hbox.pack_end (*level_meter, true, true); + if (!r->is_hidden()) { - using namespace Menu_Helpers; - - gain_astate_menu.items().push_back (MenuElem (_("Manual"), - bind (mem_fun (*_io, &IO::set_parameter_automation_state), - Parameter(GainAutomation), (AutoState) Off))); - gain_astate_menu.items().push_back (MenuElem (_("Play"), - bind (mem_fun (*_io, &IO::set_parameter_automation_state), - Parameter(GainAutomation), (AutoState) Play))); - gain_astate_menu.items().push_back (MenuElem (_("Write"), - bind (mem_fun (*_io, &IO::set_parameter_automation_state), - Parameter(GainAutomation), (AutoState) Write))); - gain_astate_menu.items().push_back (MenuElem (_("Touch"), - bind (mem_fun (*_io, &IO::set_parameter_automation_state), - Parameter(GainAutomation), (AutoState) Touch))); - - gain_astyle_menu.items().push_back (MenuElem (_("Trim"))); - gain_astyle_menu.items().push_back (MenuElem (_("Abs"))); + using namespace Menu_Helpers; - gain_astate_menu.set_name ("ArdourContextMenu"); - gain_astyle_menu.set_name ("ArdourContextMenu"); - - gain_automation_style_button.signal_button_press_event().connect (mem_fun(*this, &GainMeter::gain_automation_style_button_event), false); - gain_automation_state_button.signal_button_press_event().connect (mem_fun(*this, &GainMeter::gain_automation_state_button_event), false); - - r->gain_control()->list()->automation_state_changed.connect (mem_fun(*this, &GainMeter::gain_automation_state_changed)); - r->gain_control()->list()->automation_style_changed.connect (mem_fun(*this, &GainMeter::gain_automation_style_changed)); - fader_vbox->pack_start (gain_automation_state_button, false, false, 0); + gain_astate_menu.items().push_back (MenuElem (_("Manual"), + bind (mem_fun (*_io, &IO::set_parameter_automation_state), + Parameter(GainAutomation), (AutoState) Off))); + gain_astate_menu.items().push_back (MenuElem (_("Play"), + bind (mem_fun (*_io, &IO::set_parameter_automation_state), + Parameter(GainAutomation), (AutoState) Play))); + gain_astate_menu.items().push_back (MenuElem (_("Write"), + bind (mem_fun (*_io, &IO::set_parameter_automation_state), + Parameter(GainAutomation), (AutoState) Write))); + gain_astate_menu.items().push_back (MenuElem (_("Touch"), + bind (mem_fun (*_io, &IO::set_parameter_automation_state), + Parameter(GainAutomation), (AutoState) Touch))); + + gain_astyle_menu.items().push_back (MenuElem (_("Trim"))); + gain_astyle_menu.items().push_back (MenuElem (_("Abs"))); + + gain_astate_menu.set_name ("ArdourContextMenu"); + gain_astyle_menu.set_name ("ArdourContextMenu"); + + gain_automation_style_button.signal_button_press_event().connect (mem_fun(*this, &GainMeterBase::gain_automation_style_button_event), false); + gain_automation_state_button.signal_button_press_event().connect (mem_fun(*this, &GainMeterBase::gain_automation_state_button_event), false); + + r->gain_control()->list()->automation_state_changed.connect (mem_fun(*this, &GainMeter::gain_automation_state_changed)); + r->gain_control()->list()->automation_style_changed.connect (mem_fun(*this, &GainMeter::gain_automation_style_changed)); - gain_automation_state_changed (); + gain_automation_state_changed (); + } } - set_spacing (2); - - pack_start (gain_display_box, Gtk::PACK_SHRINK); - pack_start (hbox, Gtk::PACK_SHRINK); - - _io->gain_control()->Changed.connect (mem_fun(*this, &GainMeter::gain_changed)); + _io->gain_control()->Changed.connect (mem_fun(*this, &GainMeterBase::gain_changed)); - meter_metric_area.signal_expose_event().connect (mem_fun(*this, &GainMeter::meter_metrics_expose)); - gain_adjustment.signal_value_changed().connect (mem_fun(*this, &GainMeter::gain_adjusted)); - peak_display.signal_button_release_event().connect (mem_fun(*this, &GainMeter::peak_button_release), false); - gain_display.signal_key_press_event().connect (mem_fun(*this, &GainMeter::gain_key_press), false); + gain_adjustment.signal_value_changed().connect (mem_fun(*this, &GainMeterBase::gain_adjusted)); + peak_display.signal_button_release_event().connect (mem_fun(*this, &GainMeterBase::peak_button_release), false); + gain_display.signal_key_press_event().connect (mem_fun(*this, &GainMeterBase::gain_key_press), false); gain_changed (); show_gain (); update_gain_sensitive (); - ResetAllPeakDisplays.connect (mem_fun(*this, &GainMeter::reset_peak_display)); - ResetGroupPeakDisplays.connect (mem_fun(*this, &GainMeter::reset_group_peak_display)); - - UI::instance()->theme_changed.connect (mem_fun(*this, &GainMeter::on_theme_changed)); - - ColorsChanged.connect (bind (mem_fun (*this, &GainMeter::color_handler), false)); - DPIReset.connect (bind (mem_fun (*this, &GainMeter::color_handler), true)); + ResetAllPeakDisplays.connect (mem_fun(*this, &GainMeterBase::reset_peak_display)); + ResetGroupPeakDisplays.connect (mem_fun(*this, &GainMeterBase::reset_group_peak_display)); - //hide_all(); + UI::instance()->theme_changed.connect (mem_fun(*this, &GainMeterBase::on_theme_changed)); + ColorsChanged.connect (bind(mem_fun (*this, &GainMeterBase::color_handler), false)); + DPIReset.connect (bind(mem_fun (*this, &GainMeterBase::color_handler), true)); } -void -GainMeter::set_width (Width w, int len) -{ - _width = w; - level_meter->setup_meters (len); -} - -Glib::RefPtr -GainMeter::render_metrics (Gtk::Widget& w) -{ - //cerr << "GainMeter::render_metrics() called, red = " << w.get_style()->get_bg(Gtk::STATE_NORMAL).get_red() << endl;//DEBUG - Glib::RefPtr win (w.get_window()); - Glib::RefPtr fg_gc (w.get_style()->get_fg_gc (Gtk::STATE_NORMAL)); - Glib::RefPtr bg_gc (w.get_style()->get_bg_gc (Gtk::STATE_NORMAL)); - gint width, height; - int db_points[] = { -50, -40, -20, -30, -10, -3, 0, 4 }; - char buf[32]; - - win->get_size (width, height); - - Glib::RefPtr pixmap = Gdk::Pixmap::create (win, width, height); - - metric_pixmaps[w.get_name()] = pixmap; - - pixmap->draw_rectangle (bg_gc, true, 0, 0, width, height); - - Glib::RefPtr layout = w.create_pango_layout(""); - - for (uint32_t i = 0; i < sizeof (db_points)/sizeof (db_points[0]); ++i) { - - float fraction = log_meter (db_points[i]); - gint pos = height - (gint) floor (height * fraction); - - snprintf (buf, sizeof (buf), "%d", abs (db_points[i])); - - layout->set_text (buf); - - /* we want logical extents, not ink extents here */ - - int width, height; - layout->get_pixel_size (width, height); - - pixmap->draw_line (fg_gc, 0, pos, 4, pos); - pixmap->draw_layout (fg_gc, 6, pos - (height/2), layout); - } - - return pixmap; -} - -gint -GainMeter::meter_metrics_expose (GdkEventExpose *ev) -{ - /* Only draw dB scale if we're metering audio */ - if (_io->n_inputs().n_audio() + _io->n_outputs().n_audio() == 0) - return true; - - static Glib::RefPtr meter_style; - - if (style_changed) { - meter_style = meter_metric_area.get_style(); - } - - Glib::RefPtr win (meter_metric_area.get_window()); - Glib::RefPtr fg_gc (meter_style->get_fg_gc (Gtk::STATE_NORMAL)); - Glib::RefPtr bg_gc (meter_style->get_bg_gc (Gtk::STATE_NORMAL)); - - GdkRectangle base_rect; - GdkRectangle draw_rect; - gint width, height; - - win->get_size (width, height); - - base_rect.width = width; - base_rect.height = height; - base_rect.x = 0; - base_rect.y = 0; - - Glib::RefPtr pixmap; - std::map >::iterator i = metric_pixmaps.find (meter_metric_area.get_name()); - - if (i == metric_pixmaps.end() || style_changed || dpi_changed) { - pixmap = render_metrics (meter_metric_area); - } else { - pixmap = i->second; - } - - gdk_rectangle_intersect (&ev->area, &base_rect, &draw_rect); - win->draw_rectangle (bg_gc, false, draw_rect.x, draw_rect.y, draw_rect.width, draw_rect.height); - win->draw_drawable (fg_gc, pixmap, draw_rect.x, draw_rect.y, draw_rect.x, draw_rect.y, draw_rect.width, draw_rect.height); - - style_changed = false; - return true; -} - -void -GainMeter::on_theme_changed() -{ - style_changed = true; -} - -GainMeter::~GainMeter () +GainMeterBase::~GainMeterBase () { if (meter_menu) { delete meter_menu; @@ -332,12 +205,18 @@ GainMeter::~GainMeter () } } +void +GainMeterBase::hide_all_meters () +{ + level_meter->hide_meters(); +} + void GainMeter::hide_all_meters () { bool remove_metric_area = false; - level_meter->hide_meters(); + GainMeterBase::hide_all_meters (); if (remove_metric_area) { if (meter_metric_area.get_parent()) { @@ -347,24 +226,23 @@ GainMeter::hide_all_meters () } void +GainMeterBase::setup_meters (int len) +{ + level_meter->setup_meters(len, 5); +} + +void GainMeter::setup_meters (int len) { if (!meter_metric_area.get_parent()) { level_meter->pack_end (meter_metric_area, false, false); meter_metric_area.show_all (); } - level_meter->setup_meters(len, 5); -} - -int -GainMeter::get_gm_width () -{ - Gtk::Requisition sz = hbox.size_request (); - return sz.width; + GainMeterBase::setup_meters (len); } bool -GainMeter::gain_key_press (GdkEventKey* ev) +GainMeterBase::gain_key_press (GdkEventKey* ev) { if (key_is_legal_for_numeric_entry (ev->keyval)) { /* drop through to normal handling */ @@ -375,15 +253,16 @@ GainMeter::gain_key_press (GdkEventKey* ev) } bool -GainMeter::peak_button_release (GdkEventButton* ev) +GainMeterBase::peak_button_release (GdkEventButton* ev) { /* reset peak label */ if (ev->button == 1 && Keyboard::modifier_state_equals (ev->state, Keyboard::PrimaryModifier|Keyboard::TertiaryModifier)) { ResetAllPeakDisplays (); } else if (ev->button == 1 && Keyboard::modifier_state_equals (ev->state, Keyboard::PrimaryModifier)) { - Route* r; - if ((r = dynamic_cast (_io.get())) != 0) { + boost::shared_ptr r; + + if ((r = boost::dynamic_pointer_cast (_io)) != 0) { ResetGroupPeakDisplays (r->mix_group()); } } else { @@ -394,10 +273,11 @@ GainMeter::peak_button_release (GdkEventButton* ev) } void -GainMeter::reset_peak_display () +GainMeterBase::reset_peak_display () { - Route * r; - if ((r = dynamic_cast (_io.get())) != 0) { + boost::shared_ptr r; + + if ((r = boost::dynamic_pointer_cast (_io)) != 0) { r->peak_meter().reset_max(); } @@ -408,10 +288,11 @@ GainMeter::reset_peak_display () } void -GainMeter::reset_group_peak_display (RouteGroup* group) +GainMeterBase::reset_group_peak_display (RouteGroup* group) { - Route* r; - if ((r = dynamic_cast (_io.get())) != 0) { + boost::shared_ptr r; + + if ((r = boost::dynamic_pointer_cast (_io)) != 0) { if (group == r->mix_group()) { reset_peak_display (); } @@ -419,7 +300,7 @@ GainMeter::reset_group_peak_display (RouteGroup* group) } void -GainMeter::popup_meter_menu (GdkEventButton *ev) +GainMeterBase::popup_meter_menu (GdkEventButton *ev) { using namespace Menu_Helpers; @@ -440,7 +321,7 @@ GainMeter::popup_meter_menu (GdkEventButton *ev) } bool -GainMeter::gain_focused (GdkEventFocus* ev) +GainMeterBase::gain_focused (GdkEventFocus* ev) { if (ev->in) { gain_display.select_region (0, -1); @@ -451,7 +332,7 @@ GainMeter::gain_focused (GdkEventFocus* ev) } void -GainMeter::gain_activated () +GainMeterBase::gain_activated () { float f; @@ -470,7 +351,7 @@ GainMeter::gain_activated () } void -GainMeter::show_gain () +GainMeterBase::show_gain () { char buf[32]; @@ -486,7 +367,7 @@ GainMeter::show_gain () } void -GainMeter::gain_adjusted () +GainMeterBase::gain_adjusted () { if (!ignore_toggle) { _io->gain_control()->set_value (slider_position_to_gain (gain_adjustment.get_value())); @@ -495,7 +376,7 @@ GainMeter::gain_adjusted () } void -GainMeter::effective_gain_display () +GainMeterBase::effective_gain_display () { gfloat value = gain_to_slider_position (_io->effective_gain()); @@ -507,25 +388,25 @@ GainMeter::effective_gain_display () } void -GainMeter::gain_changed () +GainMeterBase::gain_changed () { - Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &GainMeter::effective_gain_display)); + Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &GainMeterBase::effective_gain_display)); } void -GainMeter::set_meter_strip_name (const char * name) +GainMeterBase::set_meter_strip_name (const char * name) { meter_metric_area.set_name (name); } void -GainMeter::set_fader_name (const char * name) +GainMeterBase::set_fader_name (const char * name) { gain_slider->set_name (name); } void -GainMeter::update_gain_sensitive () +GainMeterBase::update_gain_sensitive () { static_cast(gain_slider)->set_sensitive (!(_io->gain_control()->list()->automation_state() & Play)); } @@ -552,13 +433,13 @@ next_meter_point (MeterPoint mp) } gint -GainMeter::meter_press(GdkEventButton* ev) +GainMeterBase::meter_press(GdkEventButton* ev) { - Route* _route; + boost::shared_ptr _route; wait_for_release = false; - - if ((_route = dynamic_cast(_io.get())) == 0) { + + if ((_route = boost::dynamic_pointer_cast(_io)) == 0) { return FALSE; } @@ -589,7 +470,7 @@ GainMeter::meter_press(GdkEventButton* ev) _session.begin_reversible_command (_("meter point change")); Session::GlobalMeteringStateCommand *cmd = new Session::GlobalMeteringStateCommand (_session, this); - _session.foreach_route (this, &GainMeter::set_meter_point, next_meter_point (_route->meter_point())); + _session.foreach_route (this, &GainMeterBase::set_meter_point, next_meter_point (_route->meter_point())); cmd->mark(); _session.add_command (cmd); _session.commit_reversible_command (); @@ -627,26 +508,31 @@ GainMeter::meter_press(GdkEventButton* ev) } gint -GainMeter::meter_release(GdkEventButton* ev) +GainMeterBase::meter_release(GdkEventButton* ev) { - if(!ignore_toggle){ if (wait_for_release){ wait_for_release = false; - set_meter_point (*(dynamic_cast(_io.get())), old_meter_point); + + boost::shared_ptr r; + + if ((r = boost::dynamic_pointer_cast(_io)) != 0) { + set_meter_point (*r, old_meter_point); + } } } + return true; } void -GainMeter::set_meter_point (Route& route, MeterPoint mp) +GainMeterBase::set_meter_point (Route& route, MeterPoint mp) { route.set_meter_point (mp, this); } void -GainMeter::set_mix_group_meter_point (Route& route, MeterPoint mp) +GainMeterBase::set_mix_group_meter_point (Route& route, MeterPoint mp) { RouteGroup* mix_group; @@ -658,31 +544,31 @@ GainMeter::set_mix_group_meter_point (Route& route, MeterPoint mp) } void -GainMeter::meter_point_clicked () +GainMeterBase::meter_point_clicked () { - Route* r; - - if ((r = dynamic_cast (_io.get())) != 0) { + boost::shared_ptr r; + if ((r = boost::dynamic_pointer_cast (_io)) != 0) { + /* WHAT? */ } } gint -GainMeter::start_gain_touch (GdkEventButton* ev) +GainMeterBase::start_gain_touch (GdkEventButton* ev) { _io->gain_control()->list()->start_touch (); return FALSE; } gint -GainMeter::end_gain_touch (GdkEventButton* ev) +GainMeterBase::end_gain_touch (GdkEventButton* ev) { _io->gain_control()->list()->stop_touch (); return FALSE; } gint -GainMeter::gain_automation_state_button_event (GdkEventButton *ev) +GainMeterBase::gain_automation_state_button_event (GdkEventButton *ev) { if (ev->type == GDK_BUTTON_RELEASE) { return TRUE; @@ -700,7 +586,7 @@ GainMeter::gain_automation_state_button_event (GdkEventButton *ev) } gint -GainMeter::gain_automation_style_button_event (GdkEventButton *ev) +GainMeterBase::gain_automation_style_button_event (GdkEventButton *ev) { if (ev->type == GDK_BUTTON_RELEASE) { return TRUE; @@ -717,19 +603,19 @@ GainMeter::gain_automation_style_button_event (GdkEventButton *ev) } string -GainMeter::astate_string (AutoState state) +GainMeterBase::astate_string (AutoState state) { return _astate_string (state, false); } string -GainMeter::short_astate_string (AutoState state) +GainMeterBase::short_astate_string (AutoState state) { return _astate_string (state, true); } string -GainMeter::_astate_string (AutoState state, bool shrt) +GainMeterBase::_astate_string (AutoState state, bool shrt) { string sstr; @@ -752,19 +638,19 @@ GainMeter::_astate_string (AutoState state, bool shrt) } string -GainMeter::astyle_string (AutoStyle style) +GainMeterBase::astyle_string (AutoStyle style) { return _astyle_string (style, false); } string -GainMeter::short_astyle_string (AutoStyle style) +GainMeterBase::short_astyle_string (AutoStyle style) { return _astyle_string (style, true); } string -GainMeter::_astyle_string (AutoStyle style, bool shrt) +GainMeterBase::_astyle_string (AutoStyle style, bool shrt) { if (style & Trim) { return _("Trim"); @@ -776,9 +662,8 @@ GainMeter::_astyle_string (AutoStyle style, bool shrt) } void -GainMeter::gain_automation_style_changed () +GainMeterBase::gain_automation_style_changed () { - // Route* _route = dynamic_cast(&_io); switch (_width) { case Wide: gain_automation_style_button.set_label (astyle_string(_io->gain_control()->list()->automation_style())); @@ -790,10 +675,9 @@ GainMeter::gain_automation_style_changed () } void -GainMeter::gain_automation_state_changed () +GainMeterBase::gain_automation_state_changed () { - ENSURE_GUI_THREAD(mem_fun(*this, &GainMeter::gain_automation_state_changed)); - //Route* _route = dynamic_cast(&_io); + ENSURE_GUI_THREAD(mem_fun(*this, &GainMeterBase::gain_automation_state_changed)); bool x; @@ -821,12 +705,12 @@ GainMeter::gain_automation_state_changed () gain_watching.disconnect(); if (x) { - gain_watching = ARDOUR_UI::RapidScreenUpdate.connect (mem_fun (*this, &GainMeter::effective_gain_display)); + gain_watching = ARDOUR_UI::RapidScreenUpdate.connect (mem_fun (*this, &GainMeterBase::effective_gain_display)); } } void -GainMeter::update_meters() +GainMeterBase::update_meters() { char buf[32]; float mpeak = level_meter->update_meters(); @@ -846,9 +730,167 @@ GainMeter::update_meters() } } -void GainMeter::color_handler (bool dpi) +void GainMeterBase::color_handler(bool dpi) { color_changed = true; dpi_changed = (dpi) ? true : false; setup_meters(); } + +void +GainMeterBase::set_width (Width w, int len) +{ + _width = w; + level_meter->setup_meters (len); +} + + +void +GainMeterBase::on_theme_changed() +{ + style_changed = true; +} + +GainMeter::GainMeter (boost::shared_ptr io, Session& s) + : GainMeterBase (io, s, slider, false) +{ + + gain_display_box.set_homogeneous (true); + gain_display_box.set_spacing (2); + gain_display_box.pack_start (gain_display, true, true); + + meter_metric_area.set_name ("AudioTrackMetrics"); + set_size_request_to_display_given_text (meter_metric_area, "-50", 0, 0); + + gain_automation_style_button.set_name ("MixerAutomationModeButton"); + gain_automation_state_button.set_name ("MixerAutomationPlaybackButton"); + + ARDOUR_UI::instance()->tooltips().set_tip (gain_automation_state_button, _("Fader automation mode")); + ARDOUR_UI::instance()->tooltips().set_tip (gain_automation_style_button, _("Fader automation type")); + + gain_automation_style_button.unset_flags (Gtk::CAN_FOCUS); + gain_automation_state_button.unset_flags (Gtk::CAN_FOCUS); + + gain_automation_state_button.set_size_request(15, 15); + gain_automation_style_button.set_size_request(15, 15); + + HBox* fader_centering_box = manage (new HBox); + fader_centering_box->pack_start (*gain_slider, true, false); + + fader_vbox = manage (new Gtk::VBox()); + fader_vbox->set_spacing (0); + fader_vbox->pack_start (*fader_centering_box, false, false, 0); + + hbox.set_spacing (2); + hbox.pack_start (*fader_vbox, true, true); + + boost::shared_ptr r; + + if ((r = boost::dynamic_pointer_cast (_io)) != 0) { + + /* + if we have a non-hidden route (ie. we're not the click or the auditioner), + pack some route-dependent stuff. + */ + + gain_display_box.pack_end (peak_display, true, true); + hbox.pack_end (*level_meter, true, true); + + if (!r->is_hidden()) { + fader_vbox->pack_start (gain_automation_state_button, false, false, 0); + } + } + + set_spacing (2); + + pack_start (gain_display_box, Gtk::PACK_SHRINK); + pack_start (hbox, Gtk::PACK_SHRINK); + + meter_metric_area.signal_expose_event().connect (mem_fun(*this, &GainMeter::meter_metrics_expose)); +} + + +int +GainMeter::get_gm_width () +{ + Gtk::Requisition sz; + hbox.size_request (sz); + return sz.width; +} + +Glib::RefPtr +GainMeter::render_metrics (Gtk::Widget& w) +{ + Glib::RefPtr win (w.get_window()); + Glib::RefPtr fg_gc (w.get_style()->get_fg_gc (Gtk::STATE_NORMAL)); + Glib::RefPtr bg_gc (w.get_style()->get_bg_gc (Gtk::STATE_NORMAL)); + gint width, height; + int db_points[] = { -50, -40, -20, -30, -10, -3, 0, 4 }; + char buf[32]; + + win->get_size (width, height); + + Glib::RefPtr pixmap = Gdk::Pixmap::create (win, width, height); + + metric_pixmaps[w.get_name()] = pixmap; + + pixmap->draw_rectangle (bg_gc, true, 0, 0, width, height); + + Glib::RefPtr layout = w.create_pango_layout(""); + + for (uint32_t i = 0; i < sizeof (db_points)/sizeof (db_points[0]); ++i) { + + float fraction = log_meter (db_points[i]); + gint pos = height - (gint) floor (height * fraction); + + snprintf (buf, sizeof (buf), "%d", abs (db_points[i])); + + layout->set_text (buf); + + /* we want logical extents, not ink extents here */ + + int width, height; + layout->get_pixel_size (width, height); + + pixmap->draw_line (fg_gc, 0, pos, 4, pos); + pixmap->draw_layout (fg_gc, 6, pos - (height/2), layout); + } + + return pixmap; +} + +gint +GainMeter::meter_metrics_expose (GdkEventExpose *ev) +{ + static Glib::RefPtr meter_style; + if (style_changed) { + meter_style = meter_metric_area.get_style(); + } + Glib::RefPtr win (meter_metric_area.get_window()); + Glib::RefPtr bg_gc (meter_style->get_bg_gc (Gtk::STATE_INSENSITIVE)); + GdkRectangle base_rect; + GdkRectangle draw_rect; + gint width, height; + + win->get_size (width, height); + + base_rect.width = width; + base_rect.height = height; + base_rect.x = 0; + base_rect.y = 0; + + Glib::RefPtr pixmap; + std::map >::iterator i = metric_pixmaps.find (meter_metric_area.get_name()); + + if (i == metric_pixmaps.end() || style_changed || dpi_changed) { + pixmap = render_metrics (meter_metric_area); + } else { + pixmap = i->second; + } + + gdk_rectangle_intersect (&ev->area, &base_rect, &draw_rect); + win->draw_drawable (bg_gc, pixmap, draw_rect.x, draw_rect.y, draw_rect.x, draw_rect.y, draw_rect.width, draw_rect.height); + style_changed = false; + return true; +} + diff --git a/gtk2_ardour/gain_meter.h b/gtk2_ardour/gain_meter.h index cd8e74d59d..d493edf0fb 100644 --- a/gtk2_ardour/gain_meter.h +++ b/gtk2_ardour/gain_meter.h @@ -55,33 +55,29 @@ namespace Gtk { class Menu; } -class GainMeter : public Gtk::VBox +class GainMeterBase : virtual public sigc::trackable { public: - GainMeter (boost::shared_ptr, ARDOUR::Session&); - ~GainMeter (); + GainMeterBase (boost::shared_ptr, ARDOUR::Session&, const Glib::RefPtr& pix, + bool horizontal); + virtual ~GainMeterBase (); void update_gain_sensitive (); - void update_meters (); void effective_gain_display (); - void set_width (Width, int len=0); - void setup_meters (int len=0); - - int get_gm_width (); - void set_meter_strip_name (const char * name); void set_fader_name (const char * name); - /* should probably switch to using the shared_ptr that underlies - all this stuff - */ + virtual void setup_meters (int len=0); - PBD::Controllable* get_controllable() { return _io->gain_control().get(); } + boost::shared_ptr get_controllable() { return _io->gain_control(); } - private: + LevelMeter& get_level_meter() const { return *level_meter; } + Gtkmm2ext::SliderController& get_gain_slider() const { return *gain_slider; } + + protected: friend class MixerStrip; boost::shared_ptr _io; @@ -90,14 +86,12 @@ class GainMeter : public Gtk::VBox bool ignore_toggle; bool next_release_selects; - Gtkmm2ext::VSliderController *gain_slider; + Gtkmm2ext::SliderController *gain_slider; Gtk::Adjustment gain_adjustment; Gtkmm2ext::FocusEntry gain_display; Gtk::Button peak_display; - Gtk::HBox gain_display_box; - Gtk::HBox fader_box; Gtk::DrawingArea meter_metric_area; - LevelMeter *level_meter; + LevelMeter *level_meter; sigc::connection gain_watching; @@ -125,27 +119,19 @@ class GainMeter : public Gtk::VBox Width _width; - static std::map > metric_pixmaps; - static Glib::RefPtr render_metrics (Gtk::Widget&); - - gint meter_metrics_expose (GdkEventExpose *); - void show_gain (); void gain_activated (); bool gain_focused (GdkEventFocus*); float max_peak; - Gtk::VBox* fader_vbox; - Gtk::HBox hbox; - void gain_adjusted (); void gain_changed (); void meter_point_clicked (); void gain_unit_changed (); - void hide_all_meters (); + virtual void hide_all_meters (); gint meter_button_press (GdkEventButton*, uint32_t); @@ -173,10 +159,6 @@ class GainMeter : public Gtk::VBox static sigc::signal ResetAllPeakDisplays; static sigc::signal ResetGroupPeakDisplays; - static Glib::RefPtr slider; - static Glib::RefPtr rail; - static int setup_slider_pix (); - void on_theme_changed (); bool style_changed; bool dpi_changed; @@ -184,5 +166,33 @@ class GainMeter : public Gtk::VBox void color_handler(bool); }; +class GainMeter : public GainMeterBase, public Gtk::VBox +{ + public: + GainMeter (boost::shared_ptr, ARDOUR::Session&); + ~GainMeter () {} + + int get_gm_width (); + void setup_meters (int len=0); + + static void setup_slider_pix (); + + protected: + void hide_all_meters (); + + gint meter_metrics_expose (GdkEventExpose *); + + static std::map > metric_pixmaps; + static Glib::RefPtr render_metrics (Gtk::Widget&); + + private: + Gtk::HBox gain_display_box; + Gtk::HBox fader_box; + Gtk::VBox* fader_vbox; + Gtk::HBox hbox; + + static Glib::RefPtr slider; +}; + #endif /* __ardour_gtk_gain_meter_h__ */ diff --git a/gtk2_ardour/ghostregion.cc b/gtk2_ardour/ghostregion.cc index 4e06ece82f..9da7ceb370 100644 --- a/gtk2_ardour/ghostregion.cc +++ b/gtk2_ardour/ghostregion.cc @@ -43,7 +43,7 @@ GhostRegion::GhostRegion (ArdourCanvas::Group* parent, TimeAxisView& tv, TimeAxi base_rect = new ArdourCanvas::SimpleRect (*group); base_rect->property_x1() = (double) 0.0; base_rect->property_y1() = (double) 0.0; - base_rect->property_y2() = (double) trackview.height; + base_rect->property_y2() = (double) trackview.current_height(); base_rect->property_outline_what() = (guint32) 0; if (!is_automation_ghost()) { @@ -73,7 +73,7 @@ GhostRegion::set_duration (double units) void GhostRegion::set_height () { - base_rect->property_y2() = (double) trackview.height; + base_rect->property_y2() = (double) trackview.current_height(); } void @@ -121,7 +121,7 @@ AudioGhostRegion::set_height () GhostRegion::set_height(); - ht = ((trackview.height) / (double) waves.size()); + ht = ((trackview.current_height()) / (double) waves.size()); for (n = 0, i = waves.begin(); i != waves.end(); ++i, ++n) { gdouble yoff = n * ht; diff --git a/gtk2_ardour/imageframe_time_axis.cc b/gtk2_ardour/imageframe_time_axis.cc index 018fae6895..f3630e7152 100644 --- a/gtk2_ardour/imageframe_time_axis.cc +++ b/gtk2_ardour/imageframe_time_axis.cc @@ -81,7 +81,7 @@ ImageFrameTimeAxis::ImageFrameTimeAxis(const string & track_id, PublicEditor& ed label_view() ; // set the initial height of this time axis - set_height(Normal) ; + set_height(hNormal) ; } /** @@ -133,10 +133,10 @@ ImageFrameTimeAxis::~ImageFrameTimeAxis () /** * Sets the height of this TrackView to one of ths TrackHeghts * - * @param h the TrackHeight value to set + * @param h */ void -ImageFrameTimeAxis::set_height (TrackHeight h) +ImageFrameTimeAxis::set_height (uint32_t h) { VisualTimeAxis::set_height(h) ; diff --git a/gtk2_ardour/imageframe_time_axis.h b/gtk2_ardour/imageframe_time_axis.h index 4b3bf0c857..7cbed6a394 100644 --- a/gtk2_ardour/imageframe_time_axis.h +++ b/gtk2_ardour/imageframe_time_axis.h @@ -76,9 +76,9 @@ class ImageFrameTimeAxis : public VisualTimeAxis /** * Sets the height of this TrackView to one of ths TrackHeghts * - * @param h the TrackHeight value to set + * @param h the number of pixels to set the height too */ - virtual void set_height(TimeAxisView::TrackHeight) ; + virtual void set_height(uint32_t h) ; /** * Sets the number of samples per unit that are used. diff --git a/gtk2_ardour/imageframe_time_axis_view.cc b/gtk2_ardour/imageframe_time_axis_view.cc index 69205cd511..a57db60a38 100644 --- a/gtk2_ardour/imageframe_time_axis_view.cc +++ b/gtk2_ardour/imageframe_time_axis_view.cc @@ -50,7 +50,7 @@ using namespace Editing; ImageFrameTimeAxisView::ImageFrameTimeAxisView (ImageFrameTimeAxis& tv) : _trackview (tv), canvas_group (*_trackview.canvas_display), - canvas_rect (canvas_group, 0.0, 0.0, 1000000.0, tv.height) + canvas_rect (canvas_group, 0.0, 0.0, 1000000.0, tv.current_height()) { region_color = _trackview.color() ; stream_base_color = ARDOUR_UI::config()->canvasvar_ImageTrack.get() ; diff --git a/gtk2_ardour/imageframe_view.cc b/gtk2_ardour/imageframe_view.cc index f8bba3aa84..f35381301e 100644 --- a/gtk2_ardour/imageframe_view.cc +++ b/gtk2_ardour/imageframe_view.cc @@ -91,9 +91,9 @@ ImageFrameView::ImageFrameView(const string & item_id, //calculate our image width based on the track height double im_ratio = (double)width/(double)height ; - double im_width = ((double)(trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE) * im_ratio) ; + double im_width = ((double)(trackview.current_height() - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE) * im_ratio) ; - imageframe = new ImageFrame (*group, pbuf, 1.0, 1.0, ANCHOR_NW, im_width, (trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE)); + imageframe = new ImageFrame (*group, pbuf, 1.0, 1.0, ANCHOR_NW, im_width, (trackview.current_height() - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE)); frame_handle_start->signal_event().connect (bind (mem_fun (trackview.editor, &PublicEditor::canvas_imageframe_start_handle_event), frame_handle_start, this)); frame_handle_end->signal_event().connect (bind (mem_fun (trackview.editor, &PublicEditor::canvas_imageframe_end_handle_event), frame_handle_end, this)); diff --git a/gtk2_ardour/io_selector.cc b/gtk2_ardour/io_selector.cc index b0b1a5f9b7..16576a0b8f 100644 --- a/gtk2_ardour/io_selector.cc +++ b/gtk2_ardour/io_selector.cc @@ -17,8 +17,11 @@ */ +#include #include + #include + #include #include "ardour/session.h" #include "ardour/io.h" @@ -27,11 +30,15 @@ #include "ardour/audio_track.h" #include "ardour/midi_track.h" #include "ardour/data_type.h" + #include "io_selector.h" #include "utils.h" #include "gui_thread.h" #include "i18n.h" +using namespace ARDOUR; +using namespace Gtk; + IOSelector::IOSelector (ARDOUR::Session& session, boost::shared_ptr io, bool offer_inputs) : PortMatrix ( session, io->default_type(), !offer_inputs, @@ -46,14 +53,12 @@ IOSelector::IOSelector (ARDOUR::Session& session, boost::shared_ptr _io->output_changed.connect (mem_fun(*this, &IOSelector::ports_changed)); } -#ifdef FIXME - /* these got lost in a merge from 2.0 */ - set_button_sensitivity (); - io->name_changed.connect (mem_fun(*this, &IOSelector::name_changed)); -#endif + /* this got lost in a merge from 2.0 */ -} + // set_button_sensitivity (); + // io->name_changed.connect (mem_fun(*this, &IOSelector::name_changed)); +} void IOSelector::ports_changed (ARDOUR::IOChange change, void *src) @@ -161,8 +166,8 @@ IOSelector::add_row () _io->add_input_port ("", this); } - catch (ARDOUR::AudioEngine::PortRegistrationFailure& err) { - Gtk::MessageDialog msg (0, _("There are no more JACK ports available.")); + catch (AudioEngine::PortRegistrationFailure& err) { + MessageDialog msg (_("There are no more JACK ports available.")); msg.run (); } @@ -172,14 +177,13 @@ IOSelector::add_row () _io->add_output_port ("", this); } - catch (ARDOUR::AudioEngine::PortRegistrationFailure& err) { - Gtk::MessageDialog msg (0, _("There are no more JACK ports available.")); + catch (AudioEngine::PortRegistrationFailure& err) { + MessageDialog msg (_("There are no more JACK ports available.")); msg.run (); } } } - void IOSelector::remove_row (int r) { @@ -199,7 +203,54 @@ IOSelector::row_descriptor () const return _("port"); } +#if 0 +void +IOSelector::set_button_sensitivity () +{ + if (for_input) { + + if (io->input_maximum() < 0 || io->input_maximum() > (int) io->n_inputs()) { + add_port_button.set_sensitive (true); + } else { + add_port_button.set_sensitive (false); + } + + } else { + + if (io->output_maximum() < 0 || io->output_maximum() > (int) io->n_outputs()) { + add_port_button.set_sensitive (true); + } else { + add_port_button.set_sensitive (false); + } + + } + + if (for_input) { + if (io->n_inputs() && (io->input_minimum() < 0 || io->input_minimum() < (int) io->n_inputs())) { + remove_port_button.set_sensitive (true); + } else { + remove_port_button.set_sensitive (false); + } + + } else { + if (io->n_outputs() && (io->output_minimum() < 0 || io->output_minimum() < (int) io->n_outputs())) { + remove_port_button.set_sensitive (true); + } else { + remove_port_button.set_sensitive (false); + } + } +} +#endif +#if 0 +void +IOSelector::name_changed (void* src) +{ + ENSURE_GUI_THREAD(bind (mem_fun(*this, &IOSelector::name_changed), src)); + + display_ports (); +} +#endif IOSelectorWindow::IOSelectorWindow ( ARDOUR::Session& session, boost::shared_ptr io, bool for_input, bool can_cancel diff --git a/gtk2_ardour/keyboard.cc b/gtk2_ardour/keyboard.cc index 22dd274306..ef8cc34389 100644 --- a/gtk2_ardour/keyboard.cc +++ b/gtk2_ardour/keyboard.cc @@ -17,6 +17,7 @@ */ +#include #include #include "ardour_ui.h" @@ -38,11 +39,14 @@ #include "keyboard.h" #include "gui_thread.h" #include "opts.h" +#include "actions.h" #include "i18n.h" using namespace PBD; using namespace ARDOUR; +using namespace Gtk; +using namespace std; #define KBD_DEBUG 1 bool debug_keyboard = false; @@ -75,8 +79,10 @@ bool Keyboard::_some_magic_widget_has_focus = false; std::string Keyboard::user_keybindings_path; bool Keyboard::can_save_keybindings = false; +bool Keyboard::bindings_changed_after_save_became_legal = false; map Keyboard::binding_files; -std::string Keyboard::_current_binding_name = _("Unknown"); +string Keyboard::_current_binding_name = _("Unknown"); +map,Keyboard::AccelKeyLess> Keyboard::release_keys; /* set this to initially contain the modifiers we care about, then track changes in ::set_edit_modifier() etc. */ @@ -186,6 +192,7 @@ gint Keyboard::snooper (GtkWidget *widget, GdkEventKey *event) { uint32_t keyval; + bool ret = false; #if 0 cerr << "snoop widget " << widget << " key " << event->keyval << " type: " << event->type @@ -215,7 +222,23 @@ Keyboard::snooper (GtkWidget *widget, GdkEventKey *event) if (find (state.begin(), state.end(), keyval) == state.end()) { state.push_back (keyval); sort (state.begin(), state.end()); - } + + } else { + + /* key is already down. if its also used for release, + prevent auto-repeat events. + */ + + for (map::iterator k = release_keys.begin(); k != release_keys.end(); ++k) { + + const AccelKey& ak (k->first); + + if (keyval == ak.get_key() && (Gdk::ModifierType)(event->state | Gdk::RELEASE_MASK) == ak.get_mod()) { + ret = true; + break; + } + } + } } else if (event->type == GDK_KEY_RELEASE) { @@ -226,6 +249,20 @@ Keyboard::snooper (GtkWidget *widget, GdkEventKey *event) sort (state.begin(), state.end()); } + for (map::iterator k = release_keys.begin(); k != release_keys.end(); ++k) { + + const AccelKey& ak (k->first); + two_strings ts (k->second); + + if (keyval == ak.get_key() && (Gdk::ModifierType)(event->state | Gdk::RELEASE_MASK) == ak.get_mod()) { + Glib::RefPtr act = ActionManager::get_action (ts.first.c_str(), ts.second.c_str()); + if (act) { + act->activate(); + ret = true; + } + break; + } + } } if (event->type == GDK_KEY_RELEASE && event->keyval == GDK_w && modifier_state_equals (event->state, PrimaryModifier)) { @@ -235,7 +272,7 @@ Keyboard::snooper (GtkWidget *widget, GdkEventKey *event) } } - return false; + return ret; } bool @@ -388,6 +425,16 @@ accel_map_changed (GtkAccelMap* map, GdkModifierType mod, gpointer arg) { + Keyboard::keybindings_changed (); +} + +void +Keyboard::keybindings_changed () +{ + if (Keyboard::can_save_keybindings) { + Keyboard::bindings_changed_after_save_became_legal = true; + } + Keyboard::save_keybindings (); } @@ -400,7 +447,7 @@ Keyboard::set_can_save_keybindings (bool yn) void Keyboard::save_keybindings () { - if (can_save_keybindings) { + if (can_save_keybindings && bindings_changed_after_save_became_legal) { Gtk::AccelMap::save (user_keybindings_path); } } @@ -555,13 +602,34 @@ Keyboard::load_keybindings (string path) } } - return true; } catch (...) { error << string_compose (_("Ardour key bindings file not found at \"%1\" or contains errors."), path) << endmsg; return false; } + + /* now find all release-driven bindings */ + + vector groups; + vector names; + vector bindings; + + ActionManager::get_all_actions (groups, names, bindings); + + vector::iterator g; + vector::iterator b; + vector::iterator n; + + release_keys.clear (); + + for (n = names.begin(), b = bindings.begin(), g = groups.begin(); n != names.end(); ++n, ++b, ++g) { + if ((*b).get_mod() & Gdk::RELEASE_MASK) { + release_keys.insert (pair (*b, two_strings (*g, *n))); + } + } + + return true; } diff --git a/gtk2_ardour/keyboard.h b/gtk2_ardour/keyboard.h index de2a0929ed..e6d5065e86 100644 --- a/gtk2_ardour/keyboard.h +++ b/gtk2_ardour/keyboard.h @@ -20,18 +20,19 @@ #ifndef __ardour_keyboard_h__ #define __ardour_keyboard_h__ +#include #include #include #include #include +#include #include #include #include "selection.h" -using std::vector; using std::string; class Keyboard : public sigc::trackable, PBD::Stateful @@ -43,7 +44,7 @@ class Keyboard : public sigc::trackable, PBD::Stateful XMLNode& get_state (void); int set_state (const XMLNode&); - typedef vector State; + typedef std::vector State; typedef uint32_t ModifierMask; static uint32_t PrimaryModifier; @@ -114,12 +115,23 @@ class Keyboard : public sigc::trackable, PBD::Stateful static void magic_widget_drop_focus (); static void setup_keybindings (); + static void keybindings_changed (); static void save_keybindings (); static bool load_keybindings (std::string path); static void set_can_save_keybindings (bool yn); static std::string current_binding_name () { return _current_binding_name; } static std::map binding_files; + struct AccelKeyLess { + bool operator() (const Gtk::AccelKey a, const Gtk::AccelKey b) const { + if (a.get_key() != b.get_key()) { + return a.get_key() < b.get_key(); + } else { + return a.get_mod() < b.get_mod(); + } + } + }; + private: static Keyboard* _the_keyboard; @@ -134,8 +146,13 @@ class Keyboard : public sigc::trackable, PBD::Stateful static Gtk::Window* current_window; static std::string user_keybindings_path; static bool can_save_keybindings; + static bool bindings_changed_after_save_became_legal; static std::string _current_binding_name; + typedef std::pair two_strings; + + static std::map release_keys; + static gint _snooper (GtkWidget*, GdkEventKey*, gpointer); gint snooper (GtkWidget*, GdkEventKey*); diff --git a/gtk2_ardour/keyeditor.cc b/gtk2_ardour/keyeditor.cc index cdac398a30..e44d92943f 100644 --- a/gtk2_ardour/keyeditor.cc +++ b/gtk2_ardour/keyeditor.cc @@ -16,6 +16,7 @@ #include "actions.h" #include "keyboard.h" #include "keyeditor.h" +#include "utils.h" #include "i18n.h" @@ -167,6 +168,8 @@ KeyEditor::on_key_release_event (GdkEventKey* ev) goto out; } + possibly_translate_keyval_to_make_legal_accelerator (ev->keyval); + bool result = AccelMap::change_entry (path, ev->keyval, (ModifierType) ev->state, diff --git a/gtk2_ardour/latency_gui.cc b/gtk2_ardour/latency_gui.cc index d03ad5b9f9..e7c42fd780 100644 --- a/gtk2_ardour/latency_gui.cc +++ b/gtk2_ardour/latency_gui.cc @@ -41,6 +41,7 @@ LatencyGUI::LatencyGUI (Latent& l, nframes64_t sr, nframes64_t psz) initial_value (_latent.signal_latency()), sample_rate (sr), period_size (psz), + ignored (new PBD::IgnorableControllable()), /* max 1 second, step by frames, page by msecs */ adjustment (initial_value, 0.0, sample_rate, 1.0, sample_rate / 1000.0f), bc (adjustment, ignored, sigc::mem_fun (*this, &LatencyGUI::latency_printer)), diff --git a/gtk2_ardour/latency_gui.h b/gtk2_ardour/latency_gui.h index 0be7fdbf4c..f352f698d7 100644 --- a/gtk2_ardour/latency_gui.h +++ b/gtk2_ardour/latency_gui.h @@ -35,7 +35,7 @@ class LatencyGUI : public Gtk::VBox nframes64_t initial_value; nframes64_t sample_rate; nframes64_t period_size; - PBD::IgnorableControllable ignored; + boost::shared_ptr ignored; Gtk::Adjustment adjustment; Gtkmm2ext::BarController bc; diff --git a/gtk2_ardour/level_meter.cc b/gtk2_ardour/level_meter.cc index 8a05d8da56..f6e3731aac 100644 --- a/gtk2_ardour/level_meter.cc +++ b/gtk2_ardour/level_meter.cc @@ -100,6 +100,9 @@ LevelMeter::update_meters () if (mpeak > max_peak) { max_peak = mpeak; } + if (mpeak > max_peak) { + max_peak = mpeak; + } } } return max_peak; @@ -143,6 +146,7 @@ LevelMeter::setup_meters (int len, int initial_width) { uint32_t nmeters = _io->n_outputs().n_total(); regular_meter_width = initial_width; + guint16 width; hide_all_meters (); diff --git a/gtk2_ardour/location_ui.cc b/gtk2_ardour/location_ui.cc index 2079d0dc7a..451a85efd7 100644 --- a/gtk2_ardour/location_ui.cc +++ b/gtk2_ardour/location_ui.cc @@ -46,10 +46,10 @@ using namespace Gtkmm2ext; LocationEditRow::LocationEditRow(Session * sess, Location * loc, int32_t num) : location(0), session(0), item_table (1, 7, false), - start_set_button (_("Set")), + start_set_button (_("Use PH")), start_go_button (_("Go")), start_clock (X_("locationstart"), true, X_("LocationEditRowClock"), true), - end_set_button (_("Set")), + end_set_button (_("Use PH")), end_go_button (_("Go")), end_clock (X_("locationend"), true, X_("LocationEditRowClock"), true), length_clock (X_("locationlength"), true, X_("LocationEditRowClock"), true, true), @@ -82,7 +82,9 @@ LocationEditRow::LocationEditRow(Session * sess, Location * loc, int32_t num) composer_label.set_name ("LocationEditNumberLabel"); composer_entry.set_name ("LocationEditNameEntry"); - + ARDOUR_UI::instance()->tooltips().set_tip(start_set_button, _("Set value to Playhead")); + ARDOUR_UI::instance()->tooltips().set_tip(end_set_button, _("Set value to Playhead")); + isrc_label.set_text ("ISRC: "); isrc_label.set_size_request (30, -1); performer_label.set_text ("Performer: "); @@ -131,6 +133,7 @@ LocationEditRow::LocationEditRow(Session * sess, Location * loc, int32_t num) start_set_button.signal_clicked().connect(bind (mem_fun (*this, &LocationEditRow::set_button_pressed), LocStart)); start_go_button.signal_clicked().connect(bind (mem_fun (*this, &LocationEditRow::go_button_pressed), LocStart)); start_clock.ValueChanged.connect (bind (mem_fun (*this, &LocationEditRow::clock_changed), LocStart)); + start_clock.ChangeAborted.connect (bind (mem_fun (*this, &LocationEditRow::change_aborted), LocStart)); end_hbox.pack_start (end_go_button, false, false); @@ -142,9 +145,11 @@ LocationEditRow::LocationEditRow(Session * sess, Location * loc, int32_t num) end_set_button.signal_clicked().connect(bind (mem_fun (*this, &LocationEditRow::set_button_pressed), LocEnd)); end_go_button.signal_clicked().connect(bind (mem_fun (*this, &LocationEditRow::go_button_pressed), LocEnd)); end_clock.ValueChanged.connect (bind (mem_fun (*this, &LocationEditRow::clock_changed), LocEnd)); + end_clock.ChangeAborted.connect (bind (mem_fun (*this, &LocationEditRow::change_aborted), LocEnd)); // item_table.attach (length_clock, 3, 4, 0, 1, 0, 0, 4, 0); length_clock.ValueChanged.connect (bind ( mem_fun(*this, &LocationEditRow::clock_changed), LocLength)); + length_clock.ChangeAborted.connect (bind (mem_fun (*this, &LocationEditRow::change_aborted), LocLength)); // item_table.attach (cd_check_button, 4, 5, 0, 1, 0, Gtk::FILL, 4, 0); // item_table.attach (hide_check_button, 5, 6, 0, 1, 0, Gtk::FILL, 4, 0); @@ -414,6 +419,14 @@ LocationEditRow::clock_changed (LocationPart part) } +void +LocationEditRow::change_aborted (LocationPart part) +{ + if (i_am_the_modifier || !location) return; + + set_location(location); +} + void LocationEditRow::cd_toggled () { @@ -600,6 +613,12 @@ LocationEditRow::flags_changed (ARDOUR::Location *loc, void *src) i_am_the_modifier--; } +void +LocationEditRow::focus_name() { + name_entry.grab_focus(); +} + + LocationUI::LocationUI () : ArdourDialog ("locations dialog"), add_location_button (_("Add New Location")), @@ -628,6 +647,8 @@ LocationUI::LocationUI () location_rows_scroller.set_name ("LocationLocRowsScroller"); location_rows_scroller.set_policy (Gtk::POLICY_NEVER, Gtk::POLICY_AUTOMATIC); location_rows_scroller.set_size_request (-1, 130); + + newest_location = 0; loc_frame_box.set_spacing (5); loc_frame_box.set_border_width (5); @@ -789,6 +810,10 @@ LocationUI::map_locations (Locations::LocationList& locations) erow->remove_requested.connect (mem_fun(*this, &LocationUI::location_remove_requested)); erow->redraw_ranges.connect (mem_fun(*this, &LocationUI::location_redraw_ranges)); loc_children.push_back(Box_Helpers::Element(*erow, PACK_SHRINK, 1, PACK_START)); + if (location == newest_location) { + newest_location = 0; + erow->focus_name(); + } } else if (location->is_auto_punch()) { punch_edit_row.set_session (session); @@ -820,6 +845,9 @@ LocationUI::add_new_location() nframes_t where = session->audible_frame(); session->locations()->next_available_name(markername,"mark"); Location *location = new Location (where, where, markername, Location::IsMark); + if (Config->get_name_new_markers()) { + newest_location = location; + } session->begin_reversible_command (_("add marker")); XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); diff --git a/gtk2_ardour/location_ui.h b/gtk2_ardour/location_ui.h index de435b999f..3c32f02025 100644 --- a/gtk2_ardour/location_ui.h +++ b/gtk2_ardour/location_ui.h @@ -50,6 +50,7 @@ class LocationEditRow : public Gtk::HBox void set_session (ARDOUR::Session *); void set_number (int); + void focus_name(); sigc::signal remove_requested; sigc::signal redraw_ranges; @@ -114,6 +115,7 @@ class LocationEditRow : public Gtk::HBox void go_button_pressed (LocationPart part); void clock_changed (LocationPart part); + void change_aborted (LocationPart part); void cd_toggled (); void hide_toggled (); @@ -149,6 +151,7 @@ class LocationUI : public ArdourDialog private: ARDOUR::LocationStack* locations; + ARDOUR::Location *newest_location; void session_gone(); diff --git a/gtk2_ardour/main.cc b/gtk2_ardour/main.cc index dd4bcab919..abbf216eea 100644 --- a/gtk2_ardour/main.cc +++ b/gtk2_ardour/main.cc @@ -205,6 +205,13 @@ fixup_bundle_environment () actually exists ... */ + try { + sys::create_directories (user_config_directory ()); + } + catch (const sys::filesystem_error& ex) { + error << _("Could not create user configuration directory") << endmsg; + } + sys::path pangopath = user_config_directory(); pangopath /= "pango.rc"; path = pangopath.to_string(); @@ -212,6 +219,7 @@ fixup_bundle_environment () std::ofstream pangorc (path.c_str()); if (!pangorc) { error << string_compose (_("cannot open pango.rc file %1") , path) << endmsg; + return; } else { pangorc << "[Pango]\nModuleFiles="; @@ -221,6 +229,7 @@ fixup_bundle_environment () pangopath /= "pango.modules"; pangorc << pangopath.to_string() << endl; + pangorc.close (); setenv ("PANGO_RC_FILE", path.c_str(), 1); diff --git a/gtk2_ardour/marker.cc b/gtk2_ardour/marker.cc index dd5a70bb7d..edfec8a600 100644 --- a/gtk2_ardour/marker.cc +++ b/gtk2_ardour/marker.cc @@ -247,8 +247,8 @@ Marker::Marker (PublicEditor& ed, ArdourCanvas::Group& parent, guint32 rgba, con Pango::FontDescription* font = get_font_for_style (N_("MarkerText")); text = new Text (*group); - text->property_text() = annotation.c_str(); text->property_font_desc() = *font; + text->property_text() = annotation.c_str(); delete font; diff --git a/gtk2_ardour/marker_time_axis.cc b/gtk2_ardour/marker_time_axis.cc index e10967d01a..df041f8f76 100644 --- a/gtk2_ardour/marker_time_axis.cc +++ b/gtk2_ardour/marker_time_axis.cc @@ -82,7 +82,7 @@ MarkerTimeAxis::MarkerTimeAxis (PublicEditor& ed, ARDOUR::Session& sess, Canvas& label_view() ; // set the initial height of this time axis - set_height(Small) ; + set_height(hSmall) ; } /** @@ -106,13 +106,8 @@ MarkerTimeAxis::~MarkerTimeAxis() //---------------------------------------------------------------------------------------// // ui methods & data -/** - * Sets the height of this TrackView to one of the defined TrackHeights - * - * @param h the TrackHeight value to set - */ void -MarkerTimeAxis::set_height (TrackHeight h) +MarkerTimeAxis::set_height (uint32_t h) { VisualTimeAxis::set_height(h) ; diff --git a/gtk2_ardour/marker_time_axis.h b/gtk2_ardour/marker_time_axis.h index 13288ce66f..56856d3bd3 100644 --- a/gtk2_ardour/marker_time_axis.h +++ b/gtk2_ardour/marker_time_axis.h @@ -80,9 +80,9 @@ class MarkerTimeAxis : public VisualTimeAxis /** * Sets the height of this TrackView to one of the defined TrackHeights * - * @param h the TrackHeight value to set + * @param h the number of pixels to set the height to */ - virtual void set_height(TimeAxisView::TrackHeight h) ; + virtual void set_height(uint32_t h) ; /** * Sets the number of samples per unit that are used. diff --git a/gtk2_ardour/midi_region_view.cc b/gtk2_ardour/midi_region_view.cc index b38067bfbf..2f414405a0 100644 --- a/gtk2_ardour/midi_region_view.cc +++ b/gtk2_ardour/midi_region_view.cc @@ -78,7 +78,7 @@ MidiRegionView::MidiRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView & } MidiRegionView::MidiRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView &tv, boost::shared_ptr r, double spu, Gdk::Color& basic_color, TimeAxisViewItem::Visibility visibility) - : RegionView (parent, tv, r, spu, basic_color, visibility) + : RegionView (parent, tv, r, spu, basic_color, false, visibility) , _force_channel(-1) , _last_channel_selection(0xFFFF) , _default_note_length(0.0) @@ -112,7 +112,7 @@ MidiRegionView::init (Gdk::Color& basic_color, bool wfd) reset_width_dependent_items ((double) _region->length() / samples_per_unit); - set_y_position_and_height (0, trackview.height); + set_y_position_and_height (0, trackview.current_height()); region_muted (); region_resized (BoundsChanged); @@ -148,7 +148,7 @@ MidiRegionView::canvas_event(GdkEvent* ev) static double drag_start_x, drag_start_y; static double last_x, last_y; double event_x, event_y; - nframes_t event_frame = 0; + nframes64_t event_frame = 0; static ArdourCanvas::SimpleRect* drag_rect = NULL; @@ -381,7 +381,7 @@ MidiRegionView::create_note_at(double x, double y, double duration) assert(note >= 0.0); assert(note <= 127.0); - nframes_t new_note_time = trackview.editor.pixel_to_frame (x); + nframes64_t new_note_time = trackview.editor.pixel_to_frame (x); assert(new_note_time >= 0); new_note_time += _region->start(); @@ -391,14 +391,14 @@ MidiRegionView::create_note_at(double x, double y, double duration) double duration = m.frames_per_bar(t, trackview.session().frame_rate()) / m.beats_per_bar(); */ - // we need to snap here again in nframes_t in order to be sample accurate + // we need to snap here again in nframes64_t in order to be sample accurate // since note time is region-absolute but snap_to_frame expects position-relative // time we have to coordinate transform back and forth here. - nframes_t new_note_time_position_relative = new_note_time - _region->start(); + nframes64_t new_note_time_position_relative = new_note_time - _region->start(); new_note_time = snap_to_frame(new_note_time_position_relative) + _region->start(); // we need to snap the duration too to be sample accurate - nframes_t new_note_duration = nframes_t(duration); + nframes64_t new_note_duration = nframes_t(duration); new_note_duration = snap_to_frame(new_note_time_position_relative + new_note_duration) + _region->start() - new_note_time; @@ -648,7 +648,7 @@ MidiRegionView::set_y_position_and_height (double y, double h) note->property_y2() = y2; } if (CanvasHit* hit = dynamic_cast(event)) { - double x = trackview.editor.frame_to_pixel((nframes_t) + double x = trackview.editor.frame_to_pixel((nframes64_t) event->note()->time() - _region->start()); const double diamond_size = midi_stream_view()->note_height() / 2.0; double y = midi_stream_view()->note_to_y(event->note()->note()) @@ -744,7 +744,7 @@ MidiRegionView::resolve_note(uint8_t note, double end_time) return; if (_active_notes && _active_notes[note]) { - _active_notes[note]->property_x2() = trackview.editor.frame_to_pixel((nframes_t)end_time); + _active_notes[note]->property_x2() = trackview.editor.frame_to_pixel((nframes64_t)end_time); _active_notes[note]->property_outline_what() = (guint32) 0xF; // all edges _active_notes[note] = NULL; } @@ -792,13 +792,13 @@ MidiRegionView::add_note(const boost::shared_ptr note) CanvasNoteEvent* event = 0; - const double x = trackview.editor.frame_to_pixel((nframes_t)note->time() - _region->start()); + const double x = trackview.editor.frame_to_pixel((nframes64_t)note->time() - _region->start()); if (midi_view()->note_mode() == Sustained) { const double y1 = midi_stream_view()->note_to_y(note->note()); const double note_endpixel = - trackview.editor.frame_to_pixel((nframes_t)note->end_time() - _region->start()); + trackview.editor.frame_to_pixel((nframes64_t)note->end_time() - _region->start()); CanvasNote* ev_rect = new CanvasNote(*this, *group, note); ev_rect->property_x1() = x; @@ -880,7 +880,7 @@ MidiRegionView::add_pgm_change(boost::shared_ptr event) return; ArdourCanvas::Group* const group = (ArdourCanvas::Group*)get_canvas_group(); - const double x = trackview.editor.frame_to_pixel((nframes_t)event->time() - _region->start()); + const double x = trackview.editor.frame_to_pixel((nframes64_t)event->time() - _region->start()); double height = midi_stream_view()->contents_height(); _pgm_changes.push_back( @@ -1064,7 +1064,7 @@ MidiRegionView::note_dropped(CanvasNoteEvent* ev, double dt, uint8_t dnote) const boost::shared_ptr copy(new Note(*(*i)->note().get())); - // we need to snap here again in nframes_t in order to be sample accurate + // we need to snap here again in nframes64_t in order to be sample accurate double new_note_time = (*i)->note()->time(); new_note_time += dt; @@ -1075,7 +1075,7 @@ MidiRegionView::note_dropped(CanvasNoteEvent* ev, double dt, uint8_t dnote) // since note time is region-absolute but snap_to_frame expects position-relative // time we have to coordinate transform back and forth here. - new_note_time = snap_to_frame(nframes_t(new_note_time) - _region->start()) + _region->start(); + new_note_time = snap_to_frame(nframes64_t(new_note_time) - _region->start()) + _region->start(); copy->set_time(new_note_time); @@ -1111,26 +1111,26 @@ MidiRegionView::note_dropped(CanvasNoteEvent* ev, double dt, uint8_t dnote) } } -nframes_t +nframes64_t MidiRegionView::snap_to_frame(double x) { PublicEditor &editor = trackview.editor; // x is region relative // convert x to global frame - nframes_t frame = editor.pixel_to_frame(x) + _region->position(); + nframes64_t frame = editor.pixel_to_frame(x) + _region->position(); editor.snap_to(frame); // convert event_frame back to local coordinates relative to position frame -= _region->position(); return frame; } -nframes_t -MidiRegionView::snap_to_frame(nframes_t x) +nframes64_t +MidiRegionView::snap_to_frame(nframes64_t x) { PublicEditor &editor = trackview.editor; // x is region relative // convert x to global frame - nframes_t frame = x + _region->position(); + nframes64_t frame = x + _region->position(); editor.snap_to(frame); // convert event_frame back to local coordinates relative to position frame -= _region->position(); @@ -1146,7 +1146,7 @@ MidiRegionView::snap_to_pixel(double x) double MidiRegionView::get_position_pixels(void) { - nframes_t region_frame = get_position(); + nframes64_t region_frame = get_position(); return trackview.editor.frame_to_pixel(region_frame); } @@ -1250,7 +1250,7 @@ MidiRegionView::commit_resizing(CanvasNote::NoteEnd note_end, double event_x, bo // because snapping works on world coordinates we have to transform current_x // to world coordinates before snapping and transform it back afterwards - nframes_t current_frame = snap_to_frame(current_x); + nframes64_t current_frame = snap_to_frame(current_x); // transform to region start relative current_frame += _region->start(); diff --git a/gtk2_ardour/midi_region_view.h b/gtk2_ardour/midi_region_view.h index c2475f00fa..50cac66d77 100644 --- a/gtk2_ardour/midi_region_view.h +++ b/gtk2_ardour/midi_region_view.h @@ -164,7 +164,7 @@ class MidiRegionView : public RegionView /** * This function provides the snap function for region position relative coordinates - * for pixel units (double) instead of nframes_t + * for pixel units (double) instead of nframes64_t * @param x a pixel coordinate relative to region start * @return the snapped pixel coordinate relative to region start */ @@ -172,18 +172,18 @@ class MidiRegionView : public RegionView /** * This function provides the snap function for region position relative coordinates - * for pixel units (double) instead of nframes_t + * for pixel units (double) instead of nframes64_t * @param x a pixel coordinate relative to region start - * @return the snapped nframes_t coordinate relative to region start + * @return the snapped nframes64_t coordinate relative to region start */ - nframes_t snap_to_frame(double x); + nframes64_t snap_to_frame(double x); /** * This function provides the snap function for region position relative coordinates * @param x a pixel coordinate relative to region start - * @return the snapped nframes_t coordinate relative to region start + * @return the snapped nframes64_t coordinate relative to region start */ - nframes_t snap_to_frame(nframes_t x); + nframes64_t snap_to_frame(nframes64_t x); protected: diff --git a/gtk2_ardour/midi_streamview.cc b/gtk2_ardour/midi_streamview.cc index de14f302e5..5b162dc510 100644 --- a/gtk2_ardour/midi_streamview.cc +++ b/gtk2_ardour/midi_streamview.cc @@ -93,7 +93,7 @@ MidiStreamView::~MidiStreamView () RegionView* -MidiStreamView::add_region_view_internal (boost::shared_ptr r, bool wfd) +MidiStreamView::add_region_view_internal (boost::shared_ptr r, bool wfd, bool recording) { boost::shared_ptr region = boost::dynamic_pointer_cast (r); @@ -384,7 +384,7 @@ MidiStreamView::setup_rec_box () rec_rect->property_x1() = xstart; rec_rect->property_y1() = 1.0; rec_rect->property_x2() = xend; - rec_rect->property_y2() = (double) _trackview.height - 1; + rec_rect->property_y2() = (double) _trackview.current_height() - 1; rec_rect->property_outline_color_rgba() = ARDOUR_UI::config()->canvasvar_RecordingRect.get(); rec_rect->property_fill_color_rgba() = fill_color; rec_rect->lower_to_bottom(); diff --git a/gtk2_ardour/midi_streamview.h b/gtk2_ardour/midi_streamview.h index 60dde8cc85..1caad34819 100644 --- a/gtk2_ardour/midi_streamview.h +++ b/gtk2_ardour/midi_streamview.h @@ -81,7 +81,7 @@ class MidiStreamView : public StreamView void redisplay_diskstream (); inline double contents_height() const - { return (_trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE - 2); } + { return (_trackview.current_height() - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE - 2); } inline double note_to_y(uint8_t note) const { return contents_height() @@ -105,7 +105,7 @@ class MidiStreamView : public StreamView void rec_data_range_ready (jack_nframes_t start, jack_nframes_t dur, boost::weak_ptr src); void update_rec_regions (boost::shared_ptr data, jack_nframes_t start, jack_nframes_t dur); - RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_waves); + RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_waves, bool recording = false); void display_region(MidiRegionView* region_view, bool load_model); void display_diskstream (boost::shared_ptr ds); diff --git a/gtk2_ardour/midi_time_axis.cc b/gtk2_ardour/midi_time_axis.cc index f6d2993cfe..5802cc7e20 100644 --- a/gtk2_ardour/midi_time_axis.cc +++ b/gtk2_ardour/midi_time_axis.cc @@ -396,15 +396,19 @@ MidiTimeAxisView::route_active_changed () void MidiTimeAxisView::channel_selector_toggled() { - static TimeAxisView::TrackHeight previous_height; + static uint32_t previous_height; if(_midi_expander.property_expanded()) { - previous_height = height_style; - if(previous_height != TimeAxisView::Largest) { - set_height(TimeAxisView::Large); + + previous_height = current_height(); + + if (previous_height < TimeAxisView::hLargest) { + set_height (TimeAxisView::hLarge); } + } else { - set_height(previous_height); + + set_height (previous_height); } } diff --git a/gtk2_ardour/mixer_strip.cc b/gtk2_ardour/mixer_strip.cc index dff81bc5b6..c98f4c5a0f 100644 --- a/gtk2_ardour/mixer_strip.cc +++ b/gtk2_ardour/mixer_strip.cc @@ -682,7 +682,7 @@ MixerStrip::add_bundle_to_input_menu (boost::shared_ptr b, std::vectornchannels() == _route->n_inputs().n_total()) { + if (b->nchannels() == _route->n_inputs()) { citems.push_back (CheckMenuElem (b->name(), bind (mem_fun(*this, &MixerStrip::bundle_input_chosen), b))); @@ -705,7 +705,7 @@ MixerStrip::add_bundle_to_output_menu (boost::shared_ptr b, std::vector< return; } - if (b->nchannels() == _route->n_outputs().n_total()) { + if (b->nchannels() == _route->n_outputs()) { MenuList& citems = output_menu.items(); citems.push_back (CheckMenuElem (b->name(), bind (mem_fun(*this, &MixerStrip::bundle_output_chosen), b))); @@ -1208,7 +1208,6 @@ MixerStrip::map_frozen () break; } } - hide_redirect_editors (); } @@ -1303,6 +1302,8 @@ MixerStrip::meter_changed (void *src) } gpm.setup_meters (); + // reset peak when meter point changes + gpm.reset_peak_display(); set_width(_width, this); } diff --git a/gtk2_ardour/mixer_ui.cc b/gtk2_ardour/mixer_ui.cc index 6754581b43..b2f8ece64e 100644 --- a/gtk2_ardour/mixer_ui.cc +++ b/gtk2_ardour/mixer_ui.cc @@ -221,7 +221,7 @@ Mixer_UI::Mixer_UI () signal_configure_event().connect (mem_fun (*ARDOUR_UI::instance(), &ARDOUR_UI::configure_handler)); _selection.RoutesChanged.connect (mem_fun(*this, &Mixer_UI::follow_strip_selection)); - + mix_group_display_button_box->show(); mix_group_add_button->show(); mix_group_remove_button->show(); @@ -797,34 +797,33 @@ Mixer_UI::auto_rebind_midi_controls () pos++; } - PBD::Controllable::CreateBinding ( strip->solo_button->get_controllable(), controlValue, 0); - PBD::Controllable::CreateBinding ( strip->mute_button->get_controllable(), controlValue, 1); + PBD::Controllable::CreateBinding ( strip->solo_button->get_controllable().get(), controlValue, 0); + PBD::Controllable::CreateBinding ( strip->mute_button->get_controllable().get(), controlValue, 1); if( strip->is_audio_track() ) { - PBD::Controllable::CreateBinding ( strip->rec_enable_button->get_controllable(), controlValue, 2); + PBD::Controllable::CreateBinding ( strip->rec_enable_button->get_controllable().get(), controlValue, 2); } - PBD::Controllable::CreateBinding ( strip->gpm.get_controllable(), controlValue, 3); - PBD::Controllable::CreateBinding ( strip->panners.get_controllable(), controlValue, 4); + PBD::Controllable::CreateBinding ( strip->gpm.get_controllable().get(), controlValue, 3); + PBD::Controllable::CreateBinding ( strip->panners.get_controllable().get(), controlValue, 4); } else { // Remove any existing binding - PBD::Controllable::DeleteBinding ( strip->solo_button->get_controllable() ); - PBD::Controllable::DeleteBinding ( strip->mute_button->get_controllable() ); + PBD::Controllable::DeleteBinding ( strip->solo_button->get_controllable().get() ); + PBD::Controllable::DeleteBinding ( strip->mute_button->get_controllable().get() ); if( strip->is_audio_track() ) { - PBD::Controllable::DeleteBinding ( strip->rec_enable_button->get_controllable() ); + PBD::Controllable::DeleteBinding ( strip->rec_enable_button->get_controllable().get() ); } - PBD::Controllable::DeleteBinding ( strip->gpm.get_controllable() ); - PBD::Controllable::DeleteBinding ( strip->panners.get_controllable() ); // This only takes the first panner if there are multiples... + PBD::Controllable::DeleteBinding ( strip->gpm.get_controllable().get() ); + PBD::Controllable::DeleteBinding ( strip->panners.get_controllable().get() ); // This only takes the first panner if there are multiples... } } // for } - struct SignalOrderRouteSorter { bool operator() (boost::shared_ptr a, boost::shared_ptr b) { /* use of ">" forces the correct sort order */ diff --git a/gtk2_ardour/mnemonic-us.bindings.in b/gtk2_ardour/mnemonic-us.bindings.in index 2eafa6e0ad..6326c868f9 100644 --- a/gtk2_ardour/mnemonic-us.bindings.in +++ b/gtk2_ardour/mnemonic-us.bindings.in @@ -79,7 +79,8 @@ (gtk_accel_path "/Common/Save" "<%PRIMARY%>s") (gtk_accel_path "/Editor/duplicate-region" "d") (gtk_accel_path "/Editor/select-all-in-punch-range" "<%PRIMARY%>d") -(gtk_accel_path "/Editor/toggle-follow-playhead" "f") +(gtk_accel_path "/Editor/fit-tracks" "f") +(gtk_accel_path "/Editor/toggle-follow-playhead" "<%PRIMARY%>f") (gtk_accel_path "/Editor/toggle-rhythm-ferret" "<%WINDOW%>f") (gtk_accel_path "/MouseMode/set-mouse-mode-gain" "g") (gtk_accel_path "/Editor/play-selected-regions" "h") @@ -92,11 +93,20 @@ ;; HOME ROW +<<<<<<< .working (gtk_accel_path "/Editor/zoom-to-region" "<%SECONDARY%>z") +======= +(gtk_accel_path "/Editor/zoom-to-region" "<%PRIMARY%><%SECONDARY%>z") +(gtk_accel_path "/Editor/zoom-to-region-both-axes" "<%SECONDARY%>z") +>>>>>>> .merge-right.r3622 (gtk_accel_path "/Editor/undo" "<%PRIMARY%>z") (gtk_accel_path "/Editor/toggle-zoom" "<%TERTIARY%>z") +<<<<<<< .working (gtk_accel_path "/MouseMode/set-mouse-mode-zoom" "z") (gtk_accel_path "/MouseMode/set-mouse-mode-note" "n") +======= +(gtk_accel_path "/MouseMode/set-mouse-mode-zoom" "z") +>>>>>>> .merge-right.r3622 (gtk_accel_path "/Editor/editor-cut" "<%PRIMARY%>x") (gtk_accel_path "/Editor/editor-copy" "<%PRIMARY%>c") (gtk_accel_path "/Common/ToggleColorManager" "<%WINDOW%>c") @@ -178,6 +188,33 @@ (gtk_accel_path "/Editor/select-range-between-cursors" "F6") (gtk_accel_path "/Common/ToggleMaximalEditor" "F11") +(gtk_accel_path "/Editor/save-visual-state-1" "<%PRIMARY%>F1") +(gtk_accel_path "/Editor/save-visual-state-2" "<%PRIMARY%>F2") +(gtk_accel_path "/Editor/save-visual-state-3" "<%PRIMARY%>F3") +(gtk_accel_path "/Editor/save-visual-state-4" "<%PRIMARY%>F4") +(gtk_accel_path "/Editor/save-visual-state-5" "<%PRIMARY%>F5") +(gtk_accel_path "/Editor/save-visual-state-6" "<%PRIMARY%>F6") +(gtk_accel_path "/Editor/save-visual-state-7" "<%PRIMARY%>F7") +(gtk_accel_path "/Editor/save-visual-state-8" "<%PRIMARY%>F8") +(gtk_accel_path "/Editor/save-visual-state-9" "<%PRIMARY%>F9") +(gtk_accel_path "/Editor/save-visual-state-10" "<%PRIMARY%>F10") +(gtk_accel_path "/Editor/save-visual-state-11" "<%PRIMARY%>F11") +(gtk_accel_path "/Editor/save-visual-state-12" "<%PRIMARY%>F12") + +(gtk_accel_path "/Editor/goto-visual-state-1" "<%PRIMARY%>F1") +(gtk_accel_path "/Editor/goto-visual-state-2" "<%PRIMARY%>F2") +(gtk_accel_path "/Editor/goto-visual-state-3" "<%PRIMARY%>F3") +(gtk_accel_path "/Editor/goto-visual-state-4" "<%PRIMARY%>F4") +(gtk_accel_path "/Editor/goto-visual-state-5" "<%PRIMARY%>F5") +(gtk_accel_path "/Editor/goto-visual-state-6" "<%PRIMARY%>F6") +(gtk_accel_path "/Editor/goto-visual-state-7" "<%PRIMARY%>F7") +(gtk_accel_path "/Editor/goto-visual-state-8" "<%PRIMARY%>F8") +(gtk_accel_path "/Editor/goto-visual-state-9" "<%PRIMARY%>F9") +(gtk_accel_path "/Editor/goto-visual-state-10" "<%PRIMARY%>F10") +(gtk_accel_path "/Editor/goto-visual-state-11" "<%PRIMARY%>F11") +(gtk_accel_path "/Editor/goto-visual-state-12" "<%PRIMARY%>F12") + + ;; numbers (gtk_accel_path "/Editor/toggle-edit-mode" "1") diff --git a/gtk2_ardour/option_editor.cc b/gtk2_ardour/option_editor.cc index 2dfa63080d..9ddf9999b9 100644 --- a/gtk2_ardour/option_editor.cc +++ b/gtk2_ardour/option_editor.cc @@ -113,6 +113,7 @@ OptionEditor::OptionEditor (ARDOUR_UI& uip, PublicEditor& ed, Mixer_UI& mixui) { using namespace Notebook_Helpers; + first_click_setup = true; click_io_selector = 0; auditioner_io_selector = 0; session = 0; @@ -1036,8 +1037,8 @@ void OptionEditor::clear_click_editor () { if (click_io_selector) { - click_packer.remove (*click_io_selector); - click_packer.remove (*click_gpm); + click_hpacker.remove (*click_io_selector); + click_hpacker.remove (*click_gpm); delete click_io_selector; delete click_gpm; click_io_selector = 0; @@ -1049,31 +1050,59 @@ void OptionEditor::setup_click_editor () { Label* label; - HBox* hpacker = manage (new HBox); + + if (first_click_setup) { + + click_path_entry.set_name ("OptionsEntry"); + click_emphasis_path_entry.set_name ("OptionsEntry"); + + click_path_entry.signal_activate().connect (mem_fun(*this, &OptionEditor::click_sound_changed)); + click_emphasis_path_entry.signal_activate().connect (mem_fun(*this, &OptionEditor::click_emphasis_sound_changed)); + + click_path_entry.signal_focus_out_event().connect (bind (mem_fun(*this, &OptionEditor::focus_out_event_handler), &OptionEditor::click_sound_changed)); + click_emphasis_path_entry.signal_focus_out_event().connect (bind (mem_fun(*this, &OptionEditor::focus_out_event_handler), &OptionEditor::click_emphasis_sound_changed)); + + click_browse_button.set_name ("EditorGTKButton"); + click_emphasis_browse_button.set_name ("EditorGTKButton"); + + click_browse_button.signal_clicked().connect (mem_fun(*this, &OptionEditor::click_browse_clicked)); + click_emphasis_browse_button.signal_clicked().connect (mem_fun(*this, &OptionEditor::click_emphasis_browse_clicked)); + + click_packer.set_border_width (12); + click_packer.set_spacing (5); + + click_table.set_col_spacings (10); + + label = manage(new Label(_("Click audio file"))); + label->set_name ("OptionsLabel"); + click_table.attach (*label, 0, 1, 0, 1, FILL|EXPAND, FILL); + click_table.attach (click_path_entry, 1, 2, 0, 1, Gtk::FILL|Gtk::EXPAND, FILL); + click_table.attach (click_browse_button, 2, 3, 0, 1, FILL|EXPAND, FILL); + + label = manage(new Label(_("Click emphasis audiofile"))); + label->set_name ("OptionsLabel"); + click_table.attach (*label, 0, 1, 1, 2, FILL|EXPAND, FILL); + click_table.attach (click_emphasis_path_entry, 1, 2, 1, 2, Gtk::FILL|Gtk::EXPAND, FILL); + click_table.attach (click_emphasis_browse_button, 2, 3, 1, 2, FILL|EXPAND, FILL); + + click_packer.pack_start (click_table, false, false); + click_packer.pack_start (click_hpacker, false, false); + + + click_hpacker.set_spacing (10); + + first_click_setup = false; + } click_path_entry.set_sensitive (true); click_emphasis_path_entry.set_sensitive (true); - click_path_entry.set_name ("OptionsEntry"); - click_emphasis_path_entry.set_name ("OptionsEntry"); - - click_path_entry.signal_activate().connect (mem_fun(*this, &OptionEditor::click_sound_changed)); - click_emphasis_path_entry.signal_activate().connect (mem_fun(*this, &OptionEditor::click_emphasis_sound_changed)); - - click_path_entry.signal_focus_out_event().connect (bind (mem_fun(*this, &OptionEditor::focus_out_event_handler), &OptionEditor::click_sound_changed)); - click_emphasis_path_entry.signal_focus_out_event().connect (bind (mem_fun(*this, &OptionEditor::focus_out_event_handler), &OptionEditor::click_emphasis_sound_changed)); - - click_browse_button.set_name ("EditorGTKButton"); - click_emphasis_browse_button.set_name ("EditorGTKButton"); - click_browse_button.signal_clicked().connect (mem_fun(*this, &OptionEditor::click_browse_clicked)); - click_emphasis_browse_button.signal_clicked().connect (mem_fun(*this, &OptionEditor::click_emphasis_browse_clicked)); - - click_packer.set_border_width (12); - click_packer.set_spacing (5); - click_io_selector = new IOSelector (*session, session->click_io(), false); click_gpm = new GainMeter (session->click_io(), *session); + click_hpacker.pack_start (*click_io_selector, false, false); + click_hpacker.pack_start (*click_gpm, false, false); + click_table.set_col_spacings (10); label = manage(new Label(_("Click audio file"))); @@ -1088,13 +1117,6 @@ OptionEditor::setup_click_editor () click_table.attach (click_emphasis_path_entry, 1, 2, 1, 2, Gtk::FILL|Gtk::EXPAND, FILL); click_table.attach (click_emphasis_browse_button, 2, 3, 1, 2, FILL|EXPAND, FILL); - hpacker->set_spacing (10); - hpacker->pack_start (*click_io_selector, false, false); - hpacker->pack_start (*click_gpm, false, false); - - click_packer.pack_start (click_table, false, false); - click_packer.pack_start (*hpacker, false, false); - click_packer.show_all (); } diff --git a/gtk2_ardour/option_editor.h b/gtk2_ardour/option_editor.h index c6f13049b0..bb12698041 100644 --- a/gtk2_ardour/option_editor.h +++ b/gtk2_ardour/option_editor.h @@ -173,6 +173,8 @@ class OptionEditor : public ArdourDialog IOSelector* click_io_selector; GainMeter* click_gpm; PannerUI* click_panner; + bool first_click_setup; + Gtk::HBox click_hpacker; Gtk::VBox click_packer; Gtk::Table click_table; Gtk::Entry click_path_entry; diff --git a/gtk2_ardour/panner.cc b/gtk2_ardour/panner.cc index 2607cdf2b8..975f1e6b3b 100644 --- a/gtk2_ardour/panner.cc +++ b/gtk2_ardour/panner.cc @@ -35,7 +35,7 @@ null_label_callback (char* buf, unsigned int bufsize) PannerBar::PannerBar (Gtk::Adjustment& adj, boost::shared_ptr c) - : BarController (adj, *c.get(), sigc::ptr_fun (null_label_callback)) + : BarController (adj, c, sigc::ptr_fun (null_label_callback)) { set_style (BarController::Line); } diff --git a/gtk2_ardour/panner2d.cc b/gtk2_ardour/panner2d.cc index a1f99c40d4..6fa64be8e6 100644 --- a/gtk2_ardour/panner2d.cc +++ b/gtk2_ardour/panner2d.cc @@ -19,7 +19,7 @@ #include #include -#include +#include #include #include diff --git a/gtk2_ardour/panner_ui.cc b/gtk2_ardour/panner_ui.cc index d4f0d9eeca..3fe43850a3 100644 --- a/gtk2_ardour/panner_ui.cc +++ b/gtk2_ardour/panner_ui.cc @@ -166,7 +166,7 @@ PannerUI::PannerUI (boost::shared_ptr io, Session& s) show(); } -PBD::Controllable* +boost::shared_ptr PannerUI::get_controllable() { return pan_bars[0]->get_controllable(); diff --git a/gtk2_ardour/panner_ui.h b/gtk2_ardour/panner_ui.h index 093800387d..e10080a317 100644 --- a/gtk2_ardour/panner_ui.h +++ b/gtk2_ardour/panner_ui.h @@ -68,7 +68,7 @@ class PannerUI : public Gtk::HBox void effective_pan_display (); void set_meter_strip_name (string name); - PBD::Controllable* get_controllable(); + boost::shared_ptr get_controllable(); private: friend class MixerStrip; diff --git a/gtk2_ardour/plugin_interest.h b/gtk2_ardour/plugin_interest.h new file mode 100644 index 0000000000..1b7d3c0959 --- /dev/null +++ b/gtk2_ardour/plugin_interest.h @@ -0,0 +1,36 @@ +/* + Copyright (C) 2008 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 __gtkardour_plugin_interest_h__ +#define __gtkardour_plugin_interest_h__ + +#include +#include + +typedef std::vector SelectedPlugins; + +class PluginInterestedObject { + public: + PluginInterestedObject() {} + virtual ~PluginInterestedObject() {} + + virtual void use_plugins (const SelectedPlugins&) = 0; +}; + +#endif /* __gtkardour_plugin_interest_h__ */ diff --git a/gtk2_ardour/plugin_selector.cc b/gtk2_ardour/plugin_selector.cc index aa269be577..87d5532d34 100644 --- a/gtk2_ardour/plugin_selector.cc +++ b/gtk2_ardour/plugin_selector.cc @@ -19,6 +19,7 @@ #include #include +#include #include @@ -51,6 +52,7 @@ static const char* _filter_mode_strings[] = { N_("Type contains"), N_("Author contains"), N_("Library contains"), + N_("Favorites only"), 0 }; @@ -64,9 +66,15 @@ PluginSelector::PluginSelector (PluginManager *mgr) manager = mgr; session = 0; - + _menu = 0; + in_row_change = false; + plugin_model = Gtk::ListStore::create (plugin_columns); plugin_display.set_model (plugin_model); + /* XXX translators: try to convert "Fav" into a short term + related to "favorite" + */ + plugin_display.append_column (_("Fav"), plugin_columns.favorite); plugin_display.append_column (_("Available Plugins"), plugin_columns.name); plugin_display.append_column (_("Type"), plugin_columns.type_name); plugin_display.append_column (_("Category"), plugin_columns.category); @@ -78,6 +86,13 @@ PluginSelector::PluginSelector (PluginManager *mgr) plugin_display.set_headers_visible (true); plugin_display.set_headers_clickable (true); plugin_display.set_reorderable (false); + plugin_display.set_rules_hint (true); + + CellRendererToggle* fav_cell = dynamic_cast(plugin_display.get_column_cell_renderer (0)); + fav_cell->property_activatable() = true; + fav_cell->property_radio() = false; + fav_cell->signal_toggled().connect (mem_fun (*this, &PluginSelector::favorite_changed)); + scroller.set_border_width(10); scroller.set_policy(Gtk::POLICY_AUTOMATIC, Gtk::POLICY_AUTOMATIC); scroller.add(plugin_display); @@ -187,6 +202,10 @@ PluginSelector::show_this_plugin (const PluginInfoPtr& info, const std::string& std::string compstr; std::string mode = filter_mode.get_active_text (); + if (mode == _("Favorites only")) { + return manager->is_a_favorite_plugin (info); + } + if (!filterstr.empty()) { if (mode == _("Name contains")) { @@ -197,8 +216,8 @@ PluginSelector::show_this_plugin (const PluginInfoPtr& info, const std::string& compstr = info->creator; } else if (mode == _("Library contains")) { compstr = info->path; - } - + } + transform (compstr.begin(), compstr.end(), compstr.begin(), ::toupper); if (compstr.find (filterstr) != string::npos) { @@ -206,7 +225,6 @@ PluginSelector::show_this_plugin (const PluginInfoPtr& info, const std::string& } else { return false; } - } return true; @@ -224,6 +242,8 @@ PluginSelector::refill () { std::string filterstr; + in_row_change = true; + plugin_model->clear (); setup_filter_string (filterstr); @@ -232,6 +252,8 @@ PluginSelector::refill () lv2_refiller (filterstr); vst_refiller (filterstr); au_refiller (filterstr); + + in_row_change = false; } void @@ -244,11 +266,11 @@ PluginSelector::refiller (const PluginInfoList& plugs, const::std::string& filte if (show_this_plugin (*i, filterstr)) { TreeModel::Row newrow = *(plugin_model->append()); + newrow[plugin_columns.favorite] = manager->is_a_favorite_plugin (*i); newrow[plugin_columns.name] = (*i)->name; newrow[plugin_columns.type_name] = type; newrow[plugin_columns.category] = (*i)->category; - string creator = (*i)->creator; string::size_type pos = 0; @@ -313,18 +335,14 @@ PluginSelector::au_refiller (const std::string& filterstr) #endif } -void -PluginSelector::use_plugin (PluginInfoPtr pi) +PluginPtr +PluginSelector::load_plugin (PluginInfoPtr pi) { if (session == 0) { - return; + return PluginPtr(); } - PluginPtr plugin = pi->load (*session); - - if (plugin) { - PluginCreated (plugin); - } + return pi->load (*session); } void @@ -390,6 +408,7 @@ PluginSelector::run () { ResponseType r; TreeModel::Children::iterator i; + SelectedPlugins plugins; r = (ResponseType) Dialog::run (); @@ -397,24 +416,26 @@ PluginSelector::run () case RESPONSE_APPLY: for (i = amodel->children().begin(); i != amodel->children().end(); ++i) { PluginInfoPtr pp = (*i)[acols.plugin]; - use_plugin (pp); + PluginPtr p = load_plugin (pp); + if (p) { + plugins.push_back (p); + } + } + if (interested_object && !plugins.empty()) { + interested_object->use_plugins (plugins); } + break; default: break; } - cleanup (); - - return (int) r; -} - -void -PluginSelector::cleanup () -{ hide(); amodel->clear(); + interested_object = 0; + + return (int) r; } void @@ -432,6 +453,14 @@ PluginSelector::filter_entry_changed () void PluginSelector::filter_mode_changed () { + std::string mode = filter_mode.get_active_text (); + + if (mode == _("Favorites only")) { + filter_entry.set_sensitive (false); + } else { + filter_entry.set_sensitive (true); + } + refill (); } @@ -441,3 +470,153 @@ PluginSelector::on_show () ArdourDialog::on_show (); filter_entry.grab_focus (); } + +struct PluginMenuCompare { + bool operator() (PluginInfoPtr a, PluginInfoPtr b) const { + int cmp; + + cmp = strcasecmp (a->creator.c_str(), b->creator.c_str()); + + if (cmp < 0) { + return true; + } else if (cmp == 0) { + /* same creator ... compare names */ + if (strcasecmp (a->name.c_str(), b->name.c_str()) < 0) { + return true; + } + } + return false; + } +}; + +Gtk::Menu& +PluginSelector::plugin_menu() +{ + using namespace Menu_Helpers; + + typedef std::map SubmenuMap; + SubmenuMap submenu_map; + + if (!_menu) { + _menu = new Menu(); + _menu->set_name("ArdourContextMenu"); + } + + MenuList& items = _menu->items(); + Menu* favs = new Menu(); + favs->set_name("ArdourContextMenu"); + + items.clear (); + items.push_back (MenuElem (_("Favorites"), *favs)); + items.push_back (MenuElem (_("Plugin Manager"), mem_fun (*this, &PluginSelector::show_manager))); + items.push_back (SeparatorElem ()); + + PluginInfoList all_plugs; + + all_plugs.insert (all_plugs.end(), manager->ladspa_plugin_info().begin(), manager->ladspa_plugin_info().end()); +#ifdef VST_SUPPORT + all_plugs.insert (all_plugs.end(), manager->vst_plugin_info().begin(), manager->vst_plugin_info().end()); +#endif +#ifdef HAVE_AUDIOUNITS + all_plugs.insert (all_plugs.end(), manager->au_plugin_info().begin(), manager->au_plugin_info().end()); +#endif +#ifdef HAVE_SLV2 + all_plugs.insert (all_plugs.end(), manager->lv2_plugin_info().begin(), manager->lv2_plugin_info().end()); +#endif + + PluginMenuCompare cmp; + all_plugs.sort (cmp); + + for (PluginInfoList::const_iterator i = all_plugs.begin(); i != all_plugs.end(); ++i) { + SubmenuMap::iterator x; + Gtk::Menu* submenu; + + string creator = (*i)->creator; + string::size_type pos = 0; + + if (manager->is_a_favorite_plugin (*i)) { + favs->items().push_back (MenuElem ((*i)->name, (bind (mem_fun (*this, &PluginSelector::plugin_chosen_from_menu), *i)))); + } + + /* stupid LADSPA creator strings */ + + while (pos < creator.length() && (isalnum (creator[pos]) || isspace (creator[pos]))) ++pos; + creator = creator.substr (0, pos); + + if ((x = submenu_map.find (creator)) != submenu_map.end()) { + submenu = x->second; + } else { + submenu = new Gtk::Menu; + items.push_back (MenuElem (creator, *submenu)); + submenu_map.insert (pair (creator, submenu)); + submenu->set_name("ArdourContextMenu"); + } + + submenu->items().push_back (MenuElem ((*i)->name, (bind (mem_fun (*this, &PluginSelector::plugin_chosen_from_menu), *i)))); + } + + return *_menu; +} + +void +PluginSelector::plugin_chosen_from_menu (const PluginInfoPtr& pi) +{ + PluginPtr p = load_plugin (pi); + + if (p && interested_object) { + SelectedPlugins plugins; + plugins.push_back (p); + interested_object->use_plugins (plugins); + } + + interested_object = 0; +} + +void +PluginSelector::favorite_changed (const Glib::ustring& path) +{ + PluginInfoPtr pi; + + if (in_row_change) { + return; + } + + in_row_change = true; + + TreeModel::iterator iter = plugin_model->get_iter (path); + + if (iter) { + + bool favorite = !(*iter)[plugin_columns.favorite]; + + /* change state */ + + (*iter)[plugin_columns.favorite] = favorite; + + /* save new favorites list */ + + pi = (*iter)[plugin_columns.plugin]; + + if (favorite) { + manager->add_favorite (pi->type, pi->unique_id); + } else { + manager->remove_favorite (pi->type, pi->unique_id); + } + + manager->save_favorites (); + } + in_row_change = false; +} + +void +PluginSelector::show_manager () +{ + show_all(); + run (); +} + +void +PluginSelector::set_interested_object (PluginInterestedObject& obj) +{ + interested_object = &obj; +} diff --git a/gtk2_ardour/plugin_selector.h b/gtk2_ardour/plugin_selector.h index fe797588de..c4b613647d 100644 --- a/gtk2_ardour/plugin_selector.h +++ b/gtk2_ardour/plugin_selector.h @@ -26,6 +26,7 @@ #include #include +#include "plugin_interest.h" namespace ARDOUR { class Session; @@ -36,16 +37,21 @@ class PluginSelector : public ArdourDialog { public: PluginSelector (ARDOUR::PluginManager *); - sigc::signal > PluginCreated; + void set_interested_object (PluginInterestedObject&); + int run (); // XXX should we try not to overload the non-virtual Gtk::Dialog::run() ? void set_session (ARDOUR::Session*); void on_show (); + Gtk::Menu& plugin_menu (); + private: + PluginInterestedObject* interested_object; + ARDOUR::Session* session; - Gtk::ScrolledWindow scroller; // Available plugins + Gtk::ScrolledWindow scroller; // Available plugins Gtk::ScrolledWindow ascroller; // Added plugins Gtk::ComboBoxText filter_mode; @@ -58,6 +64,7 @@ class PluginSelector : public ArdourDialog struct PluginColumns : public Gtk::TreeModel::ColumnRecord { PluginColumns () { + add (favorite); add (name); add (type_name); add (category); @@ -68,6 +75,7 @@ class PluginSelector : public ArdourDialog add (midi_outs); add (plugin); } + Gtk::TreeModelColumn favorite; Gtk::TreeModelColumn name; Gtk::TreeModelColumn type_name; Gtk::TreeModelColumn category; @@ -112,10 +120,16 @@ class PluginSelector : public ArdourDialog void added_list_selection_changed(); void display_selection_changed(); void btn_apply_clicked(); - void use_plugin (ARDOUR::PluginInfoPtr); - void cleanup (); + ARDOUR::PluginPtr load_plugin (ARDOUR::PluginInfoPtr); bool show_this_plugin (const ARDOUR::PluginInfoPtr&, const std::string&); void setup_filter_string (std::string&); + + void favorite_changed (const Glib::ustring& path); + bool in_row_change; + + void plugin_chosen_from_menu (const ARDOUR::PluginInfoPtr&); + Gtk::Menu* _menu; + void show_manager (); }; #endif // __ardour_plugin_selector_h__ diff --git a/gtk2_ardour/plugin_ui.cc b/gtk2_ardour/plugin_ui.cc index 014638e9cd..d3c9effaa2 100644 --- a/gtk2_ardour/plugin_ui.cc +++ b/gtk2_ardour/plugin_ui.cc @@ -51,6 +51,7 @@ #include "utils.h" #include "gui_thread.h" #include "public_editor.h" +#include "keyboard.h" #include "i18n.h" @@ -150,6 +151,20 @@ PluginUIWindow::on_map () set_keep_above (true); } +bool +PluginUIWindow::on_enter_notify_event (GdkEventCrossing *ev) +{ + Keyboard::the_keyboard().enter_window (ev, this); + return false; +} + +bool +PluginUIWindow::on_leave_notify_event (GdkEventCrossing *ev) +{ + Keyboard::the_keyboard().leave_window (ev, this); + return false; +} + void PluginUIWindow::on_show () { diff --git a/gtk2_ardour/plugin_ui.h b/gtk2_ardour/plugin_ui.h index 65b7b0d7fb..acc1e4d53a 100644 --- a/gtk2_ardour/plugin_ui.h +++ b/gtk2_ardour/plugin_ui.h @@ -214,11 +214,14 @@ class PluginUIWindow : public Gtk::Window void resize_preferred(); void set_parent (Gtk::Window*); + bool on_enter_notify_event (GdkEventCrossing*); + bool on_leave_notify_event (GdkEventCrossing*); bool on_key_press_event (GdkEventKey*); bool on_key_release_event (GdkEventKey*); void on_show (); void on_hide (); void on_map (); + private: PlugUIBase* _pluginui; Gtk::Window* parent; diff --git a/gtk2_ardour/po/sv_SE.po b/gtk2_ardour/po/sv_SE.po index d870c203fe..158b1c4cec 100644 --- a/gtk2_ardour/po/sv_SE.po +++ b/gtk2_ardour/po/sv_SE.po @@ -1966,15 +1966,6 @@ msgstr "Tona Ut" msgid "Audition" msgstr "Avlyssna" - -#: gtk2_ardour/editor.cc:105 gtk2_ardour/editor.cc:3517 -msgid "Slide Edit" -msgstr "Glidred." - -#: gtk2_ardour/editor.cc:106 gtk2_ardour/editor.cc:3515 -msgid "Splice Edit" -msgstr "Fogred." - #: gtk2_ardour/editor.cc:111 gtk2_ardour/editor.cc:3572 #: gtk2_ardour/export_dialog.cc:78 gtk2_ardour/export_dialog.cc:92 #: gtk2_ardour/export_dialog.cc:893 gtk2_ardour/export_dialog.cc:1225 @@ -7102,6 +7093,7 @@ msgstr "EJ tonhöjdsändrat soloslagverk" #: gtk2_ardour/editor_timefx.cc:73 msgid "Contents:" msgstr "Innehåll" +<<<<<<< .working #: gtk2_ardour/editor_actions.cc:359 @@ -7442,3 +7434,558 @@ msgstr "FFT-analysfönster" #: gtk2_ardour/analysis_window.cc:135 msgid "Re-analyze data" msgstr "Återanalysera data" +======= + +#: gtk2_ardour/editor_actions.cc:359 +msgid "Playhead to Mouse" +msgstr "Startmarkören till mus" + +#: gtk2_ardour/editor_actions.cc:277 +msgid "Playhead To Active Mark" +msgstr "Startmarkören till aktiv markör" + +#: gtk2_ardour/editor_actions.cc:231 +msgid "Nudge Playhead Forward" +msgstr "Knuffa startmarkören framåt" + +#: gtk2_ardour/editor_actions.cc:233 +msgid "Nudge Playhead Backward" +msgstr "Knuffa startmarkören bakåt" + +#: gtk2_ardour/editor_actions.cc:475 +msgid "Move Forward to Transient" +msgstr "Gå framåt till transient" + +#: gtk2_ardour/editor_actions.cc:477 +msgid "Move Backwards to Transient" +msgstr "Gå bakåt till transient" + +#: gtk2_ardour/editor_actions.cc:235 +msgid "Forward To Grid" +msgstr "Framåt till rutnät" + +#: gtk2_ardour/editor_actions.cc:237 +msgid "Backward To Grid" +msgstr "Bakåt till rutnät" + +#: gtk2_ardour/editor_actions.cc:66 gtk2_ardour/editor.cc:151 +#: gtk2_ardour/editor.cc:3446 +msgid "Active Mark" +msgstr "Aktiv markör" + +#: gtk2_ardour/editor_actions.cc:137 +msgid "to Next Region Boundary" +msgstr "till nästa regionsgränsen" + +#: gtk2_ardour/editor_actions.cc:139 +msgid "to Previous Region Boundary" +msgstr "till förra regionsgränsen" + +#: gtk2_ardour/editor_actions.cc:279 +msgid "Active Mark To Playhead" +msgstr "Aktiv markör till startmarkören" + +#: gtk2_ardour/editor_actions.cc:361 +msgid "Active Marker to Mouse" +msgstr "Aktiv markör till musen" + +#: gtk2_ardour/editor_actions.cc:61 gtk2_ardour/editor_actions.cc:613 +msgid "Markers" +msgstr "Markörer" + +#: gtk2_ardour/ardour_ui_ed.cc:333 +msgid "Punch In/Out" +msgstr "Inslag/utslag" + +#: gtk2_ardour/editor_actions.cc:177 +msgid "Select All Overlapping Edit Range" +msgstr "Välj allt som överlappar redigeringsomfånget" + +#: gtk2_ardour/editor_actions.cc:179 +msgid "Select All Inside Edit Range" +msgstr "Välj allt inom redigeringsomfånget" + +#: gtk2_ardour/editor_actions.cc:182 +msgid "Select Edit Range" +msgstr "Välj redigeringsomfång" + + +#: gtk2_ardour/editor_actions.cc:444 +msgid "Separate Using Punch Range" +msgstr "Separera utifrån in-/utslagsomfånget" + +#: gtk2_ardour/editor_actions.cc:447 +msgid "Separate Using Loop Range" +msgstr "Separera utifrån loopomfånget" + +#: gtk2_ardour/editor_actions.cc:469 +msgid "Split Regions At Percussion Onsets" +msgstr "Dela regioner vid perkussiva anslag" + +#: gtk2_ardour/editor_actions.cc:282 +msgid "Trim Start At Edit Point" +msgstr "Beskär början vid redigeringspunkten" + +#: gtk2_ardour/editor_actions.cc:285 +msgid "Trim End At Edit Point" +msgstr "Beskär slutet vid redigeringspunkten" + +#: gtk2_ardour/ardour_ui_ed.cc:95 +msgid "Misc. Shortcuts" +msgstr "Diverse kortkommandon" + +#: gtk2_ardour/editor_actions.cc:385 +msgid "Boost Region Gain" +msgstr "Öka regionens volym" + +#: gtk2_ardour/editor_actions.cc:388 +msgid "Cut Region Gain" +msgstr "Sänk regionens volym" + +#: gtk2_ardour/editor_actions.cc:99 +msgid "Break drag" +msgstr "Avbryt dragning" + + +#: gtk2_ardour/editor_actions.cc:400 +msgid "Raise Region" +msgstr "Höj regionen" + +#: gtk2_ardour/editor_actions.cc:403 +msgid "Lower Region" +msgstr "Sänk regionen" + +#: gtk2_ardour/editor_actions.cc:415 +msgid "Move To Original Position" +msgstr "Flytta till ursprunglig position" + +#: gtk2_ardour/editor_actions.cc:409 +msgid "Lock Region" +msgstr "Lås region" + +#: gtk2_ardour/editor_actions.cc:397 +msgid "Remove Region Sync" +msgstr "Ta bort regionsynk.-punkt" + +#: gtk2_ardour/editor_actions.cc:505 gtk2_ardour/editor_ops.cc:5651 +msgid "Insert Time" +msgstr "Infoga tid" + +#: gtk2_ardour/editor_actions.cc:93 +msgid "Waveforms" +msgstr "Vågformer" + +#: gtk2_ardour/editor_actions.cc:509 +msgid "Toggle Active" +msgstr "Växla aktiv" + +#: gtk2_ardour/editor_actions.cc:547 +msgid "Zoom Focus Mouse" +msgstr "Zoomfokus: mus" + +#: gtk2_ardour/editor_actions.cc:582 +msgid "Next Snap Mode" +msgstr "Nästa fästläge" + +#: gtk2_ardour/editor_actions.cc:583 +msgid "Next Snap Choice" +msgstr "Nästa fästlägealternativ" + +#: gtk2_ardour/editor_actions.cc:70 +msgid "Primary Clock" +msgstr "Primär klocka" + +#: gtk2_ardour/editor_actions.cc:77 +msgid "Secondary Clock" +msgstr "Sekundär klocka" + +#: gtk2_ardour/ardour_ui_ed.cc:309 gtk2_ardour/ardour_ui_ed.cc:318 +#: gtk2_ardour/editor_actions.cc:616 +msgid "Bars & Beats" +msgstr "Takter & slag" + +#: gtk2_ardour/ardour_ui_ed.cc:311 gtk2_ardour/ardour_ui_ed.cc:320 +msgid "Minutes & Seconds" +msgstr "Minuter & sekunder" + +#: gtk2_ardour/editor_actions.cc:75 +msgid "Rulers" +msgstr "Tidslinjevisning" + +#: gtk2_ardour/editor_actions.cc:619 +msgid "Min:Sec" +msgstr "Min:sek" + +#: gtk2_ardour/editor_actions.cc:615 +msgid "Loop/Punch" +msgstr "Loop-/inslagsmarkörer" + +#: gtk2_ardour/editor_actions.cc:76 +msgid "Scroll" +msgstr "Skrollning" + +#: gtk2_ardour/rhythm_ferret.cc:40 +msgid "Analysis" +msgstr "Analys" + +#: gtk2_ardour/rhythm_ferret.cc:30 +msgid "Percussive Onset" +msgstr "Perkussivt anslag" + +#: gtk2_ardour/rhythm_ferret.cc:31 +msgid "Note Onset" +msgstr "Notanslag" + +#: gtk2_ardour/rhythm_ferret.cc:48 +msgid "Threshold" +msgstr "Tröskel" + +#: gtk2_ardour/rhythm_ferret.cc:51 +msgid "Sensitivity" +msgstr "Känslighet" + +#: gtk2_ardour/rhythm_ferret.cc:52 +msgid "Analyze" +msgstr "Analysera" + +#: gtk2_ardour/rhythm_ferret.cc:55 +msgid "Trigger gap (msecs)" +msgstr "Utlösningsmellanrum (msek)" + +#: gtk2_ardour/rhythm_ferret.cc:43 +msgid "Set Tempo Map" +msgstr "Sätt tempokarta" + +#: gtk2_ardour/rhythm_ferret.cc:44 +msgid "Conform Region" +msgstr "Anpassa region" + +#: gtk2_ardour/rhythm_ferret.cc:39 +msgid "Selection" +msgstr "Markering" + + +#: gtk2_ardour/editor_actions.cc:463 +msgid "Set Tempo from Region=Bar" +msgstr "Sätt tempo från region=takt" + +#: gtk2_ardour/editor_actions.cc:466 +msgid "Set Tempo from Edit Range=Bar" +msgstr "Sätt tempo från redigeringsomfång=takt" + + +#: gtk2_ardour/ardour_ui_ed.cc:548 +msgid "JACK does monitoring" +msgstr "JACK sköter medhörning" + +#: gtk2_ardour/ardour_ui_ed.cc:552 +msgid "Ardour does monitoring" +msgstr "Ardour sköter medhörning" + +#: gtk2_ardour/ardour_ui_ed.cc:553 +msgid "Audio Hardware does monitoring" +msgstr "Ljudhårdvaran sköter medhörning" + +#: gtk2_ardour/ardour_ui_ed.cc:438 +msgid "Tape Machine mode" +msgstr "Bandmaskinläge" + +#: gtk2_ardour/editor_actions.cc:64 +msgid "Misc Options" +msgstr "Diverse inställningar" + +#: gtk2_ardour/ardour_ui_ed.cc:446 +msgid "Create marker at xrun location" +msgstr "Skapa markör vid xrun-förekomst" + +#: gtk2_ardour/ardour_ui_ed.cc:455 +msgid "Rubberbanding Snaps to Grid" +msgstr "Gummibandning fäster mot rutnätet" + +#: gtk2_ardour/ardour_ui_ed.cc:456 +msgid "Auto-analyse new audio" +msgstr "Autoanalysera nya ljud" + +#: gtk2_ardour/editor_actions.cc:689 +msgid "Import to Region List" +msgstr "Importera till regionslistan" + +#: gtk2_ardour/mixer_strip.cc:984 +msgid "Protect against denormals" +msgstr "Skydda mot denormals" + +#: gtk2_ardour/option_editor.cc:1242 +msgid "Keyboard layout" +msgstr "Tangentbordslayout" + +#: gtk2_ardour/option_editor.cc:275 +msgid "Font Scaling" +msgstr "Typsnittsskalning" + +#: gtk2_ardour/option_editor.cc:97 +msgid "Add new MIDI port" +msgstr "Lägg till ny MIDI-port" + + +#: gtk2_ardour/editor.cc:1779 gtk2_ardour/editor.cc:1948 +msgid "Spectral Analysis" +msgstr "Spektralanalys" + +#: gtk2_ardour/editor.cc:1793 +msgid "Glue to Bars&Beats" +msgstr "Klistra mot takt&slag" + +#: gtk2_ardour/analysis_window.cc:46 +msgid "Signal source" +msgstr "Signalkälla" + +#: gtk2_ardour/analysis_window.cc:47 +msgid "Selected ranges" +msgstr "Valda omfång" + +#: gtk2_ardour/analysis_window.cc:48 +msgid "Selected regions" +msgstr "Valda regioner" + +#: gtk2_ardour/analysis_window.cc:50 +msgid "Display model" +msgstr "Visningsmodell" + +#: gtk2_ardour/analysis_window.cc:51 +msgid "Composite graphs for each track" +msgstr "Sammansatt graf för varje spår" + +#: gtk2_ardour/analysis_window.cc:52 +msgid "Composite graph of all tracks" +msgstr "Sammansatt graf för alla spår" + +#: gtk2_ardour/analysis_window.cc:54 +msgid "Show frequency power range" +msgstr "Visa frekvenskraftsomfång" + +#: gtk2_ardour/analysis_window.cc:55 +msgid "Normalize values" +msgstr "Normalisera värden" + +#: gtk2_ardour/analysis_window.cc:59 gtk2_ardour/analysis_window.cc:60 +msgid "FFT analysis window" +msgstr "FFT-analysfönster" + +#: gtk2_ardour/analysis_window.cc:135 +msgid "Re-analyze data" +msgstr "Återanalysera data" + +#: gtk2_ardour/ardour_ui_ed.cc:195 +msgid "Window" +msgstr "Fönster" + +#: gtk2_ardour/ardour_ui_dependents.cc:74 +msgid "Setup Editor" +msgstr "Förbereder redigeraren..." + +#: gtk2_ardour/ardour_ui_dependents.cc:76 +msgid "Setup Mixer" +msgstr "Förbereder mixern..." + +#: gtk2_ardour/ardour_ui_dependents.cc:81 +msgid "Reload Session History" +msgstr "Laddar sessionshistoriken..." + +#: gtk2_ardour/editor.cc:4571 +msgid "Please wait while Ardour loads visual data" +msgstr "Vänta medan Ardour laddar visuell data..." + +#: gtk2_ardour/editor_actions.cc:368 +msgid "Toggle Opaque" +msgstr "Växla genomskinligt" + +#: gtk2_ardour/editor_actions.cc:570 +msgid "Fit Selected Tracks" +msgstr "Rym valda spår" + +#: gtk2_ardour/editor_actions.cc:299 +msgid "Zoom to Region (W&H)" +msgstr "Zooma till region (bredd & höjd)" + +#: gtk2_ardour/editor_actions.cc:76 +msgid "Views" +msgstr "Visningslägen" + + +#: gtk2_ardour/editor_actions.cc:196 +msgid "Save View 1" +msgstr "Spara läge 1" + +#: gtk2_ardour/editor_actions.cc:198 +msgid "Goto View 1" +msgstr "Använd läge 1" + +#: gtk2_ardour/editor_actions.cc:200 +msgid "Save View 2" +msgstr "Spara läge 2" + +#: gtk2_ardour/editor_actions.cc:202 +msgid "Goto View 2" +msgstr "Använd läge 2 " + +#: gtk2_ardour/editor_actions.cc:204 +msgid "Save View 3" +msgstr "Spara läge 3" + +#: gtk2_ardour/editor_actions.cc:206 +msgid "Goto View 3" +msgstr "Använd läge 3" + +#: gtk2_ardour/editor_actions.cc:208 +msgid "Save View 4" +msgstr "Spara läge 4" + +#: gtk2_ardour/editor_actions.cc:210 +msgid "Goto View 4" +msgstr "Använd läge 4" + +#: gtk2_ardour/editor_actions.cc:212 +msgid "Save View 5" +msgstr "Spara läge 5" + +#: gtk2_ardour/editor_actions.cc:214 +msgid "Goto View 5" +msgstr "Använd läge 5" + +#: gtk2_ardour/editor_actions.cc:216 +msgid "Save View 6" +msgstr "Spara läge 6" + +#: gtk2_ardour/editor_actions.cc:218 +msgid "Goto View 6" +msgstr "Använd läge 6" + +#: gtk2_ardour/editor_actions.cc:220 +msgid "Save View 7" +msgstr "Spara läge 7" + +#: gtk2_ardour/editor_actions.cc:222 +msgid "Goto View 7" +msgstr "Använd läge 7" + +#: gtk2_ardour/editor_actions.cc:224 +msgid "Save View 8" +msgstr "Spara läge 8" + +#: gtk2_ardour/editor_actions.cc:226 +msgid "Goto View 8" +msgstr "Använd läge 8" + +#: gtk2_ardour/editor_actions.cc:228 +msgid "Save View 9" +msgstr "Spara läge 9" + +#: gtk2_ardour/editor_actions.cc:230 +msgid "Goto View 9" +msgstr "Använd läge 9" + +#: gtk2_ardour/editor_actions.cc:232 +msgid "Save View 10" +msgstr "Spara läge 10" + +#: gtk2_ardour/editor_actions.cc:234 +msgid "Goto View 10" +msgstr "Använd läge 10" + +#: gtk2_ardour/editor_actions.cc:236 +msgid "Save View 11" +msgstr "Spara läge 11" + +#: gtk2_ardour/editor_actions.cc:238 +msgid "Goto View 11" +msgstr "Använd läge 11" + +#: gtk2_ardour/editor_actions.cc:240 +msgid "Save View 12" +msgstr "Spara läge 12" + +#: gtk2_ardour/editor_actions.cc:242 +msgid "Goto View 12" +msgstr "Använd läge 12" + +#: gtk2_ardour/ardour_ui_ed.cc:462 +msgid "Name New Markers" +msgstr "Namnge nya markörer" + +#: gtk2_ardour/editor_ops.cc:1900 +msgid "Name New Location Marker" +msgstr "Namnge ny platsmarkör" + +#: gtk2_ardour/sfdb_ui.cc:513 +msgid "Search Freesound" +msgstr "Sök i Freesound" + +#: gtk2_ardour/sfdb_ui.cc:480 +msgid "User:" +msgstr "Användarnamn:" + +#: gtk2_ardour/sfdb_ui.cc:484 +msgid "Password:" +msgstr "Lösenord:" + +#: gtk2_ardour/sfdb_ui.cc:400 gtk2_ardour/sfdb_ui.cc:789 +msgid "Start Downloading" +msgstr "Ladda ner" + +#: gtk2_ardour/redirect_box.cc:1190 +msgid "New Plugin" +msgstr "Nytt insticksprogram" + +#: gtk2_ardour/plugin_selector.cc:100 +msgid "Plugins to be connected" +msgstr "Insticksprogram att ansluta" + +#: gtk2_ardour/plugin_selector.cc:156 +msgid "Insert Plugin(s)" +msgstr "Infoga" + +#: gtk2_ardour/plugin_selector.cc:501 +msgid "Favorites" +msgstr "Favoriter" + +#: gtk2_ardour/plugin_selector.cc:502 +msgid "Plugin Manager" +msgstr "Insticksprogram" + +#: gtk2_ardour/plugin_selector.cc:77 +msgid "Fav" +msgstr "" + +#: gtk2_ardour/plugin_selector.cc:78 +msgid "Available Plugins" +msgstr "Tillgängliga insticksprogram" + +#: gtk2_ardour/plugin_selector.cc:80 +msgid "Category" +msgstr "Kategori" + +#: gtk2_ardour/plugin_selector.cc:81 +msgid "Creator" +msgstr "Upphovsperson" + +#: gtk2_ardour/plugin_selector.cc:51 gtk2_ardour/plugin_selector.cc:209 +msgid "Name contains" +msgstr "Namn innehåller" + +#: gtk2_ardour/plugin_selector.cc:52 gtk2_ardour/plugin_selector.cc:211 +msgid "Type contains" +msgstr "Typ innehåller" + +#: gtk2_ardour/plugin_selector.cc:53 gtk2_ardour/plugin_selector.cc:213 +msgid "Author contains" +msgstr "Upphovsperson innehåller" + +#: gtk2_ardour/plugin_selector.cc:54 gtk2_ardour/plugin_selector.cc:215 +msgid "Library contains" +msgstr "Bibliotek innehåller" + +#: gtk2_ardour/plugin_selector.cc:55 gtk2_ardour/plugin_selector.cc:203 +#: gtk2_ardour/plugin_selector.cc:451 +msgid "Favorites only" +msgstr "Endast favoriter" +>>>>>>> .merge-right.r3622 diff --git a/gtk2_ardour/processor_box.cc b/gtk2_ardour/processor_box.cc index 9ce28d0aa6..370bb7548b 100644 --- a/gtk2_ardour/processor_box.cc +++ b/gtk2_ardour/processor_box.cc @@ -19,6 +19,7 @@ #include #include +#include #include @@ -46,6 +47,7 @@ #include #include #include +#include #include "ardour_ui.h" #include "ardour_dialog.h" @@ -57,15 +59,14 @@ #include "mixer_ui.h" #include "actions.h" #include "plugin_ui.h" -#include "send_ui.h" #include "io_selector.h" #include "utils.h" #include "gui_thread.h" #include "i18n.h" -#ifdef HAVE_AUDIOUNIT -#include "au_pluginui.h" +#ifdef HAVE_AUDIOUNITS +class AUPluginUI; #endif using namespace sigc; @@ -93,8 +94,8 @@ ProcessorBox::ProcessorBox (Placement pcmnt, Session& sess, boost::shared_ptrset_sizing(TREE_VIEW_COLUMN_FIXED); processor_display.get_column(0)->set_fixed_width(48); - processor_display.set_enable_search (false); - processor_display.add_object_drag (columns.processor.index(), "redirects"); + processor_display.add_object_drag (columns.processor.index(), "processors"); processor_display.signal_object_drop.connect (mem_fun (*this, &ProcessorBox::object_drop)); TreeViewColumn* name_col = processor_display.get_column(0); @@ -153,10 +153,6 @@ ProcessorBox::ProcessorBox (Placement pcmnt, Session& sess, boost::shared_ptr* ptr) { - if (type != "redirects" || cnt == 0 || !ptr) { + if (type != "processors" || cnt == 0 || !ptr) { return; } @@ -210,12 +206,14 @@ void ProcessorBox::remove_processor_gui (boost::shared_ptr processor) { boost::shared_ptr send; - boost::shared_ptr port_processor; + boost::shared_ptr port_insert; + + if ((port_insert = boost::dynamic_pointer_cast (processor)) != 0) { + + PortInsertUI *io_selector = reinterpret_cast (port_insert->get_gui()); + port_insert->set_gui (0); + delete io_selector; - if ((port_processor = boost::dynamic_pointer_cast (processor)) != 0) { - PortInsertUI *io_selector = reinterpret_cast (port_processor->get_gui()); - port_processor->set_gui (0); - delete io_selector; } else if ((send = boost::dynamic_pointer_cast (processor)) != 0) { SendUIWindow *sui = reinterpret_cast (send->get_gui()); send->set_gui (0); @@ -256,6 +254,12 @@ ProcessorBox::show_processor_menu (gint arg) processor_menu = build_processor_menu (); } + Gtk::MenuItem* plugin_menu_item = dynamic_cast(ActionManager::get_widget("/processormenu/newplugin")); + + if (plugin_menu_item) { + plugin_menu_item->set_submenu (_plugin_selector.plugin_menu()); + } + paste_action->set_sensitive (!_rr_selection.processors.empty()); processor_menu->popup (1, arg); @@ -304,7 +308,7 @@ ProcessorBox::processor_button_press_event (GdkEventButton *ev) } else if (processor && ev->button == 1 && selected) { // this is purely informational but necessary - InsertSelected (processor); // emit + ProcessorSelected (processor); // emit } return ret; @@ -340,6 +344,8 @@ ProcessorBox::processor_button_release_event (GdkEventButton *ev) } else if (processor && (ev->button == 2) && (Keyboard::no_modifier_keys_pressed (ev) && ((ev->state & Gdk::BUTTON2_MASK) == Gdk::BUTTON2_MASK))) { + /* button2-click with no modifiers */ + processor->set_active (!processor->active()); ret = true; @@ -352,7 +358,6 @@ Menu * ProcessorBox::build_processor_menu () { processor_menu = dynamic_cast(ActionManager::get_widget("/processormenu") ); - assert(processor_menu != 0); processor_menu->set_name ("ArdourContextMenu"); show_all_children(); @@ -382,26 +387,26 @@ ProcessorBox::deselect_all_processors () void ProcessorBox::choose_plugin () { - sigc::connection newplug_connection = _plugin_selector.PluginCreated.connect (mem_fun(*this,&ProcessorBox::processor_plugin_chosen)); - _plugin_selector.show_all(); - _plugin_selector.run (); - newplug_connection.disconnect(); + _plugin_selector.set_interested_object (*this); } void -ProcessorBox::processor_plugin_chosen (boost::shared_ptr plugin) +ProcessorBox::use_plugins (const SelectedPlugins& plugins) { - if (plugin) { + for (SelectedPlugins::const_iterator p = plugins.begin(); p != plugins.end(); ++p) { - boost::shared_ptr processor (new PluginInsert (_session, plugin, _placement)); - - Route::ProcessorStreams err; + boost::shared_ptr processor (new PluginInsert (_session, *p, _placement)); - if (_route->add_processor (processor, &err)) { - weird_plugin_dialog (*plugin, err, _route); + Route::ProcessorStreams err_streams; + + if (_route->add_processor (processor, &err_streams)) { + weird_plugin_dialog (**p, err_streams, _route); // XXX SHAREDPTR delete plugin here .. do we even need to care? } else { - processor->set_active(true); + + if (Profile->get_sae()) { + processor->set_active (true); + } processor->ActiveChanged.connect (bind (mem_fun (*this, &ProcessorBox::show_processor_active), boost::weak_ptr(processor))); } } @@ -471,7 +476,7 @@ ProcessorBox::weird_plugin_dialog (Plugin& p, Route::ProcessorStreams streams, b } void -ProcessorBox::choose_processor () +ProcessorBox::choose_insert () { boost::shared_ptr processor (new PortInsert (_session, _placement)); processor->ActiveChanged.connect (bind (mem_fun(*this, &ProcessorBox::show_processor_active), boost::weak_ptr(processor))); @@ -494,35 +499,54 @@ ProcessorBox::choose_send () outs = _route->n_outputs(); } - send->io()->ensure_io (ChanCount::ZERO, outs, false, this); + /* XXX need processor lock on route */ - SendUIWindow* gui = new SendUIWindow (send, _session); + try { + send->io()->ensure_io (ChanCount::ZERO, outs, false, this); + } catch (AudioEngine::PortRegistrationFailure& err) { + error << string_compose (_("Cannot set up new send: %1"), err.what()) << endmsg; + return; + } /* let the user adjust the output setup (number and connections) before passing it along to the Route */ - gui->show_all (); - gui->present (); + IOSelectorWindow *ios = new IOSelectorWindow (_session, send->io(), false, true); - /* pass shared_ptr, it will go out of scope when the GUI is deleted */ - /* also, connect it *before* existing handlers so that its definitely executed */ + ios->show_all (); - gui->signal_delete_event().connect (bind (mem_fun(*this, &ProcessorBox::send_io_finished), send, gui), false); + boost::shared_ptr r = boost::static_pointer_cast(send); + + ios->selector().Finished.connect (bind (mem_fun(*this, &ProcessorBox::send_io_finished), boost::weak_ptr(r), ios)); } -bool -ProcessorBox::send_io_finished (GdkEventAny* ev, boost::shared_ptr send, SendUIWindow* sui) +void +ProcessorBox::send_io_finished (IOSelector::Result r, boost::weak_ptr weak_processor, IOSelectorWindow* ios) { - _route->add_processor (send); - delete sui; - return false; + boost::shared_ptr processor (weak_processor.lock()); + + if (!processor) { + return; + } + + switch (r) { + case IOSelector::Cancelled: + // processor will go away when all shared_ptrs to it vanish + break; + + case IOSelector::Accepted: + _route->add_processor (processor); + break; + } + + delete_when_idle (ios); } void ProcessorBox::redisplay_processors () { - ENSURE_GUI_THREAD(mem_fun(*this, &ProcessorBox::redisplay_processors)); + ENSURE_GUI_THREAD (mem_fun(*this, &ProcessorBox::redisplay_processors)); if (no_processor_redisplay) { return; @@ -535,15 +559,15 @@ ProcessorBox::redisplay_processors () processor_active_connections.clear (); processor_name_connections.clear (); - void (ProcessorBox::*pmf)(boost::shared_ptr) = &ProcessorBox::add_processor_to_display; - _route->foreach_processor (this, pmf); + void (ProcessorBox::*method)(boost::shared_ptr) = &ProcessorBox::add_processor_to_display; + _route->foreach_processor (this, method); switch (_placement) { case PreFader: - build_processor_tooltip(processor_eventbox, _("Pre-fader processors, sends & plugins:")); + build_processor_tooltip(processor_eventbox, _("Pre-fader inserts, sends & plugins:")); break; case PostFader: - build_processor_tooltip(processor_eventbox, _("Post-fader processors, sends & plugins:")); + build_processor_tooltip(processor_eventbox, _("Post-fader inserts, sends & plugins:")); break; } } @@ -629,11 +653,7 @@ ProcessorBox::build_processor_tooltip (EventBox& box, string start) for(Gtk::TreeModel::Children::iterator iter = children.begin(); iter != children.end(); ++iter) { Gtk::TreeModel::Row row = *iter; tip += '\n'; - - /* don't use the column text, since it may be narrowed */ - - boost::shared_ptr i = row[columns.processor]; - tip += i->name(); + tip += row[columns.text]; } ARDOUR_UI::instance()->tooltips().set_tip (box, tip); } @@ -648,14 +668,14 @@ ProcessorBox::show_processor_name (boost::weak_ptr processor) void ProcessorBox::show_processor_active (boost::weak_ptr weak_processor) { - ENSURE_GUI_THREAD(bind (mem_fun(*this, &ProcessorBox::show_processor_active), weak_processor)); - boost::shared_ptr processor (weak_processor.lock()); if (!processor) { return; } + ENSURE_GUI_THREAD(bind (mem_fun(*this, &ProcessorBox::show_processor_active), weak_processor)); + Gtk::TreeModel::Children children = model->children(); Gtk::TreeModel::Children::iterator iter = children.begin(); @@ -693,8 +713,8 @@ ProcessorBox::compute_processor_sort_keys () Gtk::TreeModel::Children children = model->children(); for (Gtk::TreeModel::Children::iterator iter = children.begin(); iter != children.end(); ++iter) { - boost::shared_ptr i = (*iter)[columns.processor]; - i->set_sort_key (sort_key); + boost::shared_ptr r = (*iter)[columns.processor]; + r->set_sort_key (sort_key); sort_key++; } @@ -966,13 +986,13 @@ ProcessorBox::get_selected_processors (vector >& pr } void -ProcessorBox::for_selected_processors (void (ProcessorBox::*pmf)(boost::shared_ptr)) +ProcessorBox::for_selected_processors (void (ProcessorBox::*method)(boost::shared_ptr)) { vector pathlist = processor_display.get_selection()->get_selected_rows(); for (vector::iterator iter = pathlist.begin(); iter != pathlist.end(); ++iter) { boost::shared_ptr processor = (*(model->get_iter(*iter)))[columns.processor]; - (this->*pmf)(processor); + (this->*method)(processor); } } @@ -999,16 +1019,6 @@ ProcessorBox::all_processors_active (bool state) _route->all_processors_active (_placement, state); } -void -ProcessorBox::all_plugins_active (bool state) -{ - if (state) { - // XXX not implemented - } else { - _route->disable_plugins (_placement); - } -} - void ProcessorBox::ab_plugins () { @@ -1016,6 +1026,7 @@ ProcessorBox::ab_plugins () ab_direction = !ab_direction; } + void ProcessorBox::clear_processors () { @@ -1054,8 +1065,9 @@ void ProcessorBox::edit_processor (boost::shared_ptr processor) { boost::shared_ptr send; - boost::shared_ptr plugin_processor; - boost::shared_ptr port_processor; + boost::shared_ptr plugin_insert; + boost::shared_ptr port_insert; + Window* gidget = 0; if (boost::dynamic_pointer_cast(_route) != 0) { @@ -1070,6 +1082,8 @@ ProcessorBox::edit_processor (boost::shared_ptr processor) return; } + boost::shared_ptr send = boost::dynamic_pointer_cast (processor); + SendUIWindow *send_ui; if (send->get_gui() == 0) { @@ -1086,100 +1100,64 @@ ProcessorBox::edit_processor (boost::shared_ptr processor) send_ui = reinterpret_cast (send->get_gui()); } - if (send_ui->is_visible()) { - send_ui->get_window()->raise (); - } else { - send_ui->show_all (); - send_ui->present (); - } + gidget = send_ui; + + } else if ((plugin_insert = boost::dynamic_pointer_cast (processor)) != 0) { + + PluginUIWindow *plugin_ui; - } else if ((plugin_processor = boost::dynamic_pointer_cast (processor)) != 0) { + /* these are both allowed to be null */ + + Container* toplevel = get_toplevel(); + Window* win = dynamic_cast(toplevel); + + if (plugin_insert->get_gui() == 0) { - ARDOUR::PluginType type = plugin_processor->type(); - - if (type == ARDOUR::LADSPA || type == ARDOUR::VST) { - - PluginUIWindow *plugin_ui; + plugin_ui = new PluginUIWindow (win, plugin_insert); - /* these are both allowed to be null */ - - Container* toplevel = get_toplevel(); - Window* win = dynamic_cast(toplevel); - - if (plugin_processor->get_gui() == 0) { - - plugin_ui = new PluginUIWindow (win, plugin_processor); - - WindowTitle title(Glib::get_application_name()); - title += generate_processor_title (plugin_processor); - plugin_ui->set_title (title.get_string()); - - plugin_processor->set_gui (plugin_ui); - - // change window title when route name is changed - _route->NameChanged.connect (bind (mem_fun(*this, &ProcessorBox::route_name_changed), plugin_ui, boost::weak_ptr (plugin_processor))); - - } else { - plugin_ui = reinterpret_cast (plugin_processor->get_gui()); - } + WindowTitle title(Glib::get_application_name()); + title += generate_processor_title (plugin_insert); + plugin_ui->set_title (title.get_string()); - if (plugin_ui->is_visible()) { - plugin_ui->get_window()->raise (); - } else { - plugin_ui->show_all (); - plugin_ui->present (); - } -#ifdef HAVE_AUDIOUNIT - } else if (type == ARDOUR::AudioUnit) { - AUPluginUI* plugin_ui; - if (plugin_processor->get_gui() == 0) { - plugin_ui = new AUPluginUI (plugin_processor); - } else { - plugin_ui = reinterpret_cast (plugin_processor->get_gui()); - } - - plugin_ui = new PluginUIWindow (plugin_insert); - - // plugin_ui->set_keep_above (true); - - WindowTitle title(Glib::get_application_name()); - title += generate_redirect_title (plugin_insert); - plugin_ui->set_title (title.get_string()); - - plugin_insert->set_gui (plugin_ui); - - // change window title when route name is changed - _route->name_changed.connect (bind (mem_fun(*this, &RedirectBox::route_name_changed), plugin_ui, boost::weak_ptr (plugin_insert))); -#endif - - } else { - warning << "Unsupported plugin sent to ProcessorBox::edit_processor()" << endmsg; - return; - } - - } else if ((port_processor = boost::dynamic_pointer_cast (processor)) != 0) { - + plugin_insert->set_gui (plugin_ui); + + // change window title when route name is changed + _route->NameChanged.connect (bind (mem_fun(*this, &ProcessorBox::route_name_changed), plugin_ui, boost::weak_ptr (plugin_insert))); + + } else { + plugin_ui = reinterpret_cast (plugin_insert->get_gui()); + plugin_ui->set_parent (win); + } + + gidget = plugin_ui; + + } else if ((port_insert = boost::dynamic_pointer_cast (processor)) != 0) { + if (!_session.engine().connected()) { MessageDialog msg ( _("Not connected to JACK - no I/O changes are possible")); msg.run (); return; } - + PortInsertWindow *io_selector; - - if (port_processor->get_gui() == 0) { - io_selector = new PortInsertWindow (_session, port_processor); - port_processor->set_gui (io_selector); - + + if (port_insert->get_gui() == 0) { + io_selector = new PortInsertWindow (_session, port_insert); + port_insert->set_gui (io_selector); + } else { - io_selector = reinterpret_cast (port_processor->get_gui()); + io_selector = reinterpret_cast (port_insert->get_gui()); } + + gidget = io_selector; + } - if (io_selector->is_visible()) { - io_selector->get_window()->raise (); + if (gidget) { + if (gidget->is_visible()) { + gidget->get_window()->raise (); } else { - io_selector->show_all (); - io_selector->present (); + gidget->show_all (); + gidget->present (); } } } @@ -1208,9 +1186,9 @@ ProcessorBox::register_actions () Glib::RefPtr act; /* new stuff */ - ActionManager::register_action (popup_act_grp, X_("newplugin"), _("New Plugin ..."), sigc::ptr_fun (ProcessorBox::rb_choose_plugin)); + ActionManager::register_action (popup_act_grp, X_("newplugin"), _("New Plugin"), sigc::ptr_fun (ProcessorBox::rb_choose_plugin)); - act = ActionManager::register_action (popup_act_grp, X_("newinsert"), _("New Insert"), sigc::ptr_fun (ProcessorBox::rb_choose_processor)); + act = ActionManager::register_action (popup_act_grp, X_("newinsert"), _("New Insert"), sigc::ptr_fun (ProcessorBox::rb_choose_insert)); ActionManager::jack_sensitive_actions.push_back (act); act = ActionManager::register_action (popup_act_grp, X_("newsend"), _("New Send ..."), sigc::ptr_fun (ProcessorBox::rb_choose_send)); ActionManager::jack_sensitive_actions.push_back (act); @@ -1240,9 +1218,6 @@ ProcessorBox::register_actions () ActionManager::register_action (popup_act_grp, X_("activate_all"), _("Activate all"), sigc::ptr_fun (ProcessorBox::rb_activate_all)); ActionManager::register_action (popup_act_grp, X_("deactivate_all"), _("Deactivate all"), sigc::ptr_fun (ProcessorBox::rb_deactivate_all)); - ActionManager::register_action (popup_act_grp, X_("a_b_plugins"), _("A/B plugins"), sigc::ptr_fun (ProcessorBox::rb_ab_plugins)); - ActionManager::register_action (popup_act_grp, X_("deactivate_plugins"), _("Deactivate plugins"), sigc::ptr_fun (ProcessorBox::rb_deactivate_plugins)); - /* show editors */ act = ActionManager::register_action (popup_act_grp, X_("edit"), _("Edit"), sigc::ptr_fun (ProcessorBox::rb_edit)); ActionManager::plugin_selection_sensitive_actions.push_back(act); @@ -1262,12 +1237,12 @@ ProcessorBox::rb_choose_plugin () } void -ProcessorBox::rb_choose_processor () +ProcessorBox::rb_choose_insert () { if (_current_processor_box == 0) { return; } - _current_processor_box->choose_processor (); + _current_processor_box->choose_insert (); } void @@ -1395,27 +1370,6 @@ ProcessorBox::rb_deactivate_all () _current_processor_box->all_processors_active (false); } -void -ProcessorBox::rb_deactivate_plugins () -{ - if (_current_processor_box == 0) { - return; - } - _current_processor_box->all_plugins_active (false); -} - - -void -ProcessorBox::rb_ab_plugins () -{ - if (_current_processor_box == 0) { - return; - } - - _current_processor_box->ab_plugins (); -} - - void ProcessorBox::rb_edit () { @@ -1430,8 +1384,8 @@ void ProcessorBox::route_name_changed (PluginUIWindow* plugin_ui, boost::weak_ptr wpi) { ENSURE_GUI_THREAD(bind (mem_fun (*this, &ProcessorBox::route_name_changed), plugin_ui, wpi)); + boost::shared_ptr pi (wpi.lock()); - if (pi) { WindowTitle title(Glib::get_application_name()); diff --git a/gtk2_ardour/processor_box.h b/gtk2_ardour/processor_box.h index b6bb3ae3d7..5d3eb731ca 100644 --- a/gtk2_ardour/processor_box.h +++ b/gtk2_ardour/processor_box.h @@ -37,24 +37,26 @@ #include #include #include +#include +#include #include -#include #include +#include "plugin_interest.h" #include "route_ui.h" #include "io_selector.h" +#include "send_ui.h" #include "enums.h" class MotionController; class PluginSelector; class PluginUIWindow; class RouteRedirectSelection; -class SendUIWindow; namespace ARDOUR { - class Bundle; - class Processor; + class Connection; + class Insert; class Plugin; class PluginInsert; class PortInsert; @@ -63,8 +65,7 @@ namespace ARDOUR { class Session; } - -class ProcessorBox : public Gtk::HBox +class ProcessorBox : public Gtk::HBox, public PluginInterestedObject { public: ProcessorBox (ARDOUR::Placement, ARDOUR::Session&, @@ -78,10 +79,11 @@ class ProcessorBox : public Gtk::HBox void select_all_processors (); void deselect_all_processors (); void select_all_plugins (); + void select_all_inserts (); void select_all_sends (); - sigc::signal > InsertSelected; - sigc::signal > InsertUnselected; + sigc::signal > ProcessorSelected; + sigc::signal > ProcessorUnselected; static void register_actions(); @@ -107,9 +109,9 @@ class ProcessorBox : public Gtk::HBox add (processor); add (color); } - Gtk::TreeModelColumn text; + Gtk::TreeModelColumn text; Gtk::TreeModelColumn > processor; - Gtk::TreeModelColumn color; + Gtk::TreeModelColumn color; }; ModelColumns columns; @@ -122,7 +124,7 @@ class ProcessorBox : public Gtk::HBox static Gdk::Color* inactive_processor_color; Gtk::EventBox processor_eventbox; - //Gtk::HBox processor_hpacker; + Gtk::HBox processor_hpacker; Gtkmm2ext::DnDTreeView > processor_display; Gtk::ScrolledWindow processor_scroller; @@ -143,10 +145,10 @@ class ProcessorBox : public Gtk::HBox void show_processor_menu (gint arg); void choose_send (); - bool send_io_finished (GdkEventAny*,boost::shared_ptr, SendUIWindow*); - void choose_processor (); + void send_io_finished (IOSelector::Result, boost::weak_ptr, IOSelectorWindow*); + void choose_insert (); void choose_plugin (); - void processor_plugin_chosen (boost::shared_ptr); + void use_plugins (const SelectedPlugins&); bool no_processor_redisplay; bool ignore_delete; @@ -164,8 +166,8 @@ class ProcessorBox : public Gtk::HBox void processors_reordered (const Gtk::TreeModel::Path&, const Gtk::TreeModel::iterator&, int*); void compute_processor_sort_keys (); - vector processor_active_connections; - vector processor_name_connections; + std::vector processor_active_connections; + std::vector processor_name_connections; bool processor_drag_in_progress; void processor_drag_begin (GdkDragContext*); @@ -204,7 +206,7 @@ class ProcessorBox : public Gtk::HBox static bool leave_box (GdkEventCrossing*, ProcessorBox*); static void rb_choose_plugin (); - static void rb_choose_processor (); + static void rb_choose_insert (); static void rb_choose_send (); static void rb_clear (); static void rb_cut (); @@ -218,9 +220,8 @@ class ProcessorBox : public Gtk::HBox static void rb_deactivate (); static void rb_activate_all (); static void rb_deactivate_all (); - static void rb_edit (); static void rb_ab_plugins (); - static void rb_deactivate_plugins (); + static void rb_edit (); void route_name_changed (PluginUIWindow* plugin_ui, boost::weak_ptr pi); std::string generate_processor_title (boost::shared_ptr pi); diff --git a/gtk2_ardour/public_editor.cc b/gtk2_ardour/public_editor.cc index 6797119a1f..399c71caa9 100644 --- a/gtk2_ardour/public_editor.cc +++ b/gtk2_ardour/public_editor.cc @@ -22,13 +22,16 @@ PublicEditor* PublicEditor::_instance = 0; -/** PublicEditor constructor */ +const int PublicEditor::window_border_width = 12; +const int PublicEditor::container_border_width = 12; +const int PublicEditor::vertical_spacing = 6; +const int PublicEditor::horizontal_spacing = 6; + PublicEditor::PublicEditor () : Window (Gtk::WINDOW_TOPLEVEL) { } -/** PublicEditor destructor */ PublicEditor::~PublicEditor() { } diff --git a/gtk2_ardour/public_editor.h b/gtk2_ardour/public_editor.h index e6f576352a..9994f422d4 100644 --- a/gtk2_ardour/public_editor.h +++ b/gtk2_ardour/public_editor.h @@ -117,14 +117,15 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulThingWithGoingAway virtual void set_snap_threshold (double t) = 0; /** Snap a value according to the current snap setting. */ - virtual void snap_to (nframes_t& first, int32_t direction = 0, bool for_mark = false) = 0; + virtual void snap_to (nframes64_t& first, int32_t direction = 0, bool for_mark = false) = 0; /** Get the current snap value in beats */ - virtual double snap_length_beats (nframes_t start) = 0; + virtual double snap_length_beats (nframes64_t start) = 0; /** Undo some transactions. * @param n Number of transactions to undo. */ + virtual void undo (uint32_t n = 1) = 0; /** Redo some transactions. @@ -188,8 +189,12 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulThingWithGoingAway virtual void toggle_playback (bool with_abort) = 0; virtual void transition_to_rolling (bool fwd) = 0; - virtual nframes_t unit_to_frame (double unit) const = 0; - virtual double frame_to_unit (nframes_t frame) const = 0; + virtual nframes64_t unit_to_frame (double unit) const = 0; + // XXX remove me when libardour goes nframes64_t + double frame_to_unit (nframes_t frame) const { + return frame_to_unit ((nframes64_t) frame); + } + virtual double frame_to_unit (nframes64_t frame) const = 0; virtual double frame_to_unit (double frame) const = 0; virtual nframes64_t pixel_to_frame (double pixel) const = 0; virtual gulong frame_to_pixel (nframes64_t frame) const = 0; @@ -225,7 +230,7 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulThingWithGoingAway virtual void select_all_tracks () = 0; virtual void set_selected_track (TimeAxisView&, Selection::Operation op = Selection::Set, bool no_remove = false) = 0; virtual void set_selected_mixer_strip (TimeAxisView&) = 0; - virtual void hide_track_in_display (TimeAxisView& tv) = 0; + virtual void hide_track_in_display (TimeAxisView& tv, bool temporary = false) = 0; virtual void show_track_in_display (TimeAxisView& tv) = 0; /** Set whether the editor should follow the playhead. @@ -244,22 +249,24 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulThingWithGoingAway virtual void ensure_float (Gtk::Window&) = 0; virtual void show_window () = 0; virtual TrackViewList* get_valid_views (TimeAxisView*, ARDOUR::RouteGroup* grp = 0) = 0; - virtual nframes_t leftmost_position () const = 0; - virtual nframes_t current_page_frames () const = 0; + virtual nframes64_t leftmost_position() const = 0; + virtual nframes64_t current_page_frames() const = 0; virtual void temporal_zoom_step (bool coarser) = 0; virtual void scroll_tracks_down_line () = 0; virtual void scroll_tracks_up_line () = 0; virtual bool new_regionviews_display_gain () = 0; virtual void prepare_for_cleanup () = 0; - virtual void reset_x_origin (nframes_t frame) = 0; + virtual void finish_cleanup () = 0; + virtual void reset_x_origin (nframes64_t frame) = 0; virtual void remove_last_capture () = 0; virtual void maximise_editing_space () = 0; virtual void restore_editing_space () = 0; virtual nframes64_t get_preferred_edit_position (bool ignore_playhead = false) = 0; virtual void toggle_meter_updating() = 0; virtual void split_region_at_points (boost::shared_ptr, ARDOUR::AnalysisFeatureList&, bool can_ferret) = 0; - virtual void mouse_add_new_marker (nframes_t where, bool is_cd=false, bool is_xrun=false) = 0; + virtual void mouse_add_new_marker (nframes64_t where, bool is_cd=false, bool is_xrun=false) = 0; virtual void foreach_time_axis_view (sigc::slot) = 0; + virtual void add_to_idle_resize (TimeAxisView*,uint32_t) = 0; #ifdef WITH_CMT virtual void add_imageframe_time_axis(const std::string & track_name, void*) = 0; @@ -277,7 +284,7 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulThingWithGoingAway sigc::signal ZoomChanged; sigc::signal Resized; sigc::signal Realized; - sigc::signal UpdateAllTransportClocks; + sigc::signal UpdateAllTransportClocks; Glib::RefPtr editor_actions; @@ -320,6 +327,15 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulThingWithGoingAway virtual bool canvas_markerview_end_handle_event(GdkEvent* event, ArdourCanvas::Item*,MarkerView*) = 0; #endif + virtual void queue_draw_resize_line (int at) = 0; + virtual void start_resize_line_ops () = 0; + virtual void end_resize_line_ops () = 0; + + static const int window_border_width; + static const int container_border_width; + static const int vertical_spacing; + static const int horizontal_spacing; + /// Singleton instance, set up by Editor::Editor() static PublicEditor* _instance; diff --git a/gtk2_ardour/region_view.cc b/gtk2_ardour/region_view.cc index fff7243f53..27f9c87819 100644 --- a/gtk2_ardour/region_view.cc +++ b/gtk2_ardour/region_view.cc @@ -64,7 +64,8 @@ RegionView::RegionView (ArdourCanvas::Group* parent, boost::shared_ptr r, double spu, Gdk::Color& basic_color) - : TimeAxisViewItem (r->name(), *parent, tv, spu, basic_color, r->position(), r->length(), + : TimeAxisViewItem (r->name(), *parent, tv, spu, basic_color, r->position(), r->length(), false, + TimeAxisViewItem::Visibility (TimeAxisViewItem::ShowNameText| TimeAxisViewItem::ShowNameHighlight| TimeAxisViewItem::ShowFrame)) @@ -87,11 +88,10 @@ RegionView::RegionView (const RegionView& other) /* derived concrete type will call init () */ _region = other._region; - editor = 0; current_visible_sync_position = other.current_visible_sync_position; valid = false; - _enable_display = false; _pixel_width = other._pixel_width; + _height = other._height; } RegionView::RegionView (const RegionView& other, boost::shared_ptr other_region) @@ -104,7 +104,6 @@ RegionView::RegionView (const RegionView& other, boost::shared_ptr other /* derived concrete type will call init () */ _region = other_region; - editor = other.editor; current_visible_sync_position = other.current_visible_sync_position; valid = false; _pixel_width = other._pixel_width; @@ -116,8 +115,9 @@ RegionView::RegionView (ArdourCanvas::Group* parent, boost::shared_ptr r, double spu, Gdk::Color& basic_color, + bool recording, TimeAxisViewItem::Visibility visibility) - : TimeAxisViewItem (r->name(), *parent, tv, spu, basic_color, r->position(), r->length(), visibility) + : TimeAxisViewItem (r->name(), *parent, tv, spu, basic_color, r->position(), r->length(), recording, visibility) , _region (r) , sync_mark(0) , sync_line(0) @@ -134,10 +134,11 @@ RegionView::RegionView (ArdourCanvas::Group* parent, void RegionView::init (Gdk::Color& basic_color, bool wfd) { - valid = true; - _enable_display = false; - in_destructor = false; - wait_for_data = wfd; + editor = 0; + valid = true; + in_destructor = false; + _height = 0; + wait_for_data = wfd; sync_mark = 0; sync_line = 0; sync_mark = 0; @@ -145,7 +146,10 @@ RegionView::init (Gdk::Color& basic_color, bool wfd) compute_colors (basic_color); - name_highlight->set_data ("regionview", this); + if (name_highlight) { + name_highlight->set_data ("regionview", this); + name_highlight->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_region_view_name_highlight_event), name_highlight, this)); + } if (name_text) { name_text->set_data ("regionview", this); @@ -154,17 +158,16 @@ RegionView::init (Gdk::Color& basic_color, bool wfd) if (wfd) _enable_display = true; - set_y_position_and_height (0, trackview.height - 2); + set_height (trackview.current_height()); _region->StateChanged.connect (mem_fun(*this, &RegionView::region_changed)); group->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_region_view_event), group, this)); - name_highlight->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_region_view_name_highlight_event), name_highlight, this)); set_colors (); ColorsChanged.connect (mem_fun (*this, &RegionView::color_handler)); - // set_pango_fontsize(); + /* XXX sync mark drag? */ } @@ -517,7 +520,7 @@ RegionView::region_sync_changed () points.clear (); points.push_back (Gnome::Art::Point (offset, 0)); - points.push_back (Gnome::Art::Point (offset, trackview.height - NAME_HIGHLIGHT_SIZE)); + points.push_back (Gnome::Art::Point (offset, trackview.current_height() - NAME_HIGHLIGHT_SIZE)); sync_line->property_points().set_value (points); sync_line->show (); diff --git a/gtk2_ardour/region_view.h b/gtk2_ardour/region_view.h index 19d13ccf03..579b6e5594 100644 --- a/gtk2_ardour/region_view.h +++ b/gtk2_ardour/region_view.h @@ -101,6 +101,7 @@ class RegionView : public TimeAxisViewItem boost::shared_ptr, double samples_per_unit, Gdk::Color& basic_color, + bool recording, TimeAxisViewItem::Visibility); virtual void region_resized (ARDOUR::Change); diff --git a/gtk2_ardour/rhythm_ferret.cc b/gtk2_ardour/rhythm_ferret.cc index 63440e7ab1..4a4f3d4ec4 100644 --- a/gtk2_ardour/rhythm_ferret.cc +++ b/gtk2_ardour/rhythm_ferret.cc @@ -4,6 +4,7 @@ #include #include +#include #include #include #include @@ -32,6 +33,17 @@ static const gchar * _analysis_mode_strings[] = { 0 }; +static const gchar * _onset_function_strings[] = { + N_("Energy Based"), + N_("Spectral Difference"), + N_("High-Frequency Content"), + N_("Complex Domain"), + N_("Phase Deviation"), + N_("Kullback-Liebler"), + N_("Modified Kullback-Liebler"), + 0 +}; + RhythmFerret::RhythmFerret (PublicEditor& e) : ArdourDialog (_("Rhythm Ferret")) , editor (e) @@ -50,6 +62,13 @@ RhythmFerret::RhythmFerret (PublicEditor& e) , sensitivity_scale (sensitivity_adjustment) , sensitivity_label (_("Sensitivity")) , analyze_button (_("Analyze")) + , onset_function_label (_("Detection function")) + , peak_picker_threshold_adjustment (0.3, 0.0, 1.0, 0.01, 0.1) + , peak_picker_threshold_scale (peak_picker_threshold_adjustment) + , peak_picker_label (_("Peak Threshold")) + , silence_threshold_adjustment (-90.0, -120.0, 0.0, 1, 10) + , silence_threshold_scale (silence_threshold_adjustment) + , silence_label (_("Silent Threshold (dB)")) , trigger_gap_adjustment (3, 0, 100, 1, 10) , trigger_gap_spinner (trigger_gap_adjustment) , trigger_gap_label (_("Trigger gap (msecs)")) @@ -78,6 +97,14 @@ RhythmFerret::RhythmFerret (PublicEditor& e) analysis_mode_strings = I18N (_analysis_mode_strings); Gtkmm2ext::set_popdown_strings (analysis_mode_selector, analysis_mode_strings); analysis_mode_selector.set_active_text (analysis_mode_strings.front()); + analysis_mode_selector.signal_changed().connect (mem_fun (*this, &RhythmFerret::analysis_mode_changed)); + + onset_function_strings = I18N (_onset_function_strings); + Gtkmm2ext::set_popdown_strings (onset_detection_function_selector, onset_function_strings); + /* Onset plugin uses complex domain as default function + XXX there should be a non-hacky way to set this + */ + onset_detection_function_selector.set_active_text (onset_function_strings[3]); box = manage (new HBox); box->set_spacing (6); @@ -85,28 +112,50 @@ RhythmFerret::RhythmFerret (PublicEditor& e) box->pack_start (analysis_mode_selector, true, true); ferret_packer.pack_start (*box, false, false); + ferret_packer.pack_start (analysis_packer, false, false); + box = manage (new HBox); box->set_spacing (6); - box->pack_start (detection_threshold_label, false, false); - box->pack_start (detection_threshold_scale, true, true); + box->pack_start (trigger_gap_label, false, false); + box->pack_start (trigger_gap_spinner, false, false); ferret_packer.pack_start (*box, false, false); + ferret_packer.pack_start (analyze_button, false, false); + + analyze_button.signal_clicked().connect (mem_fun (*this, &RhythmFerret::run_analysis)); + + box = manage (new HBox); + box->set_spacing (6); + box->pack_start (detection_threshold_label, false, false); + box->pack_start (detection_threshold_scale, true, true); + perc_onset_packer.pack_start (*box, false, false); + box = manage (new HBox); box->set_spacing (6); box->pack_start (sensitivity_label, false, false); box->pack_start (sensitivity_scale, true, true); - ferret_packer.pack_start (*box, false, false); + perc_onset_packer.pack_start (*box, false, false); box = manage (new HBox); box->set_spacing (6); - box->pack_start (trigger_gap_label, false, false); - box->pack_start (trigger_gap_spinner, false, false); - ferret_packer.pack_start (*box, false, false); + box->pack_start (onset_function_label, false, false); + box->pack_start (onset_detection_function_selector, true, true); + note_onset_packer.pack_start (*box, false, false); + + box = manage (new HBox); + box->set_spacing (6); + box->pack_start (peak_picker_label, false, false); + box->pack_start (peak_picker_threshold_scale, true, true); + note_onset_packer.pack_start (*box, false, false); + + box = manage (new HBox); + box->set_spacing (6); + box->pack_start (silence_label, false, false); + box->pack_start (silence_threshold_scale, true, true); + note_onset_packer.pack_start (*box, false, false); - ferret_packer.pack_start (analyze_button, false, false); + analysis_mode_changed (); - analyze_button.signal_clicked().connect (mem_fun (*this, &RhythmFerret::run_analysis)); - ferret_frame.add (ferret_packer); logo = manage (new Gtk::Image (::get_icon (X_("ferret_02")))); @@ -137,12 +186,30 @@ RhythmFerret::~RhythmFerret() } } +void +RhythmFerret::analysis_mode_changed () +{ + analysis_packer.children().clear (); + + switch (get_analysis_mode()) { + case PercussionOnset: + analysis_packer.pack_start (perc_onset_packer); + break; + + case NoteOnset: + analysis_packer.pack_start (note_onset_packer); + break; + } + + analysis_packer.show_all (); +} + RhythmFerret::AnalysisMode RhythmFerret::get_analysis_mode () const { string str = analysis_mode_selector.get_active_text (); - if (str == _(_analysis_mode_strings[(int) NoteOnset])) { + if (str == analysis_mode_strings[(int) NoteOnset]) { return NoteOnset; } @@ -184,6 +251,9 @@ RhythmFerret::run_analysis () case PercussionOnset: run_percussion_onset_analysis (rd, (*i)->region()->position(), current_results); break; + case NoteOnset: + run_note_onset_analysis (rd, (*i)->region()->position(), current_results); + break; default: break; } @@ -232,6 +302,67 @@ RhythmFerret::run_percussion_onset_analysis (boost::shared_ptr readabl return 0; } +int +RhythmFerret::get_note_onset_function () +{ + string txt = onset_detection_function_selector.get_active_text(); + + for (int n = 0; _onset_function_strings[n]; ++n) { + /* compare translated versions */ + if (txt == onset_function_strings[n]) { + return n; + } + } + fatal << string_compose (_("programming error: %1 (%2)"), X_("illegal note onset function string"), txt) + << endmsg; + /*NOTREACHED*/ + return -1; +} + +int +RhythmFerret::run_note_onset_analysis (boost::shared_ptr readable, nframes64_t offset, AnalysisFeatureList& results) +{ + try { + OnsetDetector t (session->frame_rate()); + + for (uint32_t i = 0; i < readable->n_channels(); ++i) { + + AnalysisFeatureList these_results; + + t.reset (); + + t.set_function (get_note_onset_function()); + t.set_silence_threshold (silence_threshold_adjustment.get_value()); + t.set_peak_threshold (peak_picker_threshold_adjustment.get_value()); + + if (t.run ("", readable.get(), i, these_results)) { + continue; + } + + /* translate all transients to give absolute position */ + + for (AnalysisFeatureList::iterator x = these_results.begin(); x != these_results.end(); ++x) { + (*x) += offset; + } + + /* merge */ + + results.insert (results.end(), these_results.begin(), these_results.end()); + these_results.clear (); + } + + } catch (failed_constructor& err) { + error << "Could not load note onset detection plugin" << endmsg; + return -1; + } + + if (!results.empty()) { + OnsetDetector::cleanup_onsets (results, session->frame_rate(), trigger_gap_adjustment.get_value()); + } + + return 0; +} + void RhythmFerret::do_action () { @@ -277,6 +408,7 @@ RhythmFerret::do_split_action () i = tmp; } + session->commit_reversible_command (); } diff --git a/gtk2_ardour/rhythm_ferret.h b/gtk2_ardour/rhythm_ferret.h index 2ddb2a4ffd..91c10695ad 100644 --- a/gtk2_ardour/rhythm_ferret.h +++ b/gtk2_ardour/rhythm_ferret.h @@ -71,6 +71,9 @@ class RhythmFerret : public ArdourDialog { Gtk::VBox ferret_packer; Gtk::ComboBoxText analysis_mode_selector; Gtk::Label analysis_mode_label; + + /* transient detection widgets */ + Gtk::Adjustment detection_threshold_adjustment; Gtk::HScale detection_threshold_scale; Gtk::Label detection_threshold_label; @@ -78,22 +81,44 @@ class RhythmFerret : public ArdourDialog { Gtk::HScale sensitivity_scale; Gtk::Label sensitivity_label; Gtk::Button analyze_button; + Gtk::VBox perc_onset_packer; + + /* onset detection widgets */ + + Gtk::ComboBoxText onset_detection_function_selector; + Gtk::Label onset_function_label; + Gtk::Adjustment peak_picker_threshold_adjustment; + Gtk::HScale peak_picker_threshold_scale; + Gtk::Label peak_picker_label; + Gtk::Adjustment silence_threshold_adjustment; + Gtk::HScale silence_threshold_scale; + Gtk::Label silence_label; + Gtk::VBox note_onset_packer; + + /* generic stuff */ + Gtk::Adjustment trigger_gap_adjustment; Gtk::SpinButton trigger_gap_spinner; Gtk::Label trigger_gap_label; + Gtk::VBox analysis_packer; + Gtk::Label operation_clarification_label; Gtk::Button action_button; std::vector analysis_mode_strings; + std::vector onset_function_strings; ARDOUR::AnalysisFeatureList current_results; AnalysisMode get_analysis_mode () const; Action get_action() const; + void analysis_mode_changed (); + int get_note_onset_function (); void run_analysis (); int run_percussion_onset_analysis (boost::shared_ptr region, nframes64_t offset, ARDOUR::AnalysisFeatureList& results); + int run_note_onset_analysis (boost::shared_ptr region, nframes64_t offset, ARDOUR::AnalysisFeatureList& results); void do_action (); void do_split_action (); diff --git a/gtk2_ardour/route_params_ui.cc b/gtk2_ardour/route_params_ui.cc index 497e99ba61..f39d41def5 100644 --- a/gtk2_ardour/route_params_ui.cc +++ b/gtk2_ardour/route_params_ui.cc @@ -235,10 +235,10 @@ RouteParams_UI::setup_processor_boxes() pre_redir_hpane.pack1 (*pre_insert_box); post_redir_hpane.pack1 (*post_insert_box); - pre_insert_box->InsertSelected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PreFader)); - pre_insert_box->InsertUnselected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PreFader)); - post_insert_box->InsertSelected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PostFader)); - post_insert_box->InsertUnselected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PostFader)); + pre_insert_box->ProcessorSelected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PreFader)); + pre_insert_box->ProcessorUnselected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PreFader)); + post_insert_box->ProcessorSelected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PostFader)); + post_insert_box->ProcessorUnselected.connect (bind (mem_fun(*this, &RouteParams_UI::redirect_selected), PostFader)); pre_redir_hpane.show_all(); post_redir_hpane.show_all(); diff --git a/gtk2_ardour/route_time_axis.cc b/gtk2_ardour/route_time_axis.cc index a5619b8ae9..82777944f4 100644 --- a/gtk2_ardour/route_time_axis.cc +++ b/gtk2_ardour/route_time_axis.cc @@ -87,11 +87,12 @@ using namespace std; Glib::RefPtr RouteTimeAxisView::slider; -int +void RouteTimeAxisView::setup_slider_pix () { - slider = ::get_icon ("fader_belt_h"); - return 0; + if ((slider = ::get_icon ("fader_belt_h")) == 0) { + throw failed_constructor (); + } } RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::shared_ptr rt, Canvas& canvas) @@ -105,18 +106,12 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::sh size_button (_("h")), // height automation_button (_("a")), visual_button (_("v")), - lm (rt, sess), - underlay_xml_node (0), - gain_slider (0), - gain_adjustment (0.781787, 0.0, 1.0, 0.01, 0.1) + gm (rt, sess, slider, true) { - if (slider == 0) { - setup_slider_pix (); - } + gm.get_level_meter().set_no_show_all(); + gm.get_level_meter().setup_meters(50); - lm.set_no_show_all(); - lm.setup_meters(50); _has_state = true; playlist_menu = 0; playlist_action_menu = 0; @@ -127,8 +122,6 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::sh destructive_track_mode_item = 0; normal_track_mode_item = 0; - gain_slider = manage (new HSliderController (slider, &gain_adjustment, *_route->gain_control().get(), false)); - ignore_toggle = false; edit_group_button.set_name ("TrackGroupButton"); @@ -175,7 +168,7 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::sh } - controls_hbox.pack_start(lm, false, false); + controls_hbox.pack_start(gm.get_level_meter(), false, false); _route->meter_change.connect (mem_fun(*this, &RouteTimeAxisView::meter_changed)); _route->input_changed.connect (mem_fun(*this, &RouteTimeAxisView::io_changed)); _route->output_changed.connect (mem_fun(*this, &RouteTimeAxisView::io_changed)); @@ -184,7 +177,7 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::sh controls_table.attach (*solo_button, 7, 8, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); controls_table.attach (edit_group_button, 7, 8, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); - controls_table.attach (*gain_slider, 0, 5, 1, 2, Gtk::SHRINK, Gtk::SHRINK, 0, 0); + controls_table.attach (gm.get_gain_slider(), 0, 5, 1, 2, Gtk::SHRINK, Gtk::SHRINK, 0, 0); ARDOUR_UI::instance()->tooltips().set_tip(*solo_button,_("Solo")); ARDOUR_UI::instance()->tooltips().set_tip(*mute_button,_("Mute")); @@ -239,14 +232,8 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::sh editor.ZoomChanged.connect (mem_fun(*this, &RouteTimeAxisView::reset_samples_per_unit)); ColorsChanged.connect (mem_fun (*this, &RouteTimeAxisView::color_handler)); - gain_slider->signal_button_press_event().connect (mem_fun(*this, &RouteTimeAxisView::start_gain_touch)); - gain_slider->signal_button_release_event().connect (mem_fun(*this, &RouteTimeAxisView::end_gain_touch)); - gain_slider->set_name ("TrackGainFader"); - - gain_adjustment.signal_value_changed().connect (mem_fun(*this, &RouteTimeAxisView::gain_adjusted)); - _route->gain_control()->Changed.connect (mem_fun(*this, &RouteTimeAxisView::gain_changed)); - - gain_slider->show_all(); + gm.get_gain_slider().signal_scroll_event().connect(mem_fun(*this, &RouteTimeAxisView::controls_ebox_scroll), false); + gm.get_gain_slider().set_name ("TrackGainFader"); } RouteTimeAxisView::~RouteTimeAxisView () @@ -285,6 +272,7 @@ RouteTimeAxisView::post_construct () /* map current state of the route */ update_diskstream_display (); + subplugin_menu.items().clear (); _route->foreach_processor (this, &RouteTimeAxisView::add_processor_to_subplugin_menu); _route->foreach_processor (this, &RouteTimeAxisView::add_existing_processor_automation_curves); @@ -306,69 +294,6 @@ RouteTimeAxisView::playlist_modified () { } -void -RouteTimeAxisView::set_state (const XMLNode& node) -{ - const XMLProperty *prop; - - TimeAxisView::set_state (node); - - if ((prop = node.property ("shown_editor")) != 0) { - if (prop->value() == "no") { - _marked_for_display = false; - } else { - _marked_for_display = true; - } - } else { - _marked_for_display = true; - } - - XMLNodeList nlist = node.children(); - XMLNodeConstIterator niter; - XMLNode *child_node; - - _show_automation.clear(); - - for (niter = nlist.begin(); niter != nlist.end(); ++niter) { - child_node = *niter; - - if (child_node->name() == AutomationTimeAxisView::state_node_name) { - XMLProperty* prop = child_node->property ("automation-id"); - if (!prop) - continue; - - Parameter param(prop->value()); - if (!param) - continue; - - bool show = false; - - prop = child_node->property ("shown"); - - if (prop && prop->value() == "yes") { - show = true; - _show_automation.insert(param); - } - - if (_automation_tracks.find(param) == _automation_tracks.end()) { - create_automation_child(param, show); - } - } - else if (child_node->name() == "Underlays") { - underlay_xml_node = child_node; - - /* Wait for all gui tracks to be loaded as underlays are cross referencing tracks*/ - Glib::signal_idle().connect(mem_fun(*this, &RouteTimeAxisView::set_underlay_state)); - } - } -} - -XMLNode* -RouteTimeAxisView::get_automation_child_xml_node (Parameter param) -{ - return RouteUI::get_automation_child_xml_node (param); -} - gint RouteTimeAxisView::edit_click (GdkEventButton *ev) { @@ -632,6 +557,7 @@ RouteTimeAxisView::build_display_menu () route_active_menu_item->set_active (_route->active()); items.push_back (SeparatorElem()); + items.push_back (MenuElem (_("Hide"), mem_fun(*this, &RouteTimeAxisView::hide_click))); items.push_back (MenuElem (_("Remove"), mem_fun(*this, &RouteUI::remove_this_route))); } @@ -768,7 +694,7 @@ RouteTimeAxisView::show_timestretch (nframes_t start, nframes_t end) x1 = start / editor.get_current_zoom(); x2 = (end - 1) / editor.get_current_zoom(); - y2 = height - 2; + y2 = current_height() - 2; timestretch_rect->property_x1() = x1; timestretch_rect->property_y1() = 1.0; @@ -807,55 +733,30 @@ RouteTimeAxisView::show_selection (TimeSelection& ts) } void -RouteTimeAxisView::set_height (TrackHeight h) +RouteTimeAxisView::set_height (uint32_t h) { - int gmlen = (height_to_pixels (h)) - 5; - bool height_changed = (height == 0) || (h != height_style); - lm.setup_meters (gmlen); + int gmlen = h - 5; + bool height_changed = (height == 0) || (h != height); + gm.get_level_meter().setup_meters (gmlen); + TimeAxisView::set_height (h); ensure_xml_node (); if (_view) { - _view->set_height ((double) height); + _view->set_height ((double) current_height()); } - switch (height_style) { - case Largest: - xml_node->add_property ("track_height", "largest"); - break; - - case Large: - xml_node->add_property ("track_height", "large"); - break; - - case Larger: - xml_node->add_property ("track_height", "larger"); - break; + char buf[32]; + snprintf (buf, sizeof (buf), "%u", height); + xml_node->add_property ("height", buf); - case Normal: - xml_node->add_property ("track_height", "normal"); - break; - - case Smaller: - xml_node->add_property ("track_height", "smaller"); - break; - - case Small: - xml_node->add_property ("track_height", "small"); - break; - } - - switch (height_style) { - case Largest: - case Large: - case Larger: - case Normal: + if (height >= hNormal) { reset_meter(); show_name_entry (); hide_name_label (); - gain_slider->show(); + gm.get_gain_slider().show(); mute_button->show(); solo_button->show(); if (rec_enable_button) @@ -870,14 +771,14 @@ RouteTimeAxisView::set_height (TrackHeight h) if (is_track() && track()->mode() == ARDOUR::Normal) { playlist_button.show(); } - break; - case Smaller: + } else if (height >= hSmaller) { + reset_meter(); show_name_entry (); hide_name_label (); - gain_slider->hide(); + gm.get_gain_slider().hide(); mute_button->show(); solo_button->show(); if (rec_enable_button) @@ -892,13 +793,13 @@ RouteTimeAxisView::set_height (TrackHeight h) if (is_track() && track()->mode() == ARDOUR::Normal) { playlist_button.hide (); } - break; - case Small: + } else { + hide_name_entry (); show_name_label (); - - gain_slider->hide(); + + gm.get_gain_slider().hide(); mute_button->hide(); solo_button->hide(); if (rec_enable_button) @@ -911,7 +812,6 @@ RouteTimeAxisView::set_height (TrackHeight h) automation_button.hide (); playlist_button.hide (); name_label.set_text (_route->name()); - break; } if (height_changed) { @@ -1630,7 +1530,7 @@ RouteTimeAxisView::automation_track_hidden (Parameter param) ran->menu_item->set_active (false); } - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ } @@ -1664,10 +1564,9 @@ RouteTimeAxisView::show_all_automation () no_redraw = false; - /* Redraw */ - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ } void @@ -1699,8 +1598,8 @@ RouteTimeAxisView::show_existing_automation () } no_redraw = false; - - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ } void @@ -1728,7 +1627,7 @@ RouteTimeAxisView::hide_all_automation () _show_automation.clear(); no_redraw = false; - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ } @@ -1869,7 +1768,7 @@ RouteTimeAxisView::processor_automation_track_hidden (RouteTimeAxisView::Process i->mark_automation_visible (pan->what, false); - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ } void @@ -1902,7 +1801,7 @@ RouteTimeAxisView::add_automation_child(Parameter param, boost::shared_ptrHiding.connect (bind (mem_fun (*this, &RouteTimeAxisView::automation_track_hidden), param)); bool hideit = (!show); - + XMLNode* node; if ((node = track->get_state_node()) != 0) { @@ -1918,8 +1817,11 @@ RouteTimeAxisView::add_automation_child(Parameter param, boost::shared_ptrhide (); } else { - _show_automation.insert(param); - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _show_automation.insert (param); + + if (!no_redraw) { + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ + } } build_display_menu(); @@ -2041,7 +1943,7 @@ RouteTimeAxisView::processor_menu_item_toggled (RouteTimeAxisView::ProcessorAuto /* now trigger a redisplay */ - _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("visible_tracks", (void *) 0); /* EMIT_SIGNAL */ } } @@ -2079,7 +1981,7 @@ RouteTimeAxisView::processors_changed () /* change in visibility was possible */ - _route->gui_changed ("track_height", this); + _route->gui_changed ("visible_tracks", this); } boost::shared_ptr @@ -2131,14 +2033,14 @@ RouteTimeAxisView::automation_child(ARDOUR::Parameter param) void RouteTimeAxisView::fast_update () { - lm.update_meters (); + gm.get_level_meter().update_meters (); } void RouteTimeAxisView::hide_meter () { clear_meter (); - lm.hide_meters (); + gm.get_level_meter().hide_meters (); } void @@ -2151,7 +2053,7 @@ void RouteTimeAxisView::reset_meter () { if (Config->get_show_track_meters()) { - lm.setup_meters (height-5); + gm.get_level_meter().setup_meters (height-5); } else { hide_meter (); } @@ -2160,7 +2062,7 @@ RouteTimeAxisView::reset_meter () void RouteTimeAxisView::clear_meter () { - lm.clear_meters (); + gm.get_level_meter().clear_meters (); } void @@ -2290,36 +2192,3 @@ RouteTimeAxisView::remove_underlay(StreamView* v) } } -gint -RouteTimeAxisView::start_gain_touch (GdkEventButton* ev) -{ - _route->gain_control()->list()->start_touch (); - return FALSE; -} - -gint -RouteTimeAxisView::end_gain_touch (GdkEventButton* ev) -{ - _route->gain_control()->list()->stop_touch (); - return FALSE; -} - -void -RouteTimeAxisView::gain_adjusted () -{ - _route->set_gain (slider_position_to_gain (gain_adjustment.get_value()), this); -} - -void -RouteTimeAxisView::gain_changed () -{ - Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &RouteTimeAxisView::effective_gain_display)); -} - -void -RouteTimeAxisView::effective_gain_display () -{ - gfloat value = gain_to_slider_position (_route->effective_gain()); - gain_adjustment.set_value (value); -} - diff --git a/gtk2_ardour/route_time_axis.h b/gtk2_ardour/route_time_axis.h index e318451832..230ea45b86 100644 --- a/gtk2_ardour/route_time_axis.h +++ b/gtk2_ardour/route_time_axis.h @@ -40,7 +40,7 @@ #include "enums.h" #include "time_axis_view.h" #include "canvas.h" -#include "level_meter.h" +#include "gain_meter.h" namespace ARDOUR { @@ -74,7 +74,7 @@ public: void show_selection (TimeSelection&); void set_samples_per_unit (double); - void set_height (TimeAxisView::TrackHeight); + void set_height (uint32_t h); void show_timestretch (nframes_t start, nframes_t end); void hide_timestretch (); void selection_click (GdkEventButton*); @@ -117,6 +117,10 @@ public: virtual void create_automation_child (ARDOUR::Parameter param, bool show) = 0; + /* make sure we get the right version of this */ + + XMLNode* get_automation_child_xml_node (ARDOUR::Parameter param) { return RouteUI::get_automation_child_xml_node (param); } + typedef map AutomationTracks; AutomationTracks automation_tracks() { return _automation_tracks; } @@ -134,7 +138,9 @@ public: void clear_meter (); void io_changed (ARDOUR::IOChange, void *); void meter_changed (void *); - void effective_gain_display (); + void effective_gain_display () { gm.effective_gain_display(); } + + static void setup_slider_pix (); protected: friend class StreamView; @@ -297,11 +303,9 @@ protected: void post_construct (); - void set_state (const XMLNode&); - - XMLNode* get_automation_child_xml_node (ARDOUR::Parameter param); + GainMeterBase gm; - LevelMeter lm; + static Glib::RefPtr slider; XMLNode* underlay_xml_node; bool set_underlay_state(); @@ -310,16 +314,6 @@ protected: UnderlayList _underlay_streams; typedef list UnderlayMirrorList; UnderlayMirrorList _underlay_mirrors; - - Gtkmm2ext::HSliderController *gain_slider; - Gtk::Adjustment gain_adjustment; - static Glib::RefPtr slider; - static int setup_slider_pix (); - void gain_adjusted(); - - gint start_gain_touch (GdkEventButton*); - gint end_gain_touch (GdkEventButton*); - void gain_changed (); }; #endif /* __ardour_route_time_axis_h__ */ diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 9c88bec37c..4d1d92ac5a 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -81,10 +81,10 @@ RouteUI::RouteUI (boost::shared_ptr rt, ARDOUR::Session& sess, co _route->active_changed.connect (mem_fun (*this, &RouteUI::route_active_changed)); - mute_button = manage (new BindableToggleButton (*_route->mute_control().get(), m_name )); + mute_button = manage (new BindableToggleButton (_route->mute_control(), m_name )); mute_button->set_self_managed (true); - solo_button = manage (new BindableToggleButton (*_route->solo_control().get(), s_name )); + solo_button = manage (new BindableToggleButton (_route->solo_control(), s_name )); solo_button->set_self_managed (true); mute_button->set_name ("MuteButton"); @@ -105,7 +105,7 @@ RouteUI::RouteUI (boost::shared_ptr rt, ARDOUR::Session& sess, co _session.RecordStateChanged.connect (mem_fun (*this, &RouteUI::session_rec_enable_changed)); - rec_enable_button = manage (new BindableToggleButton (*t->rec_enable_control().get(), r_name )); + rec_enable_button = manage (new BindableToggleButton (t->rec_enable_control(), r_name )); rec_enable_button->set_name ("RecordEnableButton"); rec_enable_button->set_self_managed (true); diff --git a/gtk2_ardour/route_ui.h b/gtk2_ardour/route_ui.h index 20ac152f83..aecf351f3a 100644 --- a/gtk2_ardour/route_ui.h +++ b/gtk2_ardour/route_ui.h @@ -124,10 +124,6 @@ class RouteUI : public virtual AxisView int set_color_from_route (); - sigc::connection blink_connection; - - void rec_enable_button_blink (bool onoff, ARDOUR::AudioDiskstream *, Gtk::Widget *w); - void remove_this_route (); static gint idle_remove_this_route (RouteUI *); diff --git a/gtk2_ardour/send_ui.cc b/gtk2_ardour/send_ui.cc index c91068f97c..90ff3de717 100644 --- a/gtk2_ardour/send_ui.cc +++ b/gtk2_ardour/send_ui.cc @@ -44,7 +44,7 @@ SendUI::SendUI (boost::shared_ptr s, Session& se) vbox.pack_start (hbox, false, false, false); vbox.pack_start (panners, false,false); - io = new IOSelector (se, s->io(), false); + io = manage (new IOSelector (se, s->io(), false)); pack_start (vbox, false, false); @@ -70,7 +70,7 @@ SendUI::SendUI (boost::shared_ptr s, Session& se) SendUI::~SendUI () { _send->set_metering (false); - + /* XXX not clear that we need to do this */ screen_update_connection.disconnect(); @@ -121,8 +121,8 @@ SendUIWindow::SendUIWindow (boost::shared_ptr s, Session& ss) add (vpacker); set_name ("SendUIWindow"); - - s->GoingAway.connect (mem_fun (*this, &SendUIWindow::send_going_away)); + + going_away_connection = s->GoingAway.connect (mem_fun (*this, &SendUIWindow::send_going_away)); signal_delete_event().connect (bind (ptr_fun (just_hide_it), reinterpret_cast (this))); @@ -138,5 +138,6 @@ SendUIWindow::send_going_away () { ENSURE_GUI_THREAD (mem_fun (*this, &SendUIWindow::send_going_away)); delete_when_idle (this); + going_away_connection.disconnect (); } diff --git a/gtk2_ardour/send_ui.h b/gtk2_ardour/send_ui.h index 0cd4b1a265..5a7298c515 100644 --- a/gtk2_ardour/send_ui.h +++ b/gtk2_ardour/send_ui.h @@ -42,6 +42,8 @@ class SendUI : public Gtk::HBox IOSelector* io; + boost::shared_ptr& send() { return _send; } + private: boost::shared_ptr _send; ARDOUR::Session& _session; @@ -70,6 +72,7 @@ class SendUIWindow : public Gtk::Window Gtk::HBox hpacker; void send_going_away (); + sigc::connection going_away_connection; }; #endif /* __ardour_gtk_send_ui_h__ */ diff --git a/gtk2_ardour/sfdb_ui.cc b/gtk2_ardour/sfdb_ui.cc index b7b853ebec..77c7f59afc 100644 --- a/gtk2_ardour/sfdb_ui.cc +++ b/gtk2_ardour/sfdb_ui.cc @@ -404,16 +404,19 @@ SoundFileBrowser::SoundFileBrowser (Gtk::Window& parent, string title, ARDOUR::S found_list_view (found_list), freesound_search_btn (_("Start Downloading")), freesound_list_view (freesound_list) - { resetting_ourselves = false; gm = 0; + resetting_ourselves = false; + gm = 0; + if (ARDOUR::Profile->get_sae()) { chooser.add_shortcut_folder_uri("file:///Library/GarageBand/Apple Loops"); chooser.add_shortcut_folder_uri("file:///Library/Application Support/GarageBand/Instrument Library/Sampler/Sampler Files"); } + //add the file chooser { chooser.set_border_width (12); @@ -426,14 +429,14 @@ SoundFileBrowser::SoundFileBrowser (Gtk::Window& parent, string title, ARDOUR::S matchall_filter.add_pattern ("*.*"); matchall_filter.set_name (_("All files")); - + chooser.add_filter (audio_filter); chooser.add_filter (midi_filter); chooser.add_filter (matchall_filter); chooser.set_select_multiple (true); chooser.signal_update_preview().connect(mem_fun(*this, &SoundFileBrowser::update_preview)); chooser.signal_file_activated().connect (mem_fun (*this, &SoundFileBrowser::chooser_file_activated)); - + if (!persistent_folder.empty()) { chooser.set_current_folder (persistent_folder); } @@ -445,11 +448,6 @@ SoundFileBrowser::SoundFileBrowser (Gtk::Window& parent, string title, ARDOUR::S VBox* vbox; HBox* hbox; - hpacker.set_spacing (6); - hpacker.pack_start (notebook, true, true); - hpacker.pack_start (preview, false, false); - - get_vbox()->pack_start (hpacker, true, true); hbox = manage(new HBox); hbox->pack_start (found_entry); @@ -474,7 +472,6 @@ SoundFileBrowser::SoundFileBrowser (Gtk::Window& parent, string title, ARDOUR::S notebook.append_page (*vbox, _("Search Tags")); } - //add freesound search #ifdef FREESOUND @@ -483,12 +480,6 @@ SoundFileBrowser::SoundFileBrowser (Gtk::Window& parent, string title, ARDOUR::S HBox* passbox; Label* label; - hpacker.set_spacing (6); - hpacker.pack_start (notebook, true, true); - hpacker.pack_start (preview, false, false); - - get_vbox()->pack_start (hpacker, true, true); - passbox = manage(new HBox); passbox->set_border_width (12); passbox->set_spacing (6); @@ -522,10 +513,8 @@ SoundFileBrowser::SoundFileBrowser (Gtk::Window& parent, string title, ARDOUR::S //freesound_list_view.get_selection()->set_mode (SELECTION_MULTIPLE); freesound_list_view.signal_row_activated().connect (mem_fun (*this, &SoundFileBrowser::freesound_list_view_activated)); - freesound_search_btn.signal_clicked().connect(mem_fun(*this, &SoundFileBrowser::freesound_search_clicked)); freesound_entry.signal_activate().connect(mem_fun(*this, &SoundFileBrowser::freesound_search_clicked)); - notebook.append_page (*vbox, _("Search Freesound")); } #endif @@ -1083,11 +1072,9 @@ SoundFileOmega::check_info (const vector& paths, bool& same_size, bool& for (vector::const_iterator i = paths.begin(); i != paths.end(); ++i) { if (AudioFileSource::get_soundfile_info (*i, info, errmsg)) { - if (info.channels > 1) { multichannel = true; } - if (sz == 0) { sz = info.length; } else { diff --git a/gtk2_ardour/sfdb_ui.h b/gtk2_ardour/sfdb_ui.h index a0be66493c..24cb08cc1b 100644 --- a/gtk2_ardour/sfdb_ui.h +++ b/gtk2_ardour/sfdb_ui.h @@ -150,6 +150,7 @@ class SoundFileBrowser : public ArdourDialog Gtk::FileFilter audio_filter; Gtk::FileFilter midi_filter; + Gtk::FileFilter custom_filter; Gtk::FileFilter matchall_filter; Gtk::HBox hpacker; diff --git a/gtk2_ardour/streamview.cc b/gtk2_ardour/streamview.cc index 46cb078c63..0f52f07939 100644 --- a/gtk2_ardour/streamview.cc +++ b/gtk2_ardour/streamview.cc @@ -66,7 +66,7 @@ StreamView::StreamView (RouteTimeAxisView& tv, ArdourCanvas::Group* group) canvas_rect->property_x1() = 0.0; canvas_rect->property_y1() = 0.0; canvas_rect->property_x2() = _trackview.editor.frame_to_pixel (max_frames); - canvas_rect->property_y2() = (double) tv.height; + canvas_rect->property_y2() = (double) tv.current_height(); canvas_rect->property_outline_what() = (guint32) (0x2|0x8); // outline RHS and bottom // (Fill/Outline colours set in derived classes) diff --git a/gtk2_ardour/streamview.h b/gtk2_ardour/streamview.h index cb7a3332cd..7cb5830dcb 100644 --- a/gtk2_ardour/streamview.h +++ b/gtk2_ardour/streamview.h @@ -112,7 +112,7 @@ protected: void update_rec_box (); //virtual void update_rec_regions () = 0; - virtual RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_data) = 0; + virtual RegionView* add_region_view_internal (boost::shared_ptr, bool wait_for_waves, bool recording = false) = 0; virtual void remove_region_view (boost::weak_ptr ); //void remove_rec_region (boost::shared_ptr); (unused) diff --git a/gtk2_ardour/tape_region_view.cc b/gtk2_ardour/tape_region_view.cc index 9791d0a7aa..21bc41800e 100644 --- a/gtk2_ardour/tape_region_view.cc +++ b/gtk2_ardour/tape_region_view.cc @@ -53,7 +53,7 @@ TapeAudioRegionView::TapeAudioRegionView (ArdourCanvas::Group *parent, RouteTime double spu, Gdk::Color& basic_color) - : AudioRegionView (parent, tv, r, spu, basic_color, + : AudioRegionView (parent, tv, r, spu, basic_color, false, TimeAxisViewItem::Visibility ((r->position() != 0) ? default_tape_visibility : TimeAxisViewItem::Visibility (default_tape_visibility|TimeAxisViewItem::HideFrameLeft))) { diff --git a/gtk2_ardour/time_axis_view.cc b/gtk2_ardour/time_axis_view.cc index 3259ac8a28..0973fb9c93 100644 --- a/gtk2_ardour/time_axis_view.cc +++ b/gtk2_ardour/time_axis_view.cc @@ -74,7 +74,6 @@ bool TimeAxisView::need_size_info = true; TimeAxisView::TimeAxisView (ARDOUR::Session& sess, PublicEditor& ed, TimeAxisView* rent, Canvas& canvas) : AxisView (sess), editor (ed), - height_style(Small), y_position(0), order(0), controls_table (2, 8) @@ -105,6 +104,7 @@ TimeAxisView::TimeAxisView (ARDOUR::Session& sess, PublicEditor& ed, TimeAxisVie _has_state = false; last_name_entry_key_press_event = 0; name_packing = NamePackingBits (0); + resize_drag_start = -1; /* Create the standard LHS Controls @@ -140,7 +140,23 @@ TimeAxisView::TimeAxisView (ARDOUR::Session& sess, PublicEditor& ed, TimeAxisVie controls_table.show_all (); controls_table.set_no_show_all (); + resizer.set_size_request (10, 10); + resizer.set_name ("ResizeHandle"); + resizer.signal_expose_event().connect (mem_fun (*this, &TimeAxisView::resizer_expose)); + resizer.signal_button_press_event().connect (mem_fun (*this, &TimeAxisView::resizer_button_press)); + resizer.signal_button_release_event().connect (mem_fun (*this, &TimeAxisView::resizer_button_release)); + resizer.signal_motion_notify_event().connect (mem_fun (*this, &TimeAxisView::resizer_motion)); + resizer.set_events (Gdk::BUTTON_PRESS_MASK| + Gdk::BUTTON_RELEASE_MASK| + Gdk::POINTER_MOTION_MASK| + Gdk::SCROLL_MASK); + + resizer_box.pack_start (resizer, false, false); + resizer.show (); + resizer_box.show(); + controls_vbox.pack_start (controls_table, false, false); + controls_vbox.pack_end (resizer_box, false, true); controls_vbox.show (); //controls_ebox.set_name ("TimeAxisViewControlsBaseUnselected"); @@ -238,9 +254,9 @@ TimeAxisView::show_at (double y, int& nth, VBox *parent) _hidden = false; /* height in pixels depends on _order, so update it now we've changed _order */ - set_height (height_style); + set_height (height); - effective_height = height; + effective_height = current_height(); /* now show children */ @@ -267,6 +283,9 @@ TimeAxisView::controls_ebox_scroll (GdkEventScroll* ev) if (Keyboard::modifier_state_equals (ev->state, Keyboard::TertiaryModifier)) { step_height (true); return true; + } else if (Keyboard::no_modifiers_active (ev->state)) { + editor.scroll_tracks_up_line(); + return true; } break; @@ -274,6 +293,9 @@ TimeAxisView::controls_ebox_scroll (GdkEventScroll* ev) if (Keyboard::modifier_state_equals (ev->state, Keyboard::TertiaryModifier)) { step_height (false); return true; + } else if (Keyboard::no_modifiers_active (ev->state)) { + editor.scroll_tracks_down_line(); + return true; } break; @@ -338,39 +360,21 @@ TimeAxisView::hide () void TimeAxisView::step_height (bool bigger) { - - if (height == hLargest) { - if (!bigger) set_height (Large); - return; - } - if (height == hLarge) { - if (bigger) set_height (Largest); - else set_height (Larger); - return; - } - if (height == hLarger) { - if (bigger) set_height (Large); - else set_height (Normal); - return; - } - if (height == hNormal) { - if (bigger) set_height (Larger); - else set_height (Smaller); - return; - } - if (height == hSmaller) { - if (bigger) set_height (Normal); - else set_height (Small); - return; - } - if (height == hSmall) { - if (bigger) set_height (Smaller); - return; - } + static const uint32_t step = 20; + + if (bigger) { + set_height (height + step); + } else { + if (height > step) { + set_height (std::max (height - step, hSmall)); + } else if (height != hSmall) { + set_height (hSmall); + } + } } void -TimeAxisView::set_heights (TrackHeight h) +TimeAxisView::set_heights (uint32_t h) { TrackSelection& ts (editor.get_selection().tracks); @@ -380,27 +384,20 @@ TimeAxisView::set_heights (TrackHeight h) } void -TimeAxisView::set_height (TrackHeight h) +TimeAxisView::set_height(uint32_t h) { - height_style = h; - set_height_pixels (height_to_pixels (h)); + height = h; for (list::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { (*i)->set_height (); } -} -void -TimeAxisView::set_height_pixels (uint32_t h) -{ - height = h; - controls_hbox.set_size_request (-1, height + ((order == 0) ? 1 : 0)); - //cerr << "TimeAxisView::set_height_pixels() called h = " << h << endl;//DEBUG if (canvas_item_visible (selection_group)) { /* resize the selection rect */ show_selection (editor.get_selection().time); } - + + reshow_feature_lines (); } bool @@ -440,8 +437,11 @@ TimeAxisView::name_entry_key_release (GdkEventKey* ev) } } - if ((*i)->height_style == Small) { - (*i)->set_height(Smaller); + + /* resize to show editable name display */ + + if ((*i)->current_height() >= hSmall && (*i)->current_height() < hNormal) { + (*i)->set_height (hSmaller); } (*i)->name_entry.grab_focus(); @@ -549,7 +549,6 @@ TimeAxisView::conditionally_add_to_selection () Selection& s (editor.get_selection()); if (!s.selected (this)) { - cerr << "set selected track\n"; editor.set_selected_track (*this, Selection::Set); } } @@ -617,6 +616,8 @@ TimeAxisView::set_selected (bool yn) (*i)->set_selected (false); } } + + resizer.queue_draw (); } void @@ -628,12 +629,12 @@ TimeAxisView::build_size_menu () size_menu->set_name ("ArdourContextMenu"); MenuList& items = size_menu->items(); - items.push_back (MenuElem (_("Largest"), bind (mem_fun (*this, &TimeAxisView::set_heights), Largest))); - items.push_back (MenuElem (_("Large"), bind (mem_fun (*this, &TimeAxisView::set_heights), Large))); - items.push_back (MenuElem (_("Larger"), bind (mem_fun (*this, &TimeAxisView::set_heights), Larger))); - items.push_back (MenuElem (_("Normal"), bind (mem_fun (*this, &TimeAxisView::set_heights), Normal))); - items.push_back (MenuElem (_("Smaller"), bind (mem_fun (*this, &TimeAxisView::set_heights),Smaller))); - items.push_back (MenuElem (_("Small"), bind (mem_fun (*this, &TimeAxisView::set_heights), Small))); + items.push_back (MenuElem (_("Largest"), bind (mem_fun (*this, &TimeAxisView::set_heights), hLargest))); + items.push_back (MenuElem (_("Large"), bind (mem_fun (*this, &TimeAxisView::set_heights), hLarge))); + items.push_back (MenuElem (_("Larger"), bind (mem_fun (*this, &TimeAxisView::set_heights), hLarger))); + items.push_back (MenuElem (_("Normal"), bind (mem_fun (*this, &TimeAxisView::set_heights), hNormal))); + items.push_back (MenuElem (_("Smaller"), bind (mem_fun (*this, &TimeAxisView::set_heights),hSmaller))); + items.push_back (MenuElem (_("Small"), bind (mem_fun (*this, &TimeAxisView::set_heights), hSmall))); } void @@ -716,7 +717,7 @@ TimeAxisView::show_selection (TimeSelection& ts) x1 = editor.frame_to_unit (start); x2 = editor.frame_to_unit (start + cnt - 1); - y2 = height; + y2 = current_height(); rect->rect->property_x1() = x1; rect->rect->property_y1() = 1.0; @@ -936,7 +937,7 @@ TimeAxisView::touched (double top, double bot) y_position is the "origin" or "top" of the track. */ - double mybot = y_position + height; + double mybot = y_position + current_height(); return ((y_position <= bot && y_position >= top) || ((mybot <= bot) && (top < mybot)) || @@ -969,68 +970,69 @@ TimeAxisView::get_parent_with_state () return parent->get_parent_with_state (); } -void + +XMLNode& +TimeAxisView::get_state () +{ + XMLNode* node = new XMLNode ("TAV-" + name()); + char buf[32]; + + snprintf (buf, sizeof(buf), "%u", height); + node->add_property ("height", buf); + node->add_property ("marked_for_display", (_marked_for_display ? "1" : "0")); + return *node; +} + +int TimeAxisView::set_state (const XMLNode& node) { const XMLProperty *prop; + if ((prop = node.property ("marked_for_display")) != 0) { + _marked_for_display = (prop->value() == "1"); + } + if ((prop = node.property ("track_height")) != 0) { if (prop->value() == "largest") { - set_height (Largest); + set_height (hLargest); } else if (prop->value() == "large") { - set_height (Large); + set_height (hLarge); } else if (prop->value() == "larger") { - set_height (Larger); + set_height (hLarger); } else if (prop->value() == "normal") { - set_height (Normal); + set_height (hNormal); } else if (prop->value() == "smaller") { - set_height (Smaller); + set_height (hSmaller); } else if (prop->value() == "small") { - set_height (Small); + set_height (hSmall); } else { error << string_compose(_("unknown track height name \"%1\" in XML GUI information"), prop->value()) << endmsg; set_height (Normal); } + } else if ((prop = node.property ("height")) != 0) { + + set_height (atoi (prop->value())); + } else { - set_height (Normal); + + set_height (hNormal); } + + return 0; } void TimeAxisView::reset_height() { - set_height_pixels (height); + set_height (height); for (Children::iterator i = children.begin(); i != children.end(); ++i) { - (*i)->set_height_pixels ((TrackHeight)(*i)->height); + (*i)->set_height ((*i)->height); } } -uint32_t -TimeAxisView::height_to_pixels (TrackHeight h) -{ - switch (h) { - case Largest: - return hLargest; - case Large: - return hLarge; - case Larger: - return hLarger; - case Normal: - return hNormal; - case Smaller: - return hSmaller; - case Small: - return hSmall; - } - - // what is wrong with gcc ? - - return hNormal; -} - void TimeAxisView::compute_controls_size_info () { @@ -1039,7 +1041,8 @@ TimeAxisView::compute_controls_size_info () Gtk::Table one_row_table (1, 8); Button* buttons[5]; const int border_width = 2; - const int extra_height = (2 * border_width) + 2; // 2 pixels for the controls frame + const int extra_height = (2 * border_width) + 2 // 2 pixels for the controls frame + + 10; // resizer button window.add (one_row_table); @@ -1213,8 +1216,6 @@ TimeAxisView::reshow_feature_lines () while (feature_lines.size()< analysis_features.size()) { ArdourCanvas::SimpleLine* l = new ArdourCanvas::SimpleLine (*canvas_display); l->property_color_rgba() = (guint) ARDOUR_UI::config()->canvasvar_ZeroLine.get(); - l->property_y1() = 0; - l->property_y2() = height; feature_lines.push_back (l); } @@ -1230,7 +1231,90 @@ TimeAxisView::reshow_feature_lines () for (i = analysis_features.begin(), l = feature_lines.begin(); i != analysis_features.end() && l != feature_lines.end(); ++i, ++l) { (*l)->property_x1() = editor.frame_to_pixel (*i); (*l)->property_x2() = editor.frame_to_pixel (*i); + (*l)->property_y1() = 0; + (*l)->property_y2() = current_height(); (*l)->show (); } } +bool +TimeAxisView::resizer_button_press (GdkEventButton* event) +{ + resize_drag_start = event->y_root; + resize_idle_target = current_height(); + editor.start_resize_line_ops (); + return true; +} + +bool +TimeAxisView::resizer_button_release (GdkEventButton* ev) +{ + resize_drag_start = -1; + editor.end_resize_line_ops (); + return true; +} + +void +TimeAxisView::idle_resize (uint32_t h) +{ + set_height (h); +} + +bool +TimeAxisView::resizer_motion (GdkEventMotion* ev) +{ + if (resize_drag_start < 0) { + return true; + } + + int32_t delta = (int32_t) floor (resize_drag_start - ev->y_root); + + resize_idle_target = std::max (resize_idle_target - delta, (int) hSmall); + editor.add_to_idle_resize (this, resize_idle_target); + + resize_drag_start = ev->y_root; + + return true; +} + +bool +TimeAxisView::resizer_expose (GdkEventExpose* event) +{ + int w, h, x, y, d; + Glib::RefPtr win (resizer.get_window()); + Glib::RefPtr dark (resizer.get_style()->get_fg_gc (STATE_NORMAL)); + Glib::RefPtr light (resizer.get_style()->get_bg_gc (STATE_NORMAL)); + + win->draw_rectangle (controls_ebox.get_style()->get_bg_gc(STATE_NORMAL), + true, + event->area.x, + event->area.y, + event->area.width, + event->area.height); + + win->get_geometry (x, y, w, h, d); + + /* handle/line #1 */ + + win->draw_line (dark, 0, 0, w - 2, 0); + win->draw_point (dark, 0, 1); + win->draw_line (light, 1, 1, w - 1, 1); + win->draw_point (light, w - 1, 0); + + /* handle/line #2 */ + + win->draw_line (dark, 0, 4, w - 2, 4); + win->draw_point (dark, 0, 5); + win->draw_line (light, 1, 5, w - 1, 5); + win->draw_point (light, w - 1, 4); + + /* handle/line #3 */ + + win->draw_line (dark, 0, 8, w - 2, 8); + win->draw_point (dark, 0, 9); + win->draw_line (light, 1, 9, w - 1, 9); + win->draw_point (light, w - 1, 8); + + return true; +} + diff --git a/gtk2_ardour/time_axis_view.h b/gtk2_ardour/time_axis_view.h index 96db8aba93..ae4d035af8 100644 --- a/gtk2_ardour/time_axis_view.h +++ b/gtk2_ardour/time_axis_view.h @@ -25,6 +25,7 @@ #include #include +#include #include #include #include @@ -32,6 +33,8 @@ #include +#include + #include #include #include @@ -69,7 +72,7 @@ class GhostRegion; * This class provides the basic LHS controls and display methods. This should be * extended to create functional time-axis based views. */ -class TimeAxisView : public virtual AxisView +class TimeAxisView : public virtual AxisView, public PBD::Stateful { private: enum NamePackingBits { @@ -78,15 +81,6 @@ class TimeAxisView : public virtual AxisView }; public: - enum TrackHeight { - Largest, - Large, - Larger, - Normal, - Smaller, - Small - }; - static uint32_t hLargest; static uint32_t hLarge; static uint32_t hLarger; @@ -94,23 +88,24 @@ class TimeAxisView : public virtual AxisView static uint32_t hSmaller; static uint32_t hSmall; - static uint32_t height_to_pixels (TrackHeight); - TimeAxisView(ARDOUR::Session& sess, PublicEditor& ed, TimeAxisView* parent, ArdourCanvas::Canvas& canvas); virtual ~TimeAxisView (); + XMLNode& get_state (void); + int set_state (const XMLNode&); + /* public data: XXX create accessor/mutators for these ?? */ PublicEditor& editor; - TrackHeight height_style; - uint32_t height; /* in canvas units */ - uint32_t effective_height; /* in canvas units */ - double y_position; - int order; + uint32_t effective_height; /* in canvas units */ + double y_position; + int order; - ArdourCanvas::Group *canvas_display; - Gtk::VBox *control_parent; + uint32_t current_height() const { return height; } + + ArdourCanvas::Group *canvas_display; + Gtk::VBox *control_parent; /* The Standard LHS Controls */ Gtk::Frame controls_frame; @@ -119,10 +114,21 @@ class TimeAxisView : public virtual AxisView Gtk::Table controls_table; Gtk::EventBox controls_ebox; Gtk::VBox controls_vbox; + Gtk::DrawingArea resizer; + Gtk::HBox resizer_box; Gtk::HBox name_hbox; Gtk::Frame name_frame; Gtkmm2ext::FocusEntry name_entry; - + + bool resizer_button_press (GdkEventButton*); + bool resizer_button_release (GdkEventButton*); + bool resizer_motion (GdkEventMotion*); + bool resizer_expose (GdkEventExpose*); + + double resize_drag_start; + int32_t resize_idle_target; + void idle_resize (uint32_t); + void hide_name_label (); void hide_name_entry (); void show_name_label (); @@ -152,7 +158,7 @@ class TimeAxisView : public virtual AxisView virtual void entered () {} virtual void exited () {} - virtual void set_height (TrackHeight h); + virtual void set_height (uint32_t h); void reset_height(); /** @@ -222,9 +228,6 @@ class TimeAxisView : public virtual AxisView void set_parent (TimeAxisView& p); bool has_state () const; - virtual void set_state (const XMLNode&); - virtual XMLNode* get_state_node () { return 0; } - /* call this on the parent */ virtual XMLNode* get_automation_child_xml_node (ARDOUR::Parameter param) { return 0; } @@ -232,6 +235,7 @@ class TimeAxisView : public virtual AxisView typedef std::vector > Children; protected: + uint32_t height; /* in canvas units */ string controls_base_unselected_name; string controls_base_selected_name; @@ -327,10 +331,11 @@ class TimeAxisView : public virtual AxisView static void compute_controls_size_info (); static bool need_size_info; - void set_heights (TrackHeight); - void set_height_pixels (uint32_t h); + void set_heights (uint32_t h); void color_handler (); - list feature_lines; + + + std::list feature_lines; ARDOUR::AnalysisFeatureList analysis_features; void reshow_feature_lines (); diff --git a/gtk2_ardour/time_axis_view_item.cc b/gtk2_ardour/time_axis_view_item.cc index f4316efd87..fa520f4ca1 100644 --- a/gtk2_ardour/time_axis_view_item.cc +++ b/gtk2_ardour/time_axis_view_item.cc @@ -70,9 +70,9 @@ double TimeAxisViewItem::NAME_HIGHLIGHT_THRESH; * @param duration the duration of this item */ TimeAxisViewItem::TimeAxisViewItem(const string & it_name, ArdourCanvas::Group& parent, TimeAxisView& tv, double spu, Gdk::Color& base_color, - nframes_t start, nframes_t duration, + nframes_t start, nframes_t duration, bool recording, Visibility vis) - : trackview (tv) + : trackview (tv), _recregion(recording) { if (!have_name_font) { @@ -151,7 +151,7 @@ TimeAxisViewItem::init (const string& it_name, double spu, Gdk::Color& base_colo vestigial_frame->property_x1() = (double) 0.0; vestigial_frame->property_y1() = (double) 1.0; vestigial_frame->property_x2() = 2.0; - vestigial_frame->property_y2() = (double) trackview.height; + vestigial_frame->property_y2() = (double) trackview.current_height(); vestigial_frame->property_outline_what() = 0xF; vestigial_frame->property_outline_color_rgba() = ARDOUR_UI::config()->canvasvar_VestigialFrame.get(); vestigial_frame->property_fill_color_rgba() = ARDOUR_UI::config()->canvasvar_VestigialFrame.get(); @@ -162,7 +162,7 @@ TimeAxisViewItem::init (const string& it_name, double spu, Gdk::Color& base_colo frame->property_x1() = (double) 0.0; frame->property_y1() = (double) 1.0; frame->property_x2() = (double) trackview.editor.frame_to_pixel(duration); - frame->property_y2() = (double) trackview.height; + frame->property_y2() = (double) trackview.current_height(); frame->property_outline_what() = 0xF; frame->property_outline_color_rgba() = ARDOUR_UI::config()->canvasvar_TimeAxisFrame.get(); frame->property_fill_color_rgba() = ARDOUR_UI::config()->canvasvar_TimeAxisFrame.get(); @@ -198,8 +198,8 @@ TimeAxisViewItem::init (const string& it_name, double spu, Gdk::Color& base_colo name_highlight->property_x1() = (double) 1.0; name_highlight->property_x2() = (double) (trackview.editor.frame_to_pixel(item_duration)) - 1; } - name_highlight->property_y1() = (double) (trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE); - name_highlight->property_y2() = (double) (trackview.height - 1); + name_highlight->property_y1() = (double) (trackview.current_height() - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE); + name_highlight->property_y2() = (double) (trackview.current_height() - 1); name_highlight->property_outline_color_rgba() = ARDOUR_UI::config()->canvasvar_NameHighlightFill.get(); name_highlight->property_fill_color_rgba() = ARDOUR_UI::config()->canvasvar_NameHighlightOutline.get(); @@ -212,10 +212,10 @@ TimeAxisViewItem::init (const string& it_name, double spu, Gdk::Color& base_colo if (visibility & ShowNameText) { name_text = new ArdourCanvas::Text (*group); name_text->property_x() = (double) TimeAxisViewItem::NAME_X_OFFSET; - /* trackview.height is the bottom of the trackview. subtract 1 to get back to the bottom of the highlight, + /* trackview.current_height() is the bottom of the trackview. subtract 1 to get back to the bottom of the highlight, then NAME_Y_OFFSET to position the text in the vertical center of the highlight */ - name_text->property_y() = (double) trackview.height - 1.0 - TimeAxisViewItem::NAME_Y_OFFSET; + name_text->property_y() = (double) trackview.current_height() - 1.0 - TimeAxisViewItem::NAME_Y_OFFSET; name_text->property_font_desc() = *NAME_FONT; name_text->property_anchor() = Gtk::ANCHOR_NW; @@ -804,8 +804,13 @@ TimeAxisViewItem::set_frame_color() UINT_TO_RGBA(ARDOUR_UI::config()->canvasvar_SelectedFrameBase.get(), &r, &g, &b, &a); frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, a); } else { - UINT_TO_RGBA(ARDOUR_UI::config()->canvasvar_FrameBase.get(), &r, &g, &b, &a); - frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, a); + if (_recregion) { + UINT_TO_RGBA(ARDOUR_UI::config()->canvasvar_RecordingRect.get(), &r, &g, &b, &a); + frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, a); + } else { + UINT_TO_RGBA(ARDOUR_UI::config()->canvasvar_FrameBase.get(), &r, &g, &b, &a); + frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, fill_opacity ? fill_opacity : a); + } } } } @@ -1049,3 +1054,4 @@ TimeAxisViewItem::idle_remove_this_item(TimeAxisViewItem* item, void* src) item = 0; return false; } + diff --git a/gtk2_ardour/time_axis_view_item.h b/gtk2_ardour/time_axis_view_item.h index 18d6638738..02becad3e7 100644 --- a/gtk2_ardour/time_axis_view_item.h +++ b/gtk2_ardour/time_axis_view_item.h @@ -201,8 +201,8 @@ class TimeAxisViewItem : public Selectable */ void set_name_text(const Glib::ustring& new_name) ; - virtual void set_y_position_and_height(double y, double h) ; - + void set_y_position_and_height (double, double); + /** * */ @@ -291,6 +291,7 @@ class TimeAxisViewItem : public Selectable * the destructor, this allows us to capture the source of the deletion * event */ + sigc::signal ItemRemoved ; /** Emitted when the name/Id of this item is changed */ @@ -311,8 +312,6 @@ class TimeAxisViewItem : public Selectable /** Emitted when the mionimum item duration is changed */ sigc::signal MinDurationChanged ; - protected: - enum Visibility { ShowFrame = 0x1, ShowNameHighlight = 0x2, @@ -323,7 +322,7 @@ class TimeAxisViewItem : public Selectable HideFrameTB = 0x40, FullWidthNameHighlight = 0x80 }; - + protected: /** * Constructs a new TimeAxisViewItem. * @@ -336,7 +335,7 @@ class TimeAxisViewItem : public Selectable * @param duration the duration of this item */ TimeAxisViewItem(const std::string & it_name, ArdourCanvas::Group& parent, TimeAxisView& tv, double spu, Gdk::Color& base_color, - nframes_t start, nframes_t duration, Visibility v = Visibility (0)); + nframes_t start, nframes_t duration, bool recording = false, Visibility v = Visibility (0)); TimeAxisViewItem (const TimeAxisViewItem& other); @@ -462,6 +461,8 @@ class TimeAxisViewItem : public Selectable std::map name_text_size_cache; Visibility visibility; + bool _recregion; + }; /* class TimeAxisViewItem */ diff --git a/gtk2_ardour/ui_config.cc b/gtk2_ardour/ui_config.cc index 6ebedaa129..37a0ade3fe 100644 --- a/gtk2_ardour/ui_config.cc +++ b/gtk2_ardour/ui_config.cc @@ -20,6 +20,8 @@ #include #include /* for snprintf, grrr */ +#include + #include #include #include @@ -148,12 +150,10 @@ UIConfiguration::save_state() { XMLTree tree; - try - { + try { sys::create_directories (user_config_directory ()); } - catch (const sys::filesystem_error& ex) - { + catch (const sys::filesystem_error& ex) { error << "Could not create user configuration directory" << endmsg; return -1; } diff --git a/gtk2_ardour/utils.cc b/gtk2_ardour/utils.cc index a52969268a..9008f8b8cd 100644 --- a/gtk2_ardour/utils.cc +++ b/gtk2_ardour/utils.cc @@ -36,6 +36,7 @@ #include #include +#include #include @@ -469,39 +470,10 @@ key_press_focus_accelerator_handler (Gtk::Window& window, GdkEventKey* ev) it does allow. */ - int fakekey = GDK_VoidSymbol; - int ret = false; - - switch (ev->keyval) { - case GDK_Tab: - case GDK_ISO_Left_Tab: - fakekey = GDK_nabla; - break; - - case GDK_Up: - fakekey = GDK_uparrow; - break; - - case GDK_Down: - fakekey = GDK_downarrow; - break; - - case GDK_Right: - fakekey = GDK_rightarrow; - break; - - case GDK_Left: - fakekey = GDK_leftarrow; - break; - - default: - break; - } + uint32_t fakekey = ev->keyval; - if (fakekey != GDK_VoidSymbol) { - ret = gtk_accel_groups_activate(G_OBJECT(win), fakekey, GdkModifierType(ev->state)); - - if (ret) { + if (possibly_translate_keyval_to_make_legal_accelerator (fakekey)) { + if (gtk_accel_groups_activate(G_OBJECT(win), fakekey, GdkModifierType(ev->state))) { return true; } @@ -590,18 +562,30 @@ key_press_focus_accelerator_handler (Gtk::Window& window, GdkEventKey* ev) Glib::RefPtr get_xpm (std::string name) { - SearchPath spath(ARDOUR::ardour_search_path()); - spath += ARDOUR::system_data_search_path(); + if (!xpm_map[name]) { - spath.add_subdirectory_to_paths("pixmaps"); + SearchPath spath(ARDOUR::ardour_search_path()); + spath += ARDOUR::system_data_search_path(); + + spath.add_subdirectory_to_paths("pixmaps"); + + sys::path data_file_path; + + if (!find_file_in_search_path (spath, name, data_file_path)) { + fatal << string_compose (_("cannot find XPM file for %1"), name) << endmsg; + /*NOTREACHED*/ + } - sys::path data_file_path; + try { + xpm_map[name] = Gdk::Pixbuf::create_from_file (data_file_path.to_string()); + } - if(!find_file_in_search_path (spath, name, data_file_path)) { - fatal << string_compose (_("cannot find XPM file for %1"), name) << endmsg; + catch(const Glib::Error& e) { + warning << "Caught Glib::Error: " << e.what() << endmsg; + } } - return Gdk::Pixbuf::create_from_file (data_file_path.to_string()); + return xpm_map[name]; } Glib::RefPtr @@ -738,3 +722,42 @@ reset_dpi () DPIReset();//Emit Signal } +bool +possibly_translate_keyval_to_make_legal_accelerator (uint32_t& keyval) +{ + int fakekey = GDK_VoidSymbol; + + switch (keyval) { + case GDK_Tab: + case GDK_ISO_Left_Tab: + fakekey = GDK_nabla; + break; + + case GDK_Up: + fakekey = GDK_uparrow; + break; + + case GDK_Down: + fakekey = GDK_downarrow; + break; + + case GDK_Right: + fakekey = GDK_rightarrow; + break; + + case GDK_Left: + fakekey = GDK_leftarrow; + break; + + default: + break; + } + + if (fakekey != GDK_VoidSymbol) { + keyval = fakekey; + return true; + } + + return false; +} + diff --git a/gtk2_ardour/utils.h b/gtk2_ardour/utils.h index 4cf8fc371b..29c6bda403 100644 --- a/gtk2_ardour/utils.h +++ b/gtk2_ardour/utils.h @@ -76,6 +76,7 @@ bool canvas_item_visible (ArdourCanvas::Item* item); void set_color (Gdk::Color&, int); bool key_press_focus_accelerator_handler (Gtk::Window& window, GdkEventKey* ev); +bool possibly_translate_keyval_to_make_legal_accelerator (uint32_t& keyval); Glib::RefPtr get_xpm (std::string); Glib::RefPtr get_icon (const char*); diff --git a/gtk2_ardour/visual_time_axis.cc b/gtk2_ardour/visual_time_axis.cc index 83b95bb5d2..8a707183cd 100644 --- a/gtk2_ardour/visual_time_axis.cc +++ b/gtk2_ardour/visual_time_axis.cc @@ -101,7 +101,7 @@ VisualTimeAxis::VisualTimeAxis(const string & name, PublicEditor& ed, ARDOUR::Se hide_button.unset_flags(Gtk::CAN_FOCUS) ; visual_button.unset_flags(Gtk::CAN_FOCUS) ; - set_height(Normal) ; + set_height (hNormal) ; } /** @@ -144,39 +144,25 @@ VisualTimeAxis::name() const /** * Sets the height of this TrackView to one of the defined TrackHeghts * - * @param h the TrackHeight value to set + * @param h */ void -VisualTimeAxis::set_height(TrackHeight h) +VisualTimeAxis::set_height(uint32_t h) { - TimeAxisView::set_height(h) ; + TimeAxisView::set_height(h); - switch (height) - { - case Largest: - case Large: - case Larger: - case Normal: - { - hide_name_label (); - show_name_entry (); - other_button_hbox.show_all() ; - break; - } - case Smaller: - { - hide_name_label (); - show_name_entry (); - other_button_hbox.hide_all() ; - break; - } - case Small: - { - hide_name_entry (); - show_name_label (); - other_button_hbox.hide_all() ; - } - break; + if (h >= hNormal) { + hide_name_label (); + show_name_entry (); + other_button_hbox.show_all() ; + } else if (h >= hSmaller) { + hide_name_label (); + show_name_entry (); + other_button_hbox.hide_all() ; + } else if (h >= hSmall) { + hide_name_entry (); + show_name_label (); + other_button_hbox.hide_all() ; } } diff --git a/gtk2_ardour/visual_time_axis.h b/gtk2_ardour/visual_time_axis.h index 6d1396bc54..a0dfe654de 100644 --- a/gtk2_ardour/visual_time_axis.h +++ b/gtk2_ardour/visual_time_axis.h @@ -93,9 +93,9 @@ class VisualTimeAxis : public TimeAxisView /** * Sets the height of this TrackView to one of the defined TrackHeghts * - * @param h the TrackHeight value to set + * @param h the number of pixels to set the height to */ - virtual void set_height (TrackHeight h); + virtual void set_height (uint32_t); //---------------------------------------------------------------------------------------// // Selection Methods -- cgit v1.2.3