【Discord.js】メンバーの音声チャンネルの入退出を検知する
5/6追記:立ち上げていきなり音声チャンネルに入った場合streaming以外はnull streamingはfalseになるため注意が必要です。
めっちゃ悩んだ結果、無理やり解決させたのでメモ。
表題の件、ググるとvoiceStateUpdateイベントで監視するもろもろがでてくるのですが、
入退出だけでなく、ミュート等音声まわりをいじるだけで検知してしまうので悩んでおりました。(v11より前の書き方だと検知できたようですが…。)
IDつきの入退出のブール値や、メンバーの接続状態などとくにオブジェクト内に表記がないため簡単には出せないという罠。
▼同じように悩んでいた人々
node.js - discord.js event voiceStateUpdate - Stack Overflow
bots - problem with voiceStateUpdate in JavaScript - Stack Overflow
bots - Discord.js join/leave voice channel notification in text channel - Stack Overflow
▼解決法
ミュートや音声まわりで反応しちゃうなら、条件からひけばいいじゃん、ということで
無理やり条件から引いて解決しました。
いまのところ以下条件に反応するようです(oldState/newStateの中身の最後のパート)
5/6追記:立ち上げていきなり音声チャンネルに入った場合streaming以外はnull streamingはfalseになるため注意が必要です。
プロパティ oldState/newState
serverDeaf null false
serverMute null false
selfDeaf null false
selfMute null true
selfVideo null false
streaming false false
client.on("voiceStateUpdate", function(oldState, newState) { // ミュートでも反応してしまうので無視用 const statusChk = oldState.serverDeaf === newState.serverDeaf && oldState.serverMute === newState.serverMute && oldState.selfDeaf === newState.selfDeaf && oldState.selfMute === newState.selfMute && oldState.selfVideo === newState.selfVideo && oldState.streaming === newState.streaming; if((statusChk == true || oldState.serverDeaf == null) && newState.channel){ //チャンネルに入ってきたときの処理 } } else if (statusChk && oldState.channel) { // チャンネルから出たときの処理 } });
あー今思えばoldState/newStateとでトリガー引いた人のチャンネルの人数の変化をみるのでもよかったのかもしれない。
teratail.com
おわり。