mirror of
https://github.com/panda3d/panda3d.git
synced 2025-09-30 16:58:40 -04:00
further attempts to fix ffmpeg. sheesh.
This commit is contained in:
parent
d30783c8b1
commit
9a810db5d2
@ -50,6 +50,14 @@ ConfigVariableInt ffmpeg_max_readahead_frames
|
|||||||
"should read in advance of actual playback. Set this to 0 to "
|
"should read in advance of actual playback. Set this to 0 to "
|
||||||
"decode ffmpeg videos in the main thread."));
|
"decode ffmpeg videos in the main thread."));
|
||||||
|
|
||||||
|
ConfigVariableBool ffmpeg_support_seek
|
||||||
|
("ffmpeg-support-seek", true,
|
||||||
|
PRC_DESC("True to use the av_seek_frame() function to seek within ffmpeg "
|
||||||
|
"video files. If this is false, Panda will only seek within a "
|
||||||
|
"file by reading it from the beginning until the desired point, "
|
||||||
|
"which can be much slower. Set this false only if you suspect "
|
||||||
|
"a problem with av_seek_frame()."));
|
||||||
|
|
||||||
ConfigVariableEnum<ThreadPriority> ffmpeg_thread_priority
|
ConfigVariableEnum<ThreadPriority> ffmpeg_thread_priority
|
||||||
("ffmpeg-thread-priority", TP_normal,
|
("ffmpeg-thread-priority", TP_normal,
|
||||||
PRC_DESC("The default thread priority at which to start ffmpeg decoder "
|
PRC_DESC("The default thread priority at which to start ffmpeg decoder "
|
||||||
|
@ -19,6 +19,7 @@
|
|||||||
#include "notifyCategoryProxy.h"
|
#include "notifyCategoryProxy.h"
|
||||||
#include "configVariableEnum.h"
|
#include "configVariableEnum.h"
|
||||||
#include "configVariableInt.h"
|
#include "configVariableInt.h"
|
||||||
|
#include "configVariableBool.h"
|
||||||
#include "threadPriority.h"
|
#include "threadPriority.h"
|
||||||
#include "dconfig.h"
|
#include "dconfig.h"
|
||||||
|
|
||||||
@ -27,6 +28,7 @@ NotifyCategoryDecl(movies, EXPCL_PANDA_MOVIES, EXPTP_PANDA_MOVIES);
|
|||||||
NotifyCategoryDecl(ffmpeg, EXPCL_PANDA_MOVIES, EXPTP_PANDA_MOVIES);
|
NotifyCategoryDecl(ffmpeg, EXPCL_PANDA_MOVIES, EXPTP_PANDA_MOVIES);
|
||||||
|
|
||||||
extern ConfigVariableInt ffmpeg_max_readahead_frames;
|
extern ConfigVariableInt ffmpeg_max_readahead_frames;
|
||||||
|
extern ConfigVariableBool ffmpeg_support_seek;
|
||||||
extern ConfigVariableEnum<ThreadPriority> ffmpeg_thread_priority;
|
extern ConfigVariableEnum<ThreadPriority> ffmpeg_thread_priority;
|
||||||
|
|
||||||
extern EXPCL_PANDA_MOVIES void init_libmovies();
|
extern EXPCL_PANDA_MOVIES void init_libmovies();
|
||||||
|
@ -104,8 +104,8 @@ init_from(FfmpegVideo *source) {
|
|||||||
memset(_packet1, 0, sizeof(AVPacket));
|
memset(_packet1, 0, sizeof(AVPacket));
|
||||||
|
|
||||||
fetch_packet(0);
|
fetch_packet(0);
|
||||||
_initial_dts = _packet0->dts;
|
|
||||||
fetch_frame(-1);
|
fetch_frame(-1);
|
||||||
|
_initial_dts = _begin_frame;
|
||||||
|
|
||||||
_current_frame = -1;
|
_current_frame = -1;
|
||||||
_eof_known = false;
|
_eof_known = false;
|
||||||
@ -341,7 +341,10 @@ set_time(double time, int loop_count) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ffmpeg_cat.is_spam() /* && frame != _current_frame*/) {
|
// No point in trying to position before the first frame.
|
||||||
|
frame = max(frame, _initial_dts);
|
||||||
|
|
||||||
|
if (ffmpeg_cat.is_spam() && frame != _current_frame) {
|
||||||
ffmpeg_cat.spam()
|
ffmpeg_cat.spam()
|
||||||
<< "set_time(" << time << "): " << frame << ", loop_count = " << loop_count << "\n";
|
<< "set_time(" << time << "): " << frame << ", loop_count = " << loop_count << "\n";
|
||||||
}
|
}
|
||||||
@ -656,7 +659,15 @@ thread_main() {
|
|||||||
<< "ffmpeg thread for " << _filename.get_basename() << " starting.\n";
|
<< "ffmpeg thread for " << _filename.get_basename() << " starting.\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
// Repeatedly wait for something interesting to do, until we're told
|
// First, push the first frame onto the readahead queue.
|
||||||
|
if (_frame_ready) {
|
||||||
|
PT(FfmpegBuffer) frame = do_alloc_frame();
|
||||||
|
export_frame(frame);
|
||||||
|
MutexHolder holder(_lock);
|
||||||
|
_readahead_frames.push_back(frame);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Now repeatedly wait for something interesting to do, until we're told
|
||||||
// to shut down.
|
// to shut down.
|
||||||
while (_thread_status != TS_shutdown) {
|
while (_thread_status != TS_shutdown) {
|
||||||
nassertv(_thread_status != TS_stopped);
|
nassertv(_thread_status != TS_stopped);
|
||||||
@ -952,6 +963,7 @@ seek(int frame, bool backward) {
|
|||||||
static PStatCollector seek_pcollector("*:FFMPEG Video Decoding:Seek");
|
static PStatCollector seek_pcollector("*:FFMPEG Video Decoding:Seek");
|
||||||
PStatTimer timer(seek_pcollector);
|
PStatTimer timer(seek_pcollector);
|
||||||
|
|
||||||
|
if (ffmpeg_support_seek) {
|
||||||
// Protect the call to av_seek_frame() in a global lock, just to be
|
// Protect the call to av_seek_frame() in a global lock, just to be
|
||||||
// paranoid.
|
// paranoid.
|
||||||
ReMutexHolder av_holder(_av_lock);
|
ReMutexHolder av_holder(_av_lock);
|
||||||
@ -964,7 +976,6 @@ seek(int frame, bool backward) {
|
|||||||
int flags = 0;
|
int flags = 0;
|
||||||
if (backward) {
|
if (backward) {
|
||||||
flags = AVSEEK_FLAG_BACKWARD;
|
flags = AVSEEK_FLAG_BACKWARD;
|
||||||
//reset_stream();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (av_seek_frame(_format_ctx, _video_index, target_ts, flags) < 0) {
|
if (av_seek_frame(_format_ctx, _video_index, target_ts, flags) < 0) {
|
||||||
@ -976,7 +987,8 @@ seek(int frame, bool backward) {
|
|||||||
if (backward) {
|
if (backward) {
|
||||||
// Now try to seek forward.
|
// Now try to seek forward.
|
||||||
reset_stream();
|
reset_stream();
|
||||||
return seek(frame, false);
|
seek(frame, false);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Try a binary search to get a little closer.
|
// Try a binary search to get a little closer.
|
||||||
@ -986,32 +998,19 @@ seek(int frame, bool backward) {
|
|||||||
<< "Seek double failure.\n";
|
<< "Seek double failure.\n";
|
||||||
}
|
}
|
||||||
reset_stream();
|
reset_stream();
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
|
||||||
// Close and re-open the codec (presumably to flush the queue).
|
|
||||||
// Actually, this causes the stream to fail in certain video
|
|
||||||
// files, and doesn't seem to have any useful benefit. So screw
|
|
||||||
// it, and don't do this.
|
|
||||||
|
|
||||||
/*
|
|
||||||
avcodec_close(_video_ctx);
|
|
||||||
AVCodec *pVideoCodec = avcodec_find_decoder(_video_ctx->codec_id);
|
|
||||||
if (pVideoCodec == 0) {
|
|
||||||
cleanup();
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (avcodec_open(_video_ctx, pVideoCodec)<0) {
|
|
||||||
cleanup();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fetch_packet(0);
|
fetch_packet(0);
|
||||||
fetch_frame(-1);
|
fetch_frame(-1);
|
||||||
|
|
||||||
|
} else {
|
||||||
|
// If seeking isn't supported, close-and-reopen.
|
||||||
|
if (backward) {
|
||||||
|
reset_stream();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
@ -1065,7 +1064,6 @@ reset_stream() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fetch_packet(0);
|
fetch_packet(0);
|
||||||
_initial_dts = _packet0->dts;
|
|
||||||
fetch_frame(-1);
|
fetch_frame(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user