Exemplo n.º 1
0
        /// <summary>
        /// Playing process
        /// </summary>
        private void PlaybackThread()
        {
            bool Running = true;

            while (Running)
            {
                if (m_SeekRequested)
                {
                    Thread.Sleep(10); continue;
                }
                if (m_StopRequested)
                {
                    Running = false; continue;
                }
                if (m_PlayerState == OggPlayerStatus.Error)
                {
                    Running = false; continue;
                }
                if (m_PauseRequested)
                {
                    Thread.Sleep(10); continue;
                }


                // Check currently queued buffers
                int QueuedBuffers;
                AL.GetSource(m_Source, ALGetSourcei.BuffersQueued, out QueuedBuffers);
                // Check for underruns/playback complete
                // We're using -two- 'cos it doesn't seem to handle the last buffer properly (and the last 2 on windows systems
                // (not sure why yet - need to do some investigatling). This shouldn't cause any problems unless a large Buffer_Size is set
                // Anyway: Fear the evil magic hack 'cos this should really be if (QueuedBuffers<=0)
                if (QueuedBuffers <= 2)
                {
                    if (m_ReachedEOF)
                    {
                        if (AL.GetSourceState(m_Source) != ALSourceState.Stopped)
                        {
                            AL.SourceStop(m_Source);
                        }
                        Playback_Stop(true);
                        StateChange(OggPlayerStatus.Stopped, OggPlayerStateChanger.EndOfFile);
                        SendMessage(OggPlayerMessageType.PlaybackEndOfFile);
                        Running = false;
                    }
                    else
                    {
                        SendMessage(OggPlayerMessageType.BufferUnderrun);
                        if (!BufferThread.IsAlive)
                        {
                            BufferThread.Start();
                        }
                        Thread.Sleep(m_PrebufferDelay);
                    }
                    continue;
                }

                // See if we're playing
                if (AL.GetSourceState(m_Source) != ALSourceState.Playing)
                {
                    lock (OALLocker) { AL.SourcePlay(m_Source); }
                                        #if (DEBUG)
                    Console.WriteLine("Source restarted");
                                        #endif
                }

                // Count processed buffers
                int ProcessedBuffers;
                AL.GetSource(m_Source, ALGetSourcei.BuffersProcessed, out ProcessedBuffers);
                if (ProcessedBuffers > 0)
                {
                    // We've got some buffers to desclurple
                    lock (OALLocker)
                    {
                        while (ProcessedBuffers > 0)
                        {
                            // Unqueue the first buffer from the source
                            AL.SourceUnqueueBuffer((int)m_Source);
                            // De-allocate the buffer from memory
                            if (m_BufferRefs.Count > 0)
                            {
                                uint BufferRef = (uint)m_BufferRefs.Dequeue();
                                if (!AL.IsBuffer(BufferRef))
                                {
                                    SendMessage(OggPlayerMessageType.BufferAnomaly);
                                }
                                AL.DeleteBuffer(ref BufferRef);
                            }
                            else
                            {
                                SendMessage(OggPlayerMessageType.BufferHeapAnomaly);
                            }
                            // Update the internal quantity tracking
                            m_BufferedSizeHeap.Pop();
                            m_PlayingOffset += m_BufferedTimeHeap.Pop();
                            // Decrement processed buffers & loop
                            ProcessedBuffers--;
                        }
                    }

                    // Check tick events
                    if (m_PlayingOffset >= m_LastTick + m_TickInterval)
                    {
                        m_LastTick = m_PlayingOffset;
                        if (TickEnabled)
                        {
                            SendTick(m_PlayingOffset, m_BufferOffset);
                        }
                    }
                }
                else
                {
                    Thread.Sleep(10);
                }

                if (m_UpdateDelay > 0)
                {
                    Thread.Sleep(m_UpdateDelay);
                }
            }
        }