///Preview timer tick function
        private void PreviewTimer_Tick(object sender, EventArgs e)
        { //1
            if (m_CurrentAudioPCMFormat == null)
            {
                return;
            }

            double StepInMs = Math.Abs(4000 * m_FwdRwdRate);
            //long lStepInBytes = CalculationFunctions.ConvertTimeToByte(StepInMs, (int)mCurrentAudio.getPCMFormat().getSampleRate(), mCurrentAudio.getPCMFormat().getBlockAlign());
            long lStepInBytes    = m_CurrentAudioPCMFormat.ConvertTimeToBytes(Convert.ToInt64(StepInMs * AudioLibPCMFormat.TIME_UNIT));
            int  PlayChunkLength = 1200;
            //long lPlayChunkLength = CalculationFunctions.ConvertTimeToByte(PlayChunkLength, (int)mCurrentAudio.getPCMFormat().getSampleRate(), mCurrentAudio.getPCMFormat().getBlockAlign());
            long lPlayChunkLength = m_CurrentAudioPCMFormat.ConvertTimeToBytes(Convert.ToInt64(PlayChunkLength * AudioLibPCMFormat.TIME_UNIT));

            if (m_CurrentAudioDataLength < lPlayChunkLength)
            {
                lPlayChunkLength = m_CurrentAudioDataLength;
                PlayChunkLength  = Convert.ToInt32(m_CurrentAudioPCMFormat.ConvertBytesToTime(lPlayChunkLength) / AudioLibPCMFormat.TIME_UNIT);
            }

            //Console.WriteLine("play chunk length " + PlayChunkLength + " : " + lPlayChunkLength);

            //lPlayChunkLength = m_CurrentAudioPCMFormat.AdjustByteToBlockAlignFrameSize (PlayChunkLength) ;
            mPreviewTimer.Interval = PlayChunkLength + REFRESH_INTERVAL_MS;

            //Console.WriteLine("mPreviewTimer.Interval " + mPreviewTimer.Interval);

            //System.Media.SystemSounds.Asterisk.Play();
            long PlayStartPos = 0;
            long PlayEndPos   = 0;

            if (m_FwdRwdRate > 0)
            { //2
              //Console.WriteLine("rate is above 0");
              //if ((mCurrentAudio.getPCMLength() - (lStepInBytes + m_lChunkStartPosition)) > lPlayChunkLength)
              //Console.WriteLine("m_CurrentAudioStream.Length " + m_CurrentAudioStream.Length + ", lStepInBytes :" + lStepInBytes + ",  m_lChunkStartPosition :" + m_lChunkStartPosition + ", lPlayChunkLength :" + lPlayChunkLength);

                if ((m_CurrentAudioDataLength - (m_lChunkStartPosition)) >= lPlayChunkLength)
                { //3
                    if (m_lChunkStartPosition > 0)
                    {
                        Console.WriteLine("m_lChunkStartPosition  , step in bytes : " + m_lChunkStartPosition + " : " + lStepInBytes);
                        m_lChunkStartPosition += lStepInBytes;
                    }
                    else
                    {
                        //m_lChunkStartPosition = mFrameSize;
                        m_lChunkStartPosition = m_CurrentAudioPCMFormat.BlockAlign;
                    }

                    PlayStartPos = m_lChunkStartPosition;
                    PlayEndPos   = m_lChunkStartPosition + lPlayChunkLength;
                    //PlayAssetStream(PlayStartPos, PlayEndPos);
                    //Console.WriteLine("play pos " + PlayStartPos + " : " + PlayEndPos);
                    //mEventsEnabled = true;
                    if (CurrentState == State.Playing)
                    {
                        //stopPlayback();
                        //m_State = State.Paused;
                    }
                    if (CurrentState != State.Playing)
                    {
                        startPlayback(PlayStartPos, PlayEndPos);
                    }

                    //mEventsEnabled = false;
                    //Console.WriteLine(CurrentState);
                    if (m_lChunkStartPosition > m_CurrentAudioStream.Length)
                    {
                        m_lChunkStartPosition = m_CurrentAudioStream.Length;
                    }
                } //-3
                else
                { //3
                    Stop();
                    AudioPlaybackFinishHandler delFinished = AudioPlaybackFinished;
                    if (!mPreviewTimer.Enabled &&
                        delFinished != null)
                    {
                        delFinished(this, new AudioPlaybackFinishEventArgs());
                        //EndOfAudioAsset(this, new Events.Audio.Player.EndOfAudioAssetEventArgs());
                    }
                } //-3
            }     //-2
            else if (m_FwdRwdRate < 0)
            { //2
                //if (m_lChunkStartPosition > (lStepInBytes ) && lPlayChunkLength <= m_Asset.getPCMLength () )
                //Console.WriteLine("rewind " + m_lChunkStartPosition);
                if (m_lChunkStartPosition > 0)
                { //3
                    if (m_lChunkStartPosition < m_CurrentAudioStream.Length)
                    {
                        m_lChunkStartPosition -= lStepInBytes;
                        if (m_lChunkStartPosition < lPlayChunkLength)
                        {
                            m_lChunkStartPosition = 0;
                        }
                    }
                    else
                    {
                        m_lChunkStartPosition = m_CurrentAudioStream.Length - lPlayChunkLength;
                    }

                    PlayStartPos = m_lChunkStartPosition;
                    PlayEndPos   = m_lChunkStartPosition + lPlayChunkLength;
                    //PlayAssetStream(PlayStartPos, PlayEndPos);
                    startPlayback(PlayStartPos, PlayEndPos);
                    if (m_lChunkStartPosition < 0)
                    {
                        m_lChunkStartPosition = 0;
                    }
                } //-3
                else
                {
                    Stop();
                    AudioPlaybackFinishHandler delFinished = AudioPlaybackFinished;
                    if (!mPreviewTimer.Enabled &&
                        delFinished != null)
                    {
                        delFinished(this, new AudioPlaybackFinishEventArgs());
                        //EndOfAudioAsset(this, new Events.Audio.Player.EndOfAudioAssetEventArgs());
                    }
                }
            } //-2
        }     //-1
Esempio n. 2
0
        private void startPlayback(long startPosition, long endPosition)
        {
            initializeBuffers();

            m_PlaybackStartPositionInCurrentAudioStream = startPosition;
            m_PlaybackEndPositionInCurrentAudioStream   = endPosition == 0
                ? m_CurrentAudioDataLength
                : endPosition;

            m_CircularBufferWritePosition = 0;

            //m_CircularBufferFlushTolerance = -1;
            //m_PredictedByteIncrement = -1;

            //m_PreviousCircularBufferPlayPosition = -1;
            //m_CircularBufferTotalBytesPlayed = -1;

            m_CurrentAudioStream          = m_CurrentAudioStreamProvider();
            m_CurrentAudioStream.Position = m_PlaybackStartPositionInCurrentAudioStream;

            int circularBufferLength = m_CircularBuffer.
#if USE_SHARPDX
                                       Capabilities
#else
                                       Caps
#endif
                                       .BufferBytes
            ;

            int bytesWrittenToCirularBuffer =
                transferBytesFromWavStreamToCircularBuffer(circularBufferLength);

            m_CurrentBytePosition = m_PlaybackStartPositionInCurrentAudioStream;

            CurrentState = State.Playing;
            //if (AllowBackToBackPlayback && m_MonitoringTimer != null) m_MonitoringTimer.Start();
            try
            {
                m_CircularBuffer.Play(0,
#if USE_SHARPDX
                                      PlayFlags.Looping
#else
                                      BufferPlayFlags.Looping // this makes it a circular buffer (which we manage manually, by tracking playback versus writing positions)
#endif
                                      );
                if (m_PlaybackStopWatch == null)
                {
                    m_PlaybackStopWatch = new Stopwatch();
                }

#if NET4
                m_PlaybackStopWatch.Restart();
#else
                m_PlaybackStopWatch.Stop();
                m_PlaybackStopWatch.Reset();
                m_PlaybackStopWatch.Start();
#endif //NET4
            }
            catch (Exception)
            {
                Debug.Fail("EmergencyStopForSoundBufferProblem !");

                CurrentState = State.Stopped;

                StopForwardRewind();
                stopPlayback();

                return;
            }

            ThreadStart threadDelegate = delegate()
            {
                bool endOfAudioStream = false;
                try
                {
                    endOfAudioStream = circularBufferRefreshThreadMethod();
                }
                catch (ThreadAbortException ex)
                {
                    //
                }
                catch (Exception ex)
                {
                    Console.WriteLine(ex.Message);
                    Console.WriteLine(ex.StackTrace);
                }
                finally
                {
                    if (m_PlaybackStopWatch != null)
                    {
                        m_PlaybackStopWatch.Stop();
                    }

                    if (mPreviewTimer.Enabled)
                    {
                        if (endOfAudioStream || CurrentState == State.Playing)
                        {
                            m_ResumeStartPosition = CurrentBytePosition;

                            CurrentState = State.Paused;                                  // before stopPlayback(), doesn't kill the stream provider
                        }
                        lock (LOCK)
                        {
                            m_CircularBufferRefreshThread = null;
                        }

                        stopPlayback();
                    }
                    else
                    {
                        if (endOfAudioStream || CurrentState == State.Playing)
                        {
                            CurrentState = State.Stopped;
                        }
                        //if (CurrentState != State.Paused) CurrentState = State.Stopped;

                        lock (LOCK)
                        {
                            m_CircularBufferRefreshThread = null;
                        }

                        StopForwardRewind();
                        stopPlayback();

                        if (endOfAudioStream)
                        {
                            AudioPlaybackFinishHandler delFinished = AudioPlaybackFinished;
                            if (delFinished != null && !mPreviewTimer.Enabled)
                            {
                                delFinished(this, new AudioPlaybackFinishEventArgs());
                            }
                        }
                    }
                }

                //Console.WriteLine("Player refresh thread exiting....");

                //CurrentState = State.Stopped;

                //lock (LOCK)
                //{
                //    //m_CircularBufferRefreshThreadIsAlive = false;
                //    m_CircularBufferRefreshThread = null;
                //}

                //Console.WriteLine("Player refresh thread exit.");
            };


            int count = 0;
            while (m_CircularBufferRefreshThread != null)
            {
                Console.WriteLine(@"------------ m_CircularBufferRefreshThread NOT null!!: " + count++);
                Thread.Sleep(20);

                if (count > 10)
                {
                    Console.WriteLine(@"------------ m_CircularBufferRefreshThread NOT null!! ()BREAK(): " + count++);
                    break;
                }
            }

            if (m_CircularBufferRefreshThread != null)
            {
                stopPlayback();
            }


            DebugFix.Assert(m_CircularBufferRefreshThread == null);

            lock (LOCK)
            {
                m_CircularBufferRefreshThread              = new Thread(threadDelegate);
                m_CircularBufferRefreshThread.Name         = "Player Refresh Thread";
                m_CircularBufferRefreshThread.Priority     = ThreadPriority.Normal;
                m_CircularBufferRefreshThread.IsBackground = true;
                m_CircularBufferRefreshThread.Start();
            }


            //Console.WriteLine("Player refresh thread start.");
        }