为何Discord.js中AudioPlayer初始化时不触发Idle事件,仅在音频资源播放完毕后触发?
Great question—this is a common gotcha with event-driven state systems like Discord.js's AudioPlayer. Let's break down what's happening and how to fix it.
The Core Issue
Your code uses client.player.once(AudioPlayerStatus.Idle, ...) which listens for state transitions to Idle, not for the player being in the Idle state.
When you first initialize an AudioPlayer, it does start in the Idle state—but since there's no prior state to transition from, the Idle event isn't emitted. The event only fires when the player switches from another status (like Playing or Paused) to Idle.
How to Fix It
You have two straightforward options to handle the initial Idle state:
1. Extract the Logic to a Reusable Function
Wrap your idle-handling code in a named function, then both attach it to the event and run it manually if the player starts in Idle:
// Extract your idle logic into a reusable function const handlePlayerIdle = () => { console.log(client.playlist); next.run(message, args, client); client.playlist.shift(); }; // Listen for future transitions to Idle client.player.once(AudioPlayerStatus.Idle, handlePlayerIdle); // Check initial state and run immediately if already Idle if (client.player.state.status === AudioPlayerStatus.Idle) { handlePlayerIdle(); }
2. Trigger the Event Manually (Alternative)
If you prefer not to duplicate logic, you can manually emit the Idle event after initializing the player:
client.player.once(AudioPlayerStatus.Idle, () => { console.log(client.playlist); next.run(message, args, client); client.playlist.shift(); }); // Manually emit the event if starting in Idle if (client.player.state.status === AudioPlayerStatus.Idle) { client.player.emit(AudioPlayerStatus.Idle); }
Key Takeaway
Event listeners for statuses in Discord.js's audio system react to changes in state, not the state itself. Always check the initial state explicitly if you need to handle a status that the player starts in.
内容的提问来源于stack exchange,提问作者Suspense

