+ sdl_unlock_display();
+ }
+ }
+
+ return 0;
+}
+
+static void *video_thread( void *arg )
+{
+ // Identify the arg
+ consumer_sdl this = arg;
+
+ // Obtain time of thread start
+ struct timeval now;
+ int64_t start = 0;
+ int64_t elapsed = 0;
+ struct timespec tm;
+ mlt_frame next = NULL;
+ mlt_properties properties = NULL;
+ double speed = 0;
+
+ // Get real time flag
+ int real_time = mlt_properties_get_int( this->properties, "real_time" );
+
+ // Get the current time
+ gettimeofday( &now, NULL );
+
+ // Determine start time
+ start = ( int64_t )now.tv_sec * 1000000 + now.tv_usec;
+
+ while ( this->running )
+ {
+ // Pop the next frame
+ pthread_mutex_lock( &this->video_mutex );
+ while ( ( next = mlt_deque_pop_front( this->queue ) ) == NULL && this->running )
+ pthread_cond_wait( &this->video_cond, &this->video_mutex );
+ pthread_mutex_unlock( &this->video_mutex );
+
+ // Get the properties
+ properties = mlt_frame_properties( next );
+
+ // Get the speed of the frame
+ speed = mlt_properties_get_double( properties, "_speed" );
+
+ // Get the current time
+ gettimeofday( &now, NULL );
+
+ // Get the elapsed time
+ elapsed = ( ( int64_t )now.tv_sec * 1000000 + now.tv_usec ) - start;
+
+ // See if we have to delay the display of the current frame
+ if ( mlt_properties_get_int( properties, "rendered" ) == 1 && this->running )
+ {
+ // Obtain the scheduled playout time
+ mlt_position scheduled = mlt_properties_get_position( properties, "playtime" );
+
+ // Determine the difference between the elapsed time and the scheduled playout time
+ mlt_position difference = scheduled - elapsed;
+
+ // Smooth playback a bit
+ if ( real_time && ( difference > 20000 && speed == 1.0 ) )
+ {
+ tm.tv_sec = difference / 1000000;
+ tm.tv_nsec = ( difference % 1000000 ) * 500;
+ nanosleep( &tm, NULL );
+ }
+
+ // Show current frame if not too old
+ if ( !real_time || ( difference > -10000 || speed != 1.0 || mlt_deque_count( this->queue ) < 2 ) )
+ consumer_play_video( this, next );
+
+ // If the queue is empty, recalculate start to allow build up again
+ if ( real_time && ( mlt_deque_count( this->queue ) == 0 && speed == 1.0 ) )
+ {
+ gettimeofday( &now, NULL );
+ start = ( ( int64_t )now.tv_sec * 1000000 + now.tv_usec ) - scheduled + 20000;
+ }
+ }
+
+ // This frame can now be closed
+ mlt_frame_close( next );
+ }
+
+ mlt_consumer_stopped( &this->parent );