C# 如何仅在第一个声音文件结束时播放声音文件?

C# 如何仅在第一个声音文件结束时播放声音文件?,c#,uwp,C#,Uwp,我有以下代码: MediaElement player = new MediaElement(); Windows.Storage.StorageFolder folder; Windows.Storage.StorageFile file; string FileName = ""; private async void Play(string Tno, string Cno) { folder = await Windows.

我有以下代码:

    MediaElement player = new MediaElement();
    Windows.Storage.StorageFolder folder;
    Windows.Storage.StorageFile file;
    string FileName = "";

    private async void Play(string Tno, string Cno)
    {
        folder = await Windows.ApplicationModel.Package.Current.InstalledLocation.GetFolderAsync("Assets");

        for (int i = 1; i <= 4; i++)
        {
            switch (i)
            {
                case 1:
                    FileName = "Sound\\mysound1.wav";
                    break;
                case 2:
                    FileName = "Sound\\mysound2.wav";
                    break;
                case 3:
                    FileName = "Sound\\mysound3.wav";
                    break;
                case 4:
                    FileName = "Sound\\mysound4.wav";
                    break;
            }

            file = await folder.GetFileAsync(FileName);
            player.SetSource(await file.OpenAsync(Windows.Storage.FileAccessMode.Read), file.ContentType);
            player.Play();
    }
}
MediaElement播放器=新的MediaElement();
Windows.Storage.StorageFolder文件夹;
Windows.Storage.StorageFile文件;
字符串FileName=“”;
专用异步无效播放(字符串Tno、字符串Cno)
{
folder=等待Windows.ApplicationModel.Package.Current.InstalledLocation.GetFolderAsync(“资产”);

对于(inti=1;i在WPF应用程序中,解决方案可以是使用如下队列

public partial class MainWindow : Window
{
    private readonly Queue<string> _audioFilesQueue = new Queue<string>();
    private readonly MediaElement _player;

    public MainWindow()
    {
        InitializeComponent();

        _player = new MediaElement();
        _player.LoadedBehavior = MediaState.Manual;
        _player.UnloadedBehavior = MediaState.Manual;
        _player.MediaEnded += Player_MediaEnded;
    }

    private void Player_MediaEnded(object sender, RoutedEventArgs e)
    {
        OnProcessQueue();
    }

    private void Btn_OnClick(object sender, RoutedEventArgs e)
    {
        PlayCascade(new[]
        {
            "X:\\Library\\Sounds\\Other\\sound1.wav",
            "X:\\Library\\Sounds\\Other\\sound2.wav",
            "X:\\Library\\Sounds\\Other\\sound3.wav"
        });
    }

    private void PlayCascade(string[] sequence)
    {
        foreach (var file in sequence)
        {
            _audioFilesQueue.Enqueue(file);
        }
        OnProcessQueue();
    }

    private void OnProcessQueue()
    {
        Dispatcher.Invoke(() =>
        {
            if (_audioFilesQueue.Any())
            {
                var toPlay = _audioFilesQueue.Dequeue();
                _player.Source = new Uri(toPlay);
                _player.Play();
            }
        });
    }
公共部分类主窗口:窗口
{
私有只读队列_audioFilesQueue=new Queue();
私有只读MediaElement\u播放器;
公共主窗口()
{
初始化组件();
_player=新媒体元素();
_player.LoadedBehavior=MediaState.Manual;
_player.UnloadedBehavior=MediaState.Manual;
_player.MediaEnded+=player_MediaEnded;
}
私有void Player_mediated(对象发送方,路由目标e)
{
OnProcessQueue();
}
私有void Btn_OnClick(对象发送方,路由目标)
{
PlayCascade(新[]
{
“X:\\Library\\Sounds\\Other\\sound1.wav”,
“X:\\Library\\Sounds\\Other\\sound2.wav”,
“X:\\Library\\Sounds\\Other\\sound3.wav”
});
}
私有void播放级联(字符串[]序列)
{
foreach(按顺序排列的var文件)
{
_audiofilesque.Enqueue(文件);
}
OnProcessQueue();
}
私有void OnProcessQueue()
{
Dispatcher.Invoke(()=>
{
if(_audioFilesQueue.Any())
{
var toPlay=_audioFilesQueue.Dequeue();
_player.Source=新Uri(toPlay);
_player.Play();
}
});
}

如果是我,我会将每个wav封装在描述符包装类中,该类保存文件上的数据,例如路径、持续时间等。将包装器放入知道何时出列的特殊队列(您必须记住上次项目出列的时间,并检查持续时间是否已结束)使用MediaElement的CurrentState属性创建一个项目并播放它:如果在多线程环境中调用此方法,该怎么办?您一次只想播放一个媒体。为什么不尝试复制队列是一个很好的方法,但您应该在回答问题时更加强调(代码中真正回答问题的部分是事件回调)。别误会,队列是为此而设计的,但这只是一个质量改进,淹没了本例的真正答案。也许可以添加两个片段:一个只是解释回调如何工作,而这一个是队列。这是非常好的代码,谢谢,但不幸的是VS 2017不包含MediaState。手册,所以我对这些代码进行了注释,并将其删除不工作_player.LoadedBehavior=MediaState.Manual;_player.UnloadedBehavior=MediaState.Manual;有什么建议吗?这不是VS的问题,我想你不是在WPF应用程序上工作,而是在UWP上工作。不过,我的代码指的是WPF桌面应用程序,所以不要介意删除行或适应你的需要。当我添加Presentation时,它正在工作nCore.dll我在dll文件中有另一个奇怪的错误,但至少我得到了代码。非常感谢