Wpf 如何确定MediaElement是否正在播放?
看起来很简单,但我想不出任何方法来确定MediaElement的状态。有些状态有各种属性(如IsBuffering),但我找不到任何状态的属性,如Play、Pause等。Silverlight似乎有一个CurrentState属性来显示所有这些 目前,我判断视频是否应该播放的方式是观看各种事件和一个计时器,检查是否有任何进展Wpf 如何确定MediaElement是否正在播放?,wpf,mediaelement,Wpf,Mediaelement,看起来很简单,但我想不出任何方法来确定MediaElement的状态。有些状态有各种属性(如IsBuffering),但我找不到任何状态的属性,如Play、Pause等。Silverlight似乎有一个CurrentState属性来显示所有这些 目前,我判断视频是否应该播放的方式是观看各种事件和一个计时器,检查是否有任何进展 我不熟悉MediaElement和WPF(实际上我只在WinForms应用程序中使用MediaElement)。我遗漏了什么吗?你没有遗漏任何东西。您几乎必须手动跟踪媒体是
我不熟悉MediaElement和WPF(实际上我只在WinForms应用程序中使用MediaElement)。我遗漏了什么吗?你没有遗漏任何东西。您几乎必须手动跟踪媒体是否正在播放。很遗憾,正如你提到的,在Silverlight中很容易。对我来说,这似乎是一个重大疏忽。我所做的是“解决”MediaPlayer子类(这也适用于MediaElement),并添加我自己的播放/暂停/停止方法。在这些方法中,我维护一个表示回放状态的字段。此外,您还需要挂接MediaEnded,以便将状态从“播放”更改为“停止”。对于WPFMediaElement,以下是我使用的解决方案/解决方法:
bool IsPlaying()
{
var pos1 = wpfMediaElement.Position;
System.Threading.Thread.Sleep(1);
var pos2 = wpfMediaElement.Position;
return pos2 != pos1;
}
您可以使用反射获取
\u currentState
成员
private MediaState GetMediaState(MediaElement myMedia)
{
FieldInfo hlp = typeof(MediaElement).GetField("_helper", BindingFlags.NonPublic | BindingFlags.Instance);
object helperObject = hlp.GetValue(myMedia);
FieldInfo stateField = helperObject.GetType().GetField("_currentState", BindingFlags.NonPublic | BindingFlags.Instance);
MediaState state = (MediaState)stateField.GetValue(helperObject);
return state;
}
这包括播放/暂停,但不会在结束时从“播放”更改为“停止”
您可以通过向
MediaEnded
事件添加事件处理程序,并运行.Stop()
方法来解决此问题,这样可以正确更改状态(可以通过上述方法拾取)对于Silverlight
使用CurrentState检查状态是正在播放还是暂停
if (YourMediaElementName.CurrentState == MediaElementState.Playing)
{
// TODO: when media is playing.
}
对于
通用Windows 10平台(UWP)
:
如果您想改用枚举
,请参见以下内容:
if (yourMediaElement.CurrentState == MediaElementState.Playing)
{
//nou yourMediaElement is playng
}
对于WPF,请使用以下命令:
var playing=player.Position并且可以基于Rich S实现扩展
//don't forget
using System.Windows.Controls;
using System.Reflection;
public static class Util
{
public static MediaState GetMediaState(this MediaElement myMedia)
{
FieldInfo hlp = typeof(MediaElement).GetField("_helper", BindingFlags.NonPublic | BindingFlags.Instance);
object helperObject = hlp.GetValue(myMedia);
FieldInfo stateField = helperObject.GetType().GetField("_currentState", BindingFlags.NonPublic | BindingFlags.Instance);
MediaState state = (MediaState)stateField.GetValue(helperObject);
return state;
}
}
把它放到CodePlex上。如果你没有时间,我打算,只是不想踩到任何脚趾。那是可怕的解决办法。如果你在UI线程中调用这个方法,整个UI将是forzen。我同意,这不是最好的方法。但我敢打赌,这个世界上没有人会在小程序上意识到这一毫秒。这是亚历克斯·威奇的一个变通办法,我称之为“快脏”,为此我将放弃投票。通过访问隐藏字段来使用隐藏的HeperProperty并不是一个“好的解决方案”。。媒体元素没有状态属性是非常可怕的解决方案。。。也没有人让你在UI线程中调用它。很好的解决方案!除非微软在将来某个时候重新命名这个领域,否则这对我来说是非常有效的。谢谢我看到了重命名的潜在危险,但我们还有什么其他解决方案?下面引用的CurrentState
在现代完整WPF中不存在。应该注意的是CurrentState
仅是Silverlight。我已经在WPF GitHub存储库中添加了一个关于此的功能请求。请去竖起大拇指。
//don't forget
using System.Windows.Controls;
using System.Reflection;
public static class Util
{
public static MediaState GetMediaState(this MediaElement myMedia)
{
FieldInfo hlp = typeof(MediaElement).GetField("_helper", BindingFlags.NonPublic | BindingFlags.Instance);
object helperObject = hlp.GetValue(myMedia);
FieldInfo stateField = helperObject.GetType().GetField("_currentState", BindingFlags.NonPublic | BindingFlags.Instance);
MediaState state = (MediaState)stateField.GetValue(helperObject);
return state;
}
}