避免在UWP MediaPlayerElement和MediaPlayer中显示第一帧视频

时间:2018-01-15 22:19:40

标签: c# uwp

我正在开发一个UWP应用程序,向用户显示一系列短视频。对于这个应用程序,用户想要开始在视频中间的某个地方观看视频(并不总是相同),但如果需要,可以回到开头。

该应用使用Windows Fall Creators Update(1709)和最新的UWP SDK(6.0.6)

使用MediaPlayerElementMediaPlayer

当我设置新的源视频文件时,无论我如何尝试设置位置,它似乎总是显示视频的第一帧。

如果我在设置源之前设置了所需的位置,MediaPlayerElement将转到当前视频中的该位置,然后在位置0开始新视频。

_mediaPlayer.PlaybackSession.Position = TimeSpan.FromSeconds(10);
_mediaPlayer.Source = playbackItem;

如果我将信号源设置为null,然后在设置信号源之前设置所需的位置,MediaPlayerElement会闪烁黑色,这是不稳定的,不可取。

_mediaPlayer.Source = null;
_mediaPlayer.PlaybackSession.Position = TimeSpan.FromSeconds(10);
_mediaPlayer.Source = playbackItem;

如果我在设置来源后设置了位置,MediaPlayerElement会显示第一帧,然后转到10s的位置。

_mediaPlayer.Source = playbackItem;
_mediaPlayer.PlaybackSession.Position = TimeSpan.FromSeconds(10);

如果我在更改源时触发的任何事件回调中设置位置,它仍然会在10s显示帧之前显示第一帧。

我也尝试过使用StartPosition的MediaPlaybackItem构造函数。这会在10s处启动视频,但它会将StartPosition解释为现在为t=0s,因此您无法在StartPosition之前看到该视频。

我有什么遗失的吗?或者是一种创造性的方式来直接进入我想要的视频帧,而不在文件的开头显示帧?

2 个答案:

答案 0 :(得分:0)

我在我的设备上尝试了这个,与你形成鲜明对比的是,无论我做什么,我总能看到所请求的帧,所以它似乎取决于以某种方式使用的视频源。

MediaPlayer有一个SeekCompleted方法,只有在位置更改请求完成且视频准备好播放后才会触发。您可以完全隐藏MediaPlayerElement并仅在此事件触发后将其设为Visible

答案 1 :(得分:0)

  

我有什么遗失的吗?或者是一种创造性的方式来直接进入我想要的视频帧,而不在文件的开头显示帧?

默认情况下,

MediaElement会加载视频第一帧。对于此功能,如果您要加载另一个框架,可以使用MediaClipVideoPlayer加载的事件中剪辑视频片段,如下所示:

var videoFile = await Package.Current.InstalledLocation.GetFileAsync("big_buck_bunny.mp4");

// Create a MediaClip from the video file and apply our video effect
MediaClip clip = await MediaClip.CreateFromFileAsync(videoFile);
clip.TrimTimeFromStart = TimeSpan.FromSeconds(17);
clip.TrimTimeFromEnd = TimeSpan.FromSeconds(10);

// Create a MediaComposition object that will allow us to generate a stream source
MediaComposition compositor = new MediaComposition();
compositor.Clips.Add(clip);

// Set the stream source to the MediaElement control
this.VideoPlayer.SetMediaStreamSource(compositor.GenerateMediaStreamSource());
this.VideoPlayer.AutoPlay = false;

然后当您点击播放按钮时,您可以在CurrentStateChanged事件处理程序中手动修改媒体源。

private void VideoPlayer_CurrentStateChanged(object sender, RoutedEventArgs e)
{
    switch (this.VideoPlayer.CurrentState)
    {
        case MediaElementState.Paused:

            break;

        case MediaElementState.Playing:
            if (!this.VideoPlayer.AutoPlay)
            {
                this.VideoPlayer.Source = new Uri("ms-appx:///big_buck_bunny.mp4");
                this.VideoPlayer.AutoPlay = true;
            }
            break;
    }
}

有关详情,请参阅Media compositions and editing