diff --git a/gtk2_ardour/ardour.menus b/gtk2_ardour/ardour.menus index bb8cd9daae..f9c20a434a 100644 --- a/gtk2_ardour/ardour.menus +++ b/gtk2_ardour/ardour.menus @@ -330,6 +330,7 @@ + diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 1e89b4af31..548b65d424 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -357,7 +357,7 @@ Editor::Editor () 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 (); @@ -4134,6 +4134,15 @@ Editor::swap_visual_state () set_zoom_focus (last_visual_state.zoom_focus); reposition_and_zoom (last_visual_state.leftmost_frame, last_visual_state.frames_per_unit); + + if (zoomed_to_region) { + for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) { + (*i)->set_height_scaling_factor (1.0); + } + } + + toggle_temporarily_hidden_tracks (zoomed_to_region); + zoomed_to_region = false; } @@ -4168,7 +4177,7 @@ Editor::set_frames_per_unit (double fpu) 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 (); } diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index 900b2c9e40..6ad11dbd31 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -290,7 +290,7 @@ class Editor : public PublicEditor void maybe_add_mixer_strip_width (XMLNode&); void show_editor_mixer (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 */ @@ -1056,8 +1056,8 @@ 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); @@ -1637,11 +1637,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; }; @@ -1654,6 +1656,8 @@ public: Gtk::ScrolledWindow route_list_scroller; Gtk::Menu* route_list_menu; + void toggle_temporarily_hidden_tracks (bool yn); + void sync_order_keys (); bool ignore_route_order_sync; diff --git a/gtk2_ardour/editor_actions.cc b/gtk2_ardour/editor_actions.cc index 54ebd6f95f..3e676e073b 100644 --- a/gtk2_ardour/editor_actions.cc +++ b/gtk2_ardour/editor_actions.cc @@ -244,7 +244,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); diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index 8cb55a1cf1..a67a5f4557 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -1687,13 +1687,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); @@ -1702,14 +1703,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 @@ -1738,24 +1745,41 @@ Editor::temporal_zoom_region () temporal_zoom_by_frame (start, end, "zoom to region"); - uint32_t per_track_height = (uint32_t) floor ((canvas_height - 10.0) / tracks.size()); + if (both_axes) { + double per_track_height = (canvas_height - 10.0) / tracks.size(); + + /* set visible track heights appropriately */ + + for (set::iterator t = tracks.begin(); t != tracks.end(); ++t) { + (*t)->set_height_scaling_factor (per_track_height/(*t)->height); + } + + /* hide irrelevant tracks */ + + no_route_list_redisplay = true; - for (set::iterator t = tracks.begin(); t != tracks.end(); ++t) { - (*t)->set_height (per_track_height); + 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)); } - vertical_adjustment.set_value (std::max ((*tracks.begin())->y_position - 5.0, 0.0)); - zoomed_to_region = true; } 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); } } diff --git a/gtk2_ardour/editor_route_list.cc b/gtk2_ardour/editor_route_list.cc index 7c07e84f9a..e6ef9e40a8 100644 --- a/gtk2_ardour/editor_route_list.cc +++ b/gtk2_ardour/editor_route_list.cc @@ -68,6 +68,7 @@ Editor::handle_new_route (Session::RouteList& routes) row[route_display_columns.route] = route; row[route_display_columns.text] = route->name(); row[route_display_columns.visible] = tv->marked_for_display(); + row[route_display_columns.temporary_visible] = tv->marked_for_display(); row[route_display_columns.tv] = tv; track_views.push_back (tv); @@ -176,14 +177,33 @@ Editor::route_name_changed (TimeAxisView *tv) } void -Editor::hide_track_in_display (TimeAxisView& tv) +Editor::toggle_temporarily_hidden_tracks (bool yn) +{ + TreeModel::Children rows = route_display_model->children(); + TreeModel::Children::iterator i; + + no_route_list_redisplay = true; + + for (i = rows.begin(); i != rows.end(); ++i) { + (*i)[route_display_columns.temporary_visible] = yn; + } + + no_route_list_redisplay = false; + redisplay_route_list (); +} + +void +Editor::hide_track_in_display (TimeAxisView& tv, bool temponly) { TreeModel::Children rows = route_display_model->children(); TreeModel::Children::iterator i; for (i = rows.begin(); i != rows.end(); ++i) { if ((*i)[route_display_columns.tv] == &tv) { - (*i)[route_display_columns.visible] = false; + if (!temponly) { + (*i)[route_display_columns.visible] = false; + } + (*i)[route_display_columns.temporary_visible] = false; break; } } @@ -205,6 +225,7 @@ Editor::show_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] = true; + (*i)[route_display_columns.temporary_visible] = true; tv.set_marked_for_display (true); break; } @@ -279,7 +300,11 @@ Editor::redisplay_route_list () if (visible) { tv->set_marked_for_display (true); - position += tv->show_at (position, n, &edit_controls_vbox); + if ((*i)[route_display_columns.temporary_visible]) { + position += tv->show_at (position, n, &edit_controls_vbox); + } else { + tv->hide (); + } } else { tv->hide (); } @@ -321,6 +346,7 @@ Editor::hide_all_tracks (bool with_select) } row[route_display_columns.visible] = false; + row[route_display_columns.temporary_visible] = false; } no_route_list_redisplay = false; @@ -371,6 +397,7 @@ Editor::set_all_tracks_visibility (bool yn) } (*i)[route_display_columns.visible] = yn; + (*i)[route_display_columns.temporary_visible] = yn; } no_route_list_redisplay = false; @@ -398,17 +425,20 @@ Editor::set_all_audio_visibility (int tracks, bool yn) switch (tracks) { case 0: (*i)[route_display_columns.visible] = yn; + (*i)[route_display_columns.temporary_visible] = yn; break; case 1: if (atv->is_audio_track()) { (*i)[route_display_columns.visible] = yn; + (*i)[route_display_columns.temporary_visible] = yn; } break; case 2: if (!atv->is_audio_track()) { (*i)[route_display_columns.visible] = yn; + (*i)[route_display_columns.temporary_visible] = yn; } break; } @@ -478,6 +508,7 @@ Editor::route_list_display_button_press (GdkEventButton* ev) if (tv) { bool visible = (*iter)[route_display_columns.visible]; (*iter)[route_display_columns.visible] = !visible; + (*iter)[route_display_columns.temporary_visible] = !visible; } } return true; @@ -557,7 +588,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, diff --git a/gtk2_ardour/mnemonic-us.bindings.in b/gtk2_ardour/mnemonic-us.bindings.in index 865c632121..a1cb481f51 100644 --- a/gtk2_ardour/mnemonic-us.bindings.in +++ b/gtk2_ardour/mnemonic-us.bindings.in @@ -93,7 +93,7 @@ ;; HOME ROW (gtk_accel_path "/Editor/zoom-to-region" "z") -;;(gtk_accel_path "/Editor/zoom-to-region-both-axes" "<%SECONDARY%>z") +(gtk_accel_path "/Editor/zoom-to-region-both-axes" "<%SECONDARY%>z") (gtk_accel_path "/Editor/undo" "<%PRIMARY%>z") (gtk_accel_path "/Editor/toggle-zoom" "<%TERTIARY%>z") (gtk_accel_path "/MouseMode/set-mouse-mode-zoom" "z") diff --git a/gtk2_ardour/public_editor.h b/gtk2_ardour/public_editor.h index 4f23483b49..ed4c5be789 100644 --- a/gtk2_ardour/public_editor.h +++ b/gtk2_ardour/public_editor.h @@ -137,7 +137,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; virtual void set_follow_playhead (bool yn) = 0; virtual void toggle_follow_playhead () = 0; diff --git a/gtk2_ardour/route_time_axis.cc b/gtk2_ardour/route_time_axis.cc index 66a87762fc..07a7142b3b 100644 --- a/gtk2_ardour/route_time_axis.cc +++ b/gtk2_ardour/route_time_axis.cc @@ -653,7 +653,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; @@ -702,7 +702,7 @@ RouteTimeAxisView::set_height (uint32_t h) ensure_xml_node (); if (_view) { - _view->set_height ((double) height); + _view->set_height ((double) current_height()); } char buf[32]; diff --git a/gtk2_ardour/time_axis_view.cc b/gtk2_ardour/time_axis_view.cc index ceb8b4a99c..7723e122f4 100644 --- a/gtk2_ardour/time_axis_view.cc +++ b/gtk2_ardour/time_axis_view.cc @@ -91,6 +91,7 @@ TimeAxisView::TimeAxisView (ARDOUR::Session& sess, PublicEditor& ed, TimeAxisVie _hidden = false; height = 0; effective_height = 0; + height_scaling_factor = 1.0; parent = rent; _has_state = false; last_name_entry_key_press_event = 0; @@ -245,7 +246,7 @@ TimeAxisView::show_at (double y, int& nth, VBox *parent) /* height in pixels depends on _order, so update it now we've changed _order */ set_height (height); - effective_height = height; + effective_height = current_height(); /* now show children */ @@ -340,37 +341,25 @@ TimeAxisView::hide () Hiding (); } +void +TimeAxisView::set_height_scaling_factor (double hsf) +{ + height_scaling_factor = hsf; + set_height (height); +} + void TimeAxisView::step_height (bool bigger) { - if (height == hLargest) { - if (!bigger) set_height (hLarge); - return; - } - if (height == hLarge) { - if (bigger) set_height (hLargest); - else set_height (hLarger); - return; - } - if (height == hLarger) { - if (bigger) set_height (hLarge); - else set_height (hNormal); - return; - } - if (height == hNormal) { - if (bigger) set_height (hLarger); - else set_height (hSmaller); - return; - } - if (height == hSmaller) { - if (bigger) set_height (hNormal); - else set_height (hSmall); - return; - } - if (height == hSmall) { - if (bigger) set_height (hSmaller); - return; - } + if (bigger) { + set_height (height + 4); + } else { + if (height > 4) { + set_height (std::max (height - 4, hSmall)); + } else if (height != hSmall) { + set_height (hSmall); + } + } } void @@ -387,7 +376,7 @@ void TimeAxisView::set_height(uint32_t h) { height = h; - controls_frame.set_size_request (-1, height + ((order == 0) ? 1 : 0)); + controls_frame.set_size_request (-1, current_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 */ @@ -432,9 +421,12 @@ TimeAxisView::name_entry_key_release (GdkEventKey* ev) } while ((*i)->hidden()); } } + + + /* resize to show editable name display */ - if ((*i)->height >= hSmall && (*i)->height < hNormal) { - (*i)->set_height(hSmaller); + if ((*i)->current_height() >= hSmall && (*i)->current_height() < hNormal) { + (*i)->set_height (hSmaller); } (*i)->name_entry.grab_focus(); @@ -709,7 +701,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; @@ -896,7 +888,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)) || @@ -966,7 +958,7 @@ TimeAxisView::set_state (const XMLNode& node) void TimeAxisView::reset_height() { - set_height(height); + set_height (height); for (vector::iterator i = children.begin(); i != children.end(); ++i) { (*i)->set_height ((*i)->height); @@ -1153,7 +1145,7 @@ TimeAxisView::reshow_feature_lines () 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; + l->property_y2() = current_height(); feature_lines.push_back (l); } @@ -1177,7 +1169,7 @@ bool TimeAxisView::resizer_button_press (GdkEventButton* event) { resize_drag_start = event->y_root; - resize_idle_target = height; + resize_idle_target = current_height(); return true; } diff --git a/gtk2_ardour/time_axis_view.h b/gtk2_ardour/time_axis_view.h index f064359e40..7fa138dc39 100644 --- a/gtk2_ardour/time_axis_view.h +++ b/gtk2_ardour/time_axis_view.h @@ -93,9 +93,13 @@ class TimeAxisView : public virtual AxisView uint32_t height; /* in canvas units */ uint32_t effective_height; /* in canvas units */ - double y_position; - int order; + double height_scaling_factor; /* used to zoom the track height without changing it */ + double y_position; + int order; + uint32_t current_height() const { return (uint32_t) floor (height * height_scaling_factor); } + void set_height_scaling_factor (double); + ArdourCanvas::Group *canvas_display; Gtk::VBox *control_parent;