tl;dr 版本:如何在 WinForms 按钮的 MouseDown 事件中开始播放声音并停止在同一个按钮的 MouseUp 事件中播放声音?
中级 C# 开发人员在这里,我一直在尝试编写一个简单的Simon克隆。
我目前正试图让它仅在用户单击按钮时播放彩色按钮的声音。(我交替使用“按钮”和“平铺”。两者都指用户将在表单上按下的彩色按钮)
我最初尝试过这个:
public partial class frmMain : Form
{
private SoundPlayer soundPlayer;
private void btnGreenTile_MouseDown(object sender, MouseEventArgs e)
{
soundPlayer = new SoundPlayer(Properties.Resources.greenTileSound)
soundPlayer.Play();
}
private void btnGreenTile_MouseUp(object sender, MouseEventArgs e)
{
soundPlayer.Stop();
}
}
但这并没有停止声音,因为 MouseUp 事件没有触发,因为 MouseDown 没有完成(仍然播放大约 5 秒长的声音,以防有人按住按钮的时间超过了简单的点击)。正如 Luis Tellez 在评论中提到的那样,SoundPlayer 会在一个新线程上播放声音......所以我不知道为什么这段代码现在不起作用。
所以我研究了多线程并尝试了这个:
public partial class frmMain : Form
{
private Thread soundThread = new Thread(new ParameterizedThreadStart(PlaySound));
// Create stream objects for each sound (needed to allow SoundPlayer to use Resources)
private Stream greenTileSound = Properties.Resources.greenTilePress;
private Stream redTileSound = Properties.Resources.redTilePress;
private Stream yellowTileSound = Properties.Resources.yellowTilePress;
private Stream blueTileSound = Properties.Resources.blueTilePress;
public frmMain()
{
InitializeComponent();
}
private void btnGreenTile_MouseDown(object sender, MouseEventArgs e)
{
soundThread.Start(greenTileSound);
}
private void btnGreenTile_MouseUp(object sender, MouseEventArgs e)
{
soundThread.Abort();
}
// Have to use object as parameter because ParamterizedThreadStart() only takes object arguments
private static void PlaySound(object soundToPlay)
{
SoundPlayer soundPlayer = new SoundPlayer((Stream)soundToPlay);
soundPlayer.Play();
}
}
使用上面的代码,它不会停止在 MouseUp 上播放声音,甚至更好的是它会抛出一个带有消息“线程正在运行或终止;它无法重新启动”的 ThreadStateException。
正如您可能知道的那样,我只是在尝试编写此代码时才了解多线程。我必须使用 ParameterizedThreadStart,因为它在线程启动时调用的方法 PlaySound() 需要将参数传递给 soundPlayer,其资源对应于播放器按下的彩色按钮(.wav 文件)。
然后我想也许我应该尝试使用 soundThread.Suspend() 而不是 soundThread.Abort()但 Suspend 已被弃用...
谁能指出我正确的方向以使声音在 MouseUp 上停止?我需要使用多线程吗?我认为我的问题归结为逻辑,但我完全陷入困境。感谢您的任何帮助!:)
作为旁注,我有点惊讶这个问题或类似的问题还没有被问到(至少我无法通过谷歌搜索或 stackExchange 搜索找到它)。