Added virtual pause() method into osg::AudioSink to support pausing of a movie thread and it's associated audio.

Updated osgmovie plugin to use the pause support.
This commit is contained in:
Robert Osfield 2010-01-07 14:35:17 +00:00
parent 47af634399
commit 5d9bf9f4d5
4 changed files with 82 additions and 34 deletions

View File

@ -383,16 +383,21 @@ class SDLAudioSink : public osg::AudioSink
public: public:
SDLAudioSink(osg::AudioStream* audioStream): SDLAudioSink(osg::AudioStream* audioStream):
_playing(false), _started(false),
_paused(false),
_audioStream(audioStream) {} _audioStream(audioStream) {}
~SDLAudioSink(); ~SDLAudioSink();
virtual void startPlaying(); virtual void play();
virtual bool playing() const { return _playing; } virtual void pause();
virtual void stop();
virtual bool playing() const { return _started && !_paused; }
bool _playing; bool _started;
bool _paused;
osg::observer_ptr<osg::AudioStream> _audioStream; osg::observer_ptr<osg::AudioStream> _audioStream;
}; };
@ -670,19 +675,24 @@ static void soundReadCallback(void * user_data, uint8_t * data, int datalen)
SDLAudioSink::~SDLAudioSink() SDLAudioSink::~SDLAudioSink()
{ {
if (_playing) stop();
{
SDL_PauseAudio(1);
SDL_CloseAudio();
osg::notify(osg::NOTICE)<<"~SDLAudioSink() destructor, but still playing"<<std::endl;
}
} }
void SDLAudioSink::startPlaying() void SDLAudioSink::play()
{ {
_playing = true; if (_started)
{
if (_paused)
{
SDL_PauseAudio(0);
_paused = false;
}
return;
}
_started = true;
_paused = false;
osg::notify(osg::NOTICE)<<"SDLAudioSink()::startPlaying()"<<std::endl; osg::notify(osg::NOTICE)<<"SDLAudioSink()::startPlaying()"<<std::endl;
osg::notify(osg::NOTICE)<<" audioFrequency()="<<_audioStream->audioFrequency()<<std::endl; osg::notify(osg::NOTICE)<<" audioFrequency()="<<_audioStream->audioFrequency()<<std::endl;
@ -707,6 +717,25 @@ void SDLAudioSink::startPlaying()
} }
void SDLAudioSink::pause()
{
if (_started)
{
SDL_PauseAudio(1);
_paused = true;
}
}
void SDLAudioSink::stop()
{
if (_started)
{
if (!_paused) SDL_PauseAudio(1);
SDL_CloseAudio();
osg::notify(osg::NOTICE)<<"~SDLAudioSink() destructor, but still playing"<<std::endl;
}
}
#endif #endif

View File

@ -26,14 +26,18 @@ public:
AudioSink(); AudioSink();
virtual void startPlaying() = 0; virtual const char * libraryName() const { return "osg"; }
virtual const char * className() const { return "AudioSinkInterface"; }
virtual void play() = 0;
virtual void pause() = 0;
virtual void stop() = 0;
virtual bool playing() const = 0; virtual bool playing() const = 0;
virtual double getDelay() const { return _delay; } virtual double getDelay() const { return _delay; }
virtual void setDelay(const double delay) { _delay = delay; } virtual void setDelay(const double delay) { _delay = delay; }
virtual const char * libraryName() const { return "osgFFmpeg"; }
virtual const char * className() const { return "AudioSinkInterface"; }
private: private:

View File

@ -91,10 +91,15 @@ void FFmpegDecoderAudio::open(AVStream * const stream)
void FFmpegDecoderAudio::pause(bool pause) void FFmpegDecoderAudio::pause(bool pause)
{ {
if(pause) if (pause != m_paused)
m_paused = true; {
else m_paused = pause;
m_paused = false; if (m_audio_sink.valid())
{
if (m_paused) m_audio_sink->pause();
else m_audio_sink->play();
}
}
} }
void FFmpegDecoderAudio::close(bool waitForThreadToExit) void FFmpegDecoderAudio::close(bool waitForThreadToExit)
@ -183,7 +188,7 @@ void FFmpegDecoderAudio::decodeLoop()
if (! skip_audio && ! m_audio_sink->playing()) if (! skip_audio && ! m_audio_sink->playing())
{ {
m_clocks.audioSetDelay(m_audio_sink->getDelay()); m_clocks.audioSetDelay(m_audio_sink->getDelay());
m_audio_sink->startPlaying(); m_audio_sink->play();
} }
else else
{ {

View File

@ -28,9 +28,29 @@ BEGIN_ABSTRACT_OBJECT_REFLECTOR(osg::AudioSink)
I_Constructor0(____AudioSink, I_Constructor0(____AudioSink,
"", "",
""); "");
I_Method0(void, startPlaying, I_Method0(const char *, libraryName,
Properties::VIRTUAL,
__C5_char_P1__libraryName,
"return the name of the object's library. ",
"Must be defined by derived classes. The OpenSceneGraph convention is that the namespace of a library is the same as the library name. ");
I_Method0(const char *, className,
Properties::VIRTUAL,
__C5_char_P1__className,
"return the name of the object's class type. ",
"Must be defined by derived classes. ");
I_Method0(void, play,
Properties::PURE_VIRTUAL, Properties::PURE_VIRTUAL,
__void__startPlaying, __void__play,
"",
"");
I_Method0(void, pause,
Properties::PURE_VIRTUAL,
__void__pause,
"",
"");
I_Method0(void, stop,
Properties::PURE_VIRTUAL,
__void__stop,
"", "",
""); "");
I_Method0(bool, playing, I_Method0(bool, playing,
@ -48,16 +68,6 @@ BEGIN_ABSTRACT_OBJECT_REFLECTOR(osg::AudioSink)
__void__setDelay__C5_double, __void__setDelay__C5_double,
"", "",
""); "");
I_Method0(const char *, libraryName,
Properties::VIRTUAL,
__C5_char_P1__libraryName,
"return the name of the object's library. ",
"Must be defined by derived classes. The OpenSceneGraph convention is that the namespace of a library is the same as the library name. ");
I_Method0(const char *, className,
Properties::VIRTUAL,
__C5_char_P1__className,
"return the name of the object's class type. ",
"Must be defined by derived classes. ");
I_SimpleProperty(double, Delay, I_SimpleProperty(double, Delay,
__double__getDelay, __double__getDelay,
0); 0);