You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WinUI3媒体播放器按钮失效及ArgumentException异常修复求助

WinUI3 媒体播放器命令按钮异常问题

问题现象

  • 仅快进按钮功能正常
  • 后退按钮点击一次后失效
  • 上一曲、下一曲按钮无任何响应
  • 断点调试显示仅CommandManager_FastForwardReceived函数被触发,其余处理函数均未执行
  • 尝试修复过程中抛出异常:Exception thrown: 'System.ArgumentException' in WinRT.Runtime.dll

相关代码

事件注册代码

mp.MediaPlayer.CommandManager.PreviousReceived += CommandManager_PreviousReceived;
mp.MediaPlayer.CommandManager.FastForwardReceived += CommandManager_FastForwardReceived;
mp.MediaPlayer.CommandManager.RewindReceived += CommandManager_RewindReceived;

事件处理函数

private void CommandManager_NextReceived(MediaPlaybackCommandManager sender ,
        MediaPlaybackCommandManagerNextReceivedEventArgs args) {
    DispatcherQueue.TryEnqueue(() => {
        args.Handled = true;
        PlayNextInQueue();
    });
}

private void CommandManager_PreviousReceived(MediaPlaybackCommandManager sender ,
        MediaPlaybackCommandManagerPreviousReceivedEventArgs args) {
    DispatcherQueue.TryEnqueue(() => {
        args.Handled = true;
        PlayPreviousInQueue();
    });
}

private void CommandManager_FastForwardReceived(MediaPlaybackCommandManager sender ,
        MediaPlaybackCommandManagerFastForwardReceivedEventArgs args) {
    args.Handled = true;
    if ((mp.MediaPlayer.PlaybackSession.NaturalDuration.TotalSeconds - mp.MediaPlayer.Position.TotalSeconds) <= 5) {
        PlayNextInQueue();
    }
    else {
        mp.MediaPlayer.Position += TimeSpan.FromSeconds(5);
    }
}

private void CommandManager_RewindReceived(MediaPlaybackCommandManager sender ,
     MediaPlaybackCommandManagerRewindReceivedEventArgs args) {
    DispatcherQueue.TryEnqueue(() => {
        args.Handled = true;
        if (mp.MediaPlayer.Position.TotalSeconds > 5) {
            mp.MediaPlayer.Position -= TimeSpan.FromSeconds(5);
        }
        else {
            mp.MediaPlayer.Position = TimeSpan.Zero;
        }
    });
}

修复方案

  1. 补全事件注册
    下一曲按钮无响应是因为未注册NextReceived事件,添加以下代码:

    mp.MediaPlayer.CommandManager.NextReceived += CommandManager_NextReceived;
    
  2. 修正DispatcherQueue使用逻辑
    后退、上一曲等按钮失效的核心原因是:在异步队列中设置args.Handled = true,导致系统无法及时识别事件已处理,进而出现重复触发或失效。需先同步标记事件已处理,再将UI相关操作放入DispatcherQueue:

    • 修改CommandManager_PreviousReceived:
      private void CommandManager_PreviousReceived(MediaPlaybackCommandManager sender ,
              MediaPlaybackCommandManagerPreviousReceivedEventArgs args) {
          args.Handled = true;
          DispatcherQueue.TryEnqueue(() => {
              PlayPreviousInQueue();
          });
      }
      
    • 修改CommandManager_RewindReceived:
      private void CommandManager_RewindReceived(MediaPlaybackCommandManager sender ,
           MediaPlaybackCommandManagerRewindReceivedEventArgs args) {
          args.Handled = true;
          DispatcherQueue.TryEnqueue(() => {
              if (mp.MediaPlayer.Position.TotalSeconds > 5) {
                  mp.MediaPlayer.Position -= TimeSpan.FromSeconds(5);
              }
              else {
                  mp.MediaPlayer.Position = TimeSpan.Zero;
              }
          });
      }
      
    • 修改CommandManager_NextReceived:
      private void CommandManager_NextReceived(MediaPlaybackCommandManager sender ,
              MediaPlaybackCommandManagerNextReceivedEventArgs args) {
          args.Handled = true;
          DispatcherQueue.TryEnqueue(() => {
              PlayNextInQueue();
          });
      }
      
  3. 排查ArgumentException异常
    该异常通常由线程不安全访问或操作已释放对象导致:

    • 确保mp.MediaPlayer在事件触发时未被销毁或释放
    • 所有对MediaPlayer及其属性的访问都通过DispatcherQueue.TryEnqueue切换到UI线程执行
    • 检查PlayNextInQueue和PlayPreviousInQueue方法,确认是否存在传递无效参数(如空媒体源)的情况

内容的提问来源于stack exchange,提问作者tribeti

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.21 10:33:26