special case [optimize] RT processor reorder.
[ardour.git] / libs / ardour / session_transport.cc
index 449349996fd5ff6f3c57d05ff8437d9894cac225..e953271ead967e36a1edbd95a0c884f8a06cd5f1 100644 (file)
@@ -782,15 +782,18 @@ Session::check_declick_out ()
 void
 Session::unset_play_loop ()
 {
-       play_loop = false;
-       clear_events (SessionEvent::AutoLoop);
-       clear_events (SessionEvent::AutoLoopDeclick);
-       set_track_loop (false);
-
-       if (Config->get_seamless_loop()) {
-               /* likely need to flush track buffers: this will locate us to wherever we are */
-               add_post_transport_work (PostTransportLocate);
-               _butler->schedule_transport_work ();
+       if (play_loop) {
+               play_loop = false;
+               clear_events (SessionEvent::AutoLoop);
+               clear_events (SessionEvent::AutoLoopDeclick);
+               set_track_loop (false);
+               
+       
+               if (Config->get_seamless_loop()) {
+                       /* likely need to flush track buffers: this will locate us to wherever we are */
+                       add_post_transport_work (PostTransportLocate);
+                       _butler->schedule_transport_work ();
+               }
        }
 }
 
@@ -973,6 +976,8 @@ Session::micro_locate (framecnt_t distance)
 void
 Session::locate (framepos_t target_frame, bool with_roll, bool with_flush, bool for_seamless_loop, bool force, bool with_mmc)
 {
+       bool need_butler = false;
+       
        /* Locates for seamless looping are fairly different from other
         * locates. They assume that the diskstream buffers for each track
         * already have the correct data in them, and thus there is no need to
@@ -1048,7 +1053,8 @@ Session::locate (framepos_t target_frame, bool with_roll, bool with_flush, bool
                }
 
                add_post_transport_work (todo);
-
+               need_butler = true;
+               
        } else {
 
                /* this is functionally what clear_clicks() does but with a tentative lock */
@@ -1115,6 +1121,7 @@ Session::locate (framepos_t target_frame, bool with_roll, bool with_flush, bool
                                                         * end.
                                                         */
                                                        add_post_transport_work (PostTransportLocate);
+                                                       need_butler = true;
                                                }
                                                    
                                        }
@@ -1139,7 +1146,9 @@ Session::locate (framepos_t target_frame, bool with_roll, bool with_flush, bool
                }
        }
 
-       _butler->schedule_transport_work ();
+       if (need_butler) {
+               _butler->schedule_transport_work ();
+       }
 
        loop_changing = false;
 
@@ -1312,7 +1321,28 @@ Session::set_transport_speed (double speed, framepos_t destination_frame, bool a
                }
 
                DEBUG_TRACE (DEBUG::Transport, string_compose ("send TSC3 with speed = %1\n", _transport_speed));
-               TransportStateChange (); /* EMIT SIGNAL */
+
+               /* throttle signal emissions. 
+                * when slaved [_last]_transport_speed
+                * usually changes every cycle (tiny amounts due to DLL).
+                * Emitting a signal every cycle is overkill and unwarranted.
+                *
+                * Using _last_transport_speed is not acceptable,
+                * since it allows for large changes over a long period 
+                * of time. Hence we introduce a dedicated variable to keep track
+                *
+                * The 0.2% dead-zone is somewhat arbitrary. Main use-case
+                * for TransportStateChange() here is the ShuttleControl display.
+                */
+               if (fabsf(_signalled_varispeed - speed) > .002f
+                   // still, signal hard changes to 1.0 and 0.0:
+                   || ( speed == 1.f && _signalled_varispeed != 1.f)
+                   || ( speed == 0.f && _signalled_varispeed != 0.f)
+                  )
+               {
+                       TransportStateChange (); /* EMIT SIGNAL */
+                       _signalled_varispeed = speed;
+               }
        }
 }
 
@@ -1796,6 +1826,12 @@ Session::route_processors_changed (RouteProcessorChange c)
        }
 
        if (c.type == RouteProcessorChange::MeterPointChange) {
+               set_dirty ();
+               return;
+       }
+
+       if (c.type == RouteProcessorChange::RealTimeChange) {
+               set_dirty ();
                return;
        }