Drop video frames if we running out of time.
authorCarl Hetherington <cth@carlh.net>
Fri, 4 Aug 2017 00:29:48 +0000 (01:29 +0100)
committerCarl Hetherington <cth@carlh.net>
Mon, 14 Aug 2017 20:07:49 +0000 (21:07 +0100)
src/wx/film_viewer.cc
src/wx/film_viewer.h

index 2b7f73e68328763c85e608617cb8df358269f4a4..50e357b5444442b110d9366109ab4e0d7603f149 100644 (file)
@@ -281,6 +281,14 @@ FilmViewer::get ()
                return;
        }
 
+       if ((time() - video.second) > one_video_frame()) {
+               /* Too late; just drop this frame before we try to get its image (which will be the time-consuming
+                  part if this frame is J2K).
+               */
+               _video_position = video.second;
+               return;
+       }
+
        /* In an ideal world, what we would do here is:
         *
         * 1. convert to XYZ exactly as we do in the DCP creation path.
@@ -324,7 +332,7 @@ FilmViewer::timer ()
        get ();
        update_position_label ();
        update_position_slider ();
-       DCPTime const next = _video_position + DCPTime::from_frames (1, _film->video_frame_rate ());
+       DCPTime const next = _video_position + one_video_frame();
 
        if (next >= _film->length()) {
                stop ();
@@ -382,10 +390,11 @@ FilmViewer::slider_moved (bool update_slider)
                return;
        }
 
+
        DCPTime t (_slider->GetValue() * _film->length().get() / 4096);
        /* Ensure that we hit the end of the film at the end of the slider */
        if (t >= _film->length ()) {
-               t = _film->length() - DCPTime::from_frames (1, _film->video_frame_rate ());
+               t = _film->length() - one_video_frame();
        }
        seek (t, false);
        update_position_label ();
@@ -529,7 +538,7 @@ FilmViewer::active_jobs_changed (optional<string> j)
 DCPTime
 FilmViewer::nudge_amount (wxMouseEvent& ev)
 {
-       DCPTime amount = DCPTime::from_frames (1, _film->video_frame_rate ());
+       DCPTime amount = one_video_frame ();
 
        if (ev.ShiftDown() && !ev.ControlDown()) {
                amount = DCPTime::from_seconds (1);
@@ -792,3 +801,9 @@ FilmViewer::set_dcp_decode_reduction (optional<int> reduction)
 {
        _player->set_dcp_decode_reduction (reduction);
 }
+
+DCPTime
+FilmViewer::one_video_frame () const
+{
+       return DCPTime::from_frames (1, _film->video_frame_rate());
+}
index 3f7a3be331a34c5f6626cb3add171f06c1fb45c2..c08409529569a8ca1c4becc9f5ed919da5f9c948 100644 (file)
@@ -94,6 +94,7 @@ private:
        void start ();
        bool stop ();
        Frame average_latency () const;
+       DCPTime one_video_frame () const;
 
        boost::shared_ptr<Film> _film;
        boost::shared_ptr<Player> _player;
@@ -136,10 +137,10 @@ private:
        bool _playing;
        boost::shared_ptr<Butler> _butler;
 
-        std::list<Frame> _latency_history;
-        /** Mutex to protect _latency_history */
-        mutable boost::mutex _latency_history_mutex;
-        int _latency_history_count;
+       std::list<Frame> _latency_history;
+       /** Mutex to protect _latency_history */
+       mutable boost::mutex _latency_history_mutex;
+       int _latency_history_count;
 
        boost::signals2::scoped_connection _config_changed_connection;
 };