switch to 5 new fade curves, taken from mixbus2 branch. make xfade context menus...
[ardour.git] / gtk2_ardour / editor_mouse.cc
index 16f87d920d292967dfe807033c17ad255dea1cf7..d7d1c342806d02168fc29b142b4737048052392d 100644 (file)
@@ -91,6 +91,21 @@ using Gtkmm2ext::Keyboard;
 bool
 Editor::mouse_frame (framepos_t& where, bool& in_track_canvas) const
 {
+        /* gdk_window_get_pointer() has X11's XQueryPointer semantics in that it only
+           pays attentions to subwindows. this means that menu windows are ignored, and 
+           if the pointer is in a menu, the return window from the call will be the
+           the regular subwindow *under* the menu.
+
+           this matters quite a lot if the pointer is moving around in a menu that overlaps
+           the track canvas because we will believe that we are within the track canvas
+           when we are not. therefore, we track enter/leave events for the track canvas
+           and allow that to override the result of gdk_window_get_pointer().
+        */
+
+        if (!within_track_canvas) {
+                return false;
+        }
+
        int x, y;
        double wx, wy;
        Gdk::ModifierType mask;
@@ -441,9 +456,9 @@ Editor::mouse_mode_toggled (MouseMode m)
        instant_save ();
 
        if (!internal_editing()) {
-               if (mouse_mode != MouseRange && _join_object_range_state == JOIN_OBJECT_RANGE_NONE) {
+               if (mouse_mode != MouseRange && mouse_mode != MouseGain && _join_object_range_state == JOIN_OBJECT_RANGE_NONE) {
 
-                       /* in all modes except range and joined object/range, hide the range selection,
+                       /* in all modes except range, gain and joined object/range, hide the range selection,
                           show the object (region) selection.
                        */
 
@@ -625,11 +640,12 @@ Editor::button_selection (ArdourCanvas::Item* /*item*/, GdkEvent* event, ItemTyp
                }
                break;
 
-
        case FadeInHandleItem:
        case FadeInItem:
        case FadeOutHandleItem:
        case FadeOutItem:
+       case StartCrossFadeItem:
+       case EndCrossFadeItem:
                if (doing_object_stuff() || (mouse_mode != MouseRange && mouse_mode != MouseObject)) {
                        set_selected_regionview_from_click (press, op);
                } else if (event->type == GDK_BUTTON_PRESS) {
@@ -640,7 +656,7 @@ Editor::button_selection (ArdourCanvas::Item* /*item*/, GdkEvent* event, ItemTyp
        case ControlPointItem:
                set_selected_track_as_side_effect (op);
                if (doing_object_stuff() || (mouse_mode != MouseRange && mouse_mode != MouseObject)) {
-                       set_selected_control_point_from_click (op, false);
+                       set_selected_control_point_from_click (press, op);
                }
                break;
 
@@ -809,7 +825,7 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                                        AutomationTimeAxisView* atv = dynamic_cast<AutomationTimeAxisView*> (tvp.first);
                                        if (smart_mode_action->get_active() && atv) {
                                                /* smart "join" mode: drag automation */
-                                               _drags->set (new AutomationRangeDrag (this, atv->base_item(), selection->time), event, _cursors->up_down);
+                                               _drags->set (new AutomationRangeDrag (this, atv, selection->time), event, _cursors->up_down);
                                        } else {
                                                /* this was debated, but decided the more common action was to
                                                   make a new selection */
@@ -874,6 +890,7 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                default:
                        break;
                }
+               break;
 
        case MouseObject:
                switch (item_type) {
@@ -915,6 +932,14 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                                return true;
                        }
 
+                       case StartCrossFadeItem:
+                               _drags->set (new CrossfadeEdgeDrag (this, reinterpret_cast<AudioRegionView*>(item->get_data("regionview")), item, true), event, 0);
+                               break;
+
+                       case EndCrossFadeItem:
+                               _drags->set (new CrossfadeEdgeDrag (this, reinterpret_cast<AudioRegionView*>(item->get_data("regionview")), item, false), event, 0);
+                               break;
+
                        case FeatureLineItem:
                        {
                                if (Keyboard::modifier_state_contains (event->button.state, Keyboard::TertiaryModifier)) {
@@ -1025,7 +1050,7 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                                                /* if we're over an automation track, start a drag of its data */
                                                AutomationTimeAxisView* atv = dynamic_cast<AutomationTimeAxisView*> (tvp.first);
                                                if (atv) {
-                                                       _drags->set (new AutomationRangeDrag (this, atv->base_item(), selection->time), event, _cursors->up_down);
+                                                       _drags->set (new AutomationRangeDrag (this, atv, selection->time), event, _cursors->up_down);
                                                }
 
                                                /* if we're over a track and a region, and in the `object' part of a region,
@@ -1095,13 +1120,6 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT
 
        case MouseGain:
                switch (item_type) {
-               case RegionItem:
-                       /* start a grab so that if we finish after moving
-                          we can tell what happened.
-                       */
-                       _drags->set (new RegionGainDrag (this, item), event, current_canvas_cursor);
-                       break;
-
                case GainLineItem:
                        _drags->set (new LineDrag (this, item), event);
                        return true;
@@ -1111,27 +1129,21 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                        return true;
                        break;
 
-               default:
+               case SelectionItem:
+               {
+                       AudioRegionView* arv = dynamic_cast<AudioRegionView *> (clicked_regionview);
+                       if (arv) {
+                               _drags->set (new AutomationRangeDrag (this, arv, selection->time), event, _cursors->up_down);
+                               _drags->start_grab (event);
+                       }
+                       return true;
                        break;
                }
-               return true;
-               break;
-
-               switch (item_type) {
-               case ControlPointItem:
-                       _drags->set (new ControlPointDrag (this, item), event);
-                       break;
 
                case AutomationLineItem:
                        _drags->set (new LineDrag (this, item), event);
                        break;
-
-               case RegionItem:
-                       // XXX need automation mode to identify which
-                       // line to use
-                       // start_line_grab_from_regionview (item, event);
-                       break;
-
+                       
                default:
                        break;
                }
@@ -1295,7 +1307,7 @@ Editor::button_press_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemTyp
                        break;
 
                case RegionItem:
-                       if (!dynamic_cast<MidiRegionView*> (clicked_regionview)) {
+                       if (!dynamic_cast<MidiRegionView*> (clicked_regionview) && !dynamic_cast<AutomationRegionView*> (clicked_regionview)) {
                                leave_internal_edit_mode = true;
                        }
                        break;
@@ -1468,6 +1480,14 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                                popup_fade_context_menu (1, event->button.time, item, item_type);
                                break;
 
+                       case StartCrossFadeItem:
+                               popup_xfade_in_context_menu (1, event->button.time, item, item_type);
+                               break;
+
+                       case EndCrossFadeItem:
+                               popup_xfade_out_context_menu (1, event->button.time, item, item_type);
+                               break;
+
                        case StreamItem:
                                popup_track_context_menu (1, event->button.time, item_type, false);
                                break;
@@ -1483,7 +1503,7 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                        case SelectionItem:
                                popup_track_context_menu (1, event->button.time, item_type, true);
                                break;
-
+                               
                        case AutomationTrackItem:
                                popup_track_context_menu (1, event->button.time, item_type, false);
                                break;
@@ -1649,7 +1669,7 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT
                                   points when doing this.
                                */
                                AudioRegionView* arv = dynamic_cast<AudioRegionView*> (clicked_regionview);
-                               if (were_dragging && arv) {
+                               if (!were_dragging && arv) {
                                        arv->add_gain_point_event (item, event);
                                }
                                return true;
@@ -2705,16 +2725,29 @@ Editor::escape ()
 void
 Editor::set_internal_edit (bool yn)
 {
+       if (_internal_editing == yn) {
+               return;
+       }
+
        _internal_editing = yn;
        
        if (yn) {
                 pre_internal_mouse_mode = mouse_mode;
+               pre_internal_snap_type = _snap_type;
+               pre_internal_snap_mode = _snap_mode;
 
                 for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) {
                         (*i)->enter_internal_edit_mode ();
                 }
 
+               set_snap_to (internal_snap_type);
+               set_snap_mode (internal_snap_mode);
+
        } else {
+
+               internal_snap_mode = _snap_mode;
+               internal_snap_type = _snap_type;
+
                 for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) {
                         (*i)->leave_internal_edit_mode ();
                 }
@@ -2723,6 +2756,9 @@ Editor::set_internal_edit (bool yn)
                         /* we were drawing .. flip back to something sensible */
                         set_mouse_mode (pre_internal_mouse_mode);
                 }
+
+               set_snap_to (pre_internal_snap_type);
+               set_snap_mode (pre_internal_snap_mode);
        }
        
        set_canvas_cursor ();