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

如何在按下H键后立即终止winsound播放任务?

问题解决:按下H键立即停止闹钟音效

问题原因

你的代码里winsound.PlaySound()默认是阻塞调用,一旦开始播放就会直到音效结束才返回,所以即使按下H键修改了alarm_flag,当前的播放也会继续完成才会退出循环。另外,keyboard.is_pressed的循环检测效率很低,还会占用不必要的CPU资源。

解决方案

  1. 给PlaySound添加winsound.SND_ASYNC参数,让音效异步播放,调用后立即返回,这样可以随时中断播放。
  2. 按下H键时,不仅设置alarm_flag,还要调用winsound.PlaySound(None, winsound.SND_PURGE)直接终止当前播放。
  3. 用keyboard.add_hotkey替代循环检测按键,更高效且代码更简洁。
  4. 设置线程为守护线程,确保主程序退出时所有线程自动结束。

修改后的代码

import winsound
from threading import Thread
import keyboard
import sys

alarm_flag = True

def alarm():
    global alarm_flag
    while alarm_flag:
        # 异步播放音效,调用后立即返回
        winsound.PlaySound("C:\\windows\\media\\Alarm01.wav", winsound.SND_FILENAME | winsound.SND_ASYNC)

def stop_alarm():
    global alarm_flag
    def on_h_press():
        nonlocal alarm_flag
        alarm_flag = False
        # 立即停止当前播放的音效
        winsound.PlaySound(None, winsound.SND_PURGE)
        # 退出整个程序
        sys.exit()
    # 注册H键的热键回调
    keyboard.add_hotkey('h', on_h_press)
    # 保持线程运行,监听按键
    keyboard.wait()

# 设置守护线程,主程序退出时线程自动结束
alarm_thread = Thread(target=alarm, daemon=True)
stop_alarm_thread = Thread(target=stop_alarm, daemon=True)

alarm_thread.start()
stop_alarm_thread.start()

# 让主程序等待,否则会直接退出
stop_alarm_thread.join()

关键说明

  • winsound.SND_ASYNC:让播放操作在后台进行,函数调用后立即返回,不会阻塞线程。
  • winsound.SND_PURGE:用于清除当前正在播放的音效,实现立即停止的效果。
  • keyboard.add_hotkey:相比循环检测,这种方式更高效,只有当按键按下时才会触发回调。
  • 守护线程:设置daemon=True,确保主程序退出时,所有子线程也会自动终止,避免残留进程。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.05 00:35:08