如何正确等待MediaPlayer打开

时间:2017-05-05 11:14:27

标签: c# wpf

我在下面跟随以下代码并附有评论。我正在寻找一种更好的方法,而无需调用Application.DoEvents()。

 public class Player : IDisposable
{                      
    public bool IsOpen
    {
        get; private set;
    }
    ///Opens the media player.  This is very fast, but the actually opening takes a bit longer.  
    ///When it does open, it fires the MediaPlayer_MediaOpened event
    public bool Open(string fileName)
    {
            // close previous file
            Close();

            mediaPlayer = new MediaPlayer();
            mediaPlayer.ScrubbingEnabled = true;
            mediaPlayer.MediaOpened += MediaPlayer_MediaOpened;
            mediaPlayer.Open(new Uri(fileName));


            return true;
    }
    /// <summary>
    /// Fires when the MediaPlayer has finished opening.
    /// </summary>
    private void MediaPlayer_MediaOpened(object sender, EventArgs e)
    {
        totalMilliseconds = mediaPlayer.NaturalDuration.TimeSpan.TotalMilliseconds;
        //40.00 represents 25 frames a second.
        int totFrames = (int)(totalMilliseconds / 40.00);
        framePixels = new uint[mediaPlayer.NaturalVideoWidth * mediaPlayer.NaturalVideoHeight];
        previousFramePixels = new uint[framePixels.Length];
        for (int i = 0; i < totFrames; i++)
            totalFrames.Add(TimeSpan.FromMilliseconds((((2 * i) + 1) * totalMilliseconds) / (2 * totFrames)));
        IsOpen = true;
    }        
}

所以,当我创建对象并打开它时,我必须等待MediaOpen事件才能触发,然后才能执行任何操作,例如抓取框架。这就是我在下面等待的方式。这是我不喜欢的部分,并希望以不同的方式做。

 player = new Player();
        player.Open("C:\\FileName.avi");

        //This is the part i don't liie.  There HAS to be a better way.  
        DateTime waitStarted = DateTime.Now;
        while (!player.IsOpen)
        {
            Thread.Sleep(5);
            if ((DateTime.Now - waitStarted).TotalSeconds >= 5)
                throw new Exception("Timed Out While Waiting For Videos To Open.");
            Application.DoEvents();
        }
        Bitmap b = player.GetNextFrame();

先谢谢你的帮助。

1 个答案:

答案 0 :(得分:0)

我没有尝试编译此代码,但我认为它会对您有所帮助。

public class Player : IDisposable
{                      
public bool IsOpen
{
    get; private set;
}

///You have to return a task to run this code asynchronously
public Task Open(string fileName)
{
        // close previous file
        Close();

        mediaPlayer = new MediaPlayer();
        mediaPlayer.ScrubbingEnabled = true;
        mediaPlayer.MediaOpened += MediaPlayer_MediaOpened;

        return Task.Run(mediaPlayer.Open(new Uri(fileName)));
}
/// <summary>
/// Fires when the MediaPlayer has finished opening.
/// </summary>
private void MediaPlayer_MediaOpened(object sender, EventArgs e)
{
    totalMilliseconds = mediaPlayer.NaturalDuration.TimeSpan.TotalMilliseconds;
    //40.00 represents 25 frames a second.
    int totFrames = (int)(totalMilliseconds / 40.00);
    framePixels = new uint[mediaPlayer.NaturalVideoWidth * mediaPlayer.NaturalVideoHeight];
    previousFramePixels = new uint[framePixels.Length];
    for (int i = 0; i < totFrames; i++) {
        totalFrames.Add(TimeSpan.FromMilliseconds((((2 * i) + 1) * totalMilliseconds) / (2 * totFrames)));
        IsOpen = true;
    }        
}
    player = new Player();
    //The program wait the player to open before continuing
    //you'll need to add the async keyword on the signature method containing this code.
    await player.Open("C:\\FileName.avi");

    Bitmap b = player.GetNextFrame();

更多资源herehere