- モジュールのインポート
- コンテキストの作成
- ボタンの追加
- 注意点
- 備考
- 親オブジェクトでのボタン追加・削除・取得
- 備考
- 送信前の準備
- 備考
- 送信
- 編集と削除
- イベント受信から応答まで
- データモデルの仕様
- サンプルコード
from discord_components import InteractionButton, InteractionButtonStyles, InteractionButtonParts
これが親オブジェクトになる。これにボタンを追加していく土台。
InteractionButton(bot: discord.Client|discord.commands.Bot)
context = InteractionButton(bot=ctx)
キーワード引数botにはクライアントを指定。
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
bot | No | Yes | Botクライアント |
original_message | Yes | Yes | 元のメッセージ(ユーザーのものなど) |
InteractionButtonPartsでボタンを作る。
InteractionButtonParts(name: str, label: str, url: str, style: int, disabled: bool)
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
name | 場合による | Yes | ボタンのID。重複しないこと |
label | No | Yes | ボタンに表示させる文字列 |
url | 場合による | Yes | ボタンにリンクさせるURL |
style | Yes | Yes | ボタンのスタイル(備考を参照すること) |
disabled | Yes | Yes | 押せなくするかどうか |
button = InteractionButtonParts(name='sample1', label='ボタンだよ', style=InteractionButtonStyles.primary())
- styleに5 (またはInteractionButtonStyles.url()) を指定した場合、urlパラメータが必須となる。それ以外の場合は、nameが必須となる。
- labelの最大文字数は50
- ボタンのスタイルはいくつかある。
↓表(InteractionButtonStyles.は省略)
種類 | 色の名前 | 別名 | ID |
---|---|---|---|
通常 | blurple | primary | 1 |
サブ | grey | secondary | 2 |
完了 | green | success | 3 |
キャンセル | red | danger | 4 |
URL用 | - | url | 5 |
context.add_button(button) # 追加
context.remove_button(button) # 削除
context.get_button(0) # 1個目のボタン取得
- 追加したボタンは内部プロパティ
buttons
に格納される。 - remove_buttonに指定したボタンがなくてもエラーにはならない。
- 追加できるボタンは5つまで(でもこれ、たぶん間違ってるから後で調べ直す)
context.build(content: str, embed: discord.Embed)
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
content | embed指定なしの場合No | Yes | テキストメッセージ |
embed | content指定なしの場合No | Yes | 表示させたいEmbed |
送信に必要なデータを生成する。
build()を呼び出さないと送信時にエラーになる。
内部プロパティjson
に辞書で保存される。
引数はなくても良い(はず)
- add_buttonまたはremove_buttonした後は必ずbuild()を呼び出すこと。
obj = await context.send(channel: discord.TextChannel)
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
channel | No | Yes | 送信先チャンネル |
このメソッドはコルーチンである。
指定チャンネルに送信する。 channelにはDiscord.pyのTextChannelを渡すこと。
返り値として、RAWなメッセージオブジェクトが返ってくる。(InteractionButtonRemoteObject)
送信したボタンはあとから編集することができる。
await obj.edit(new_context: InteractionButton)
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
new_context | No | No | 置き換える新しいオブジェクト |
削除もできる。
await obj.delete()
送信で得たオブジェクトは、InteractionButtonRemoteObjectがベースで、wait_for_press()
でクリックイベントを受信する状態にできる。
event = await obj.wait_for_press(timeout: float)
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
timeout | Yes | Yes | タイムアウトになるまでの時間(秒) |
※wait_forと同じと考えてよい。
返り値はイベントの内容が格納されたInteractionButtonEventResponseがベースのものが得られる。
タイムアウトを指定していて、かつ時間が過ぎたときは、例外asyncio.TimeoutError
が発生する。
async def callback(ctx, event):
await event.reply(f'{event.name}が押されました')
obj.set_callback(callback)
obj.start_receive()
set_callbackで受け取る関数を指定、start_receive()で開始。
停止する場合はstop_receive()、コールバック関数を外す場合はclear_callback()を呼び出す。
コールバックの関数にはctx
(discord.ext.commands.Context) 、event
(InteractionButtonEventResponse)の順に引数が渡される。
※何らかの理由でctxがNoneになることがある。
obj.set_callback(coro)
引数名 | キーワード引数か | 意味 |
---|---|---|
coro | No | イベントを受信する関数(コルーチン) |
※キーワード引数ではない
コルーチン以外のものを指定した場合はTypeErrorとなる。
イベント受信時はawait coro(data)
の形で内部から呼び出される。
dataの型はInteractionButtonEventResponseである。
task = obj.start_receive(timeout: float)
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
timeout | Yes | Yes | タイムアウトになるまでの時間(秒) |
※キーワード引数
返り値の型はasyncio.Taskである。
返り値として得られたものを使って、応答メッセージを送信できる。
await event.reply(text: str)
引数名 | 省略可能 | キーワード引数か | 意味 |
---|---|---|---|
text | No | No | テキストメッセージ |
embed | Yes | Yes | 埋め込み |
hidden | Yes | Yes | メッセージ送信者にのみ表示するか |
embedにはdiscord.Embedを指定できる。
hiddenはbool。
ack()で、メッセージの送信はしないが、受信したということだけ通知できる。
await event.ack()
属性名 | 型 | 内容 |
---|---|---|
bot | Client系 | クライアント |
embed | discord.Embed | 埋め込み |
original_message | discord.Message | 元のメッセージ(ユーザーのものなど) |
json | dict | 送信用内部辞書 |
buttons | list | ボタンの格納先 |
メソッド名 | 内容 |
---|---|
add_button | ボタン追加 |
add_buttons | 複数ボタン追加 |
remove_button | ボタン削除 |
get_button | ボタン取得 |
build | データ生成 |
await send | 送信 |
bot、jsonを直接編集することは望ましくない。
属性名 | 型 | 内容 |
---|---|---|
name | str | ボタンのID |
type | int | Component Type |
label | str | ボタンに表示させる文字列 |
style | int | ボタンのスタイル |
url | str | ボタンに結びつけるURL |
disabled | bool | 無効にするかどうか |
メソッド名 | 内容 |
---|---|
to_dict | JSON変換用 |
typeは常に2で固定。
属性名 | 型 | 内容 |
---|---|---|
bot | Client系 | クライアント |
payload | dict | RAWメッセージオブジェクト |
id | int | メッセージID |
channel_id | int | チャンネルID |
message | discord.Message | メッセージオブジェクト |
original_message | discord.Message | 元のメッセージ(ユーザーのものなど) |
guild_id | int | サーバーID |
timeout | int | タイムアウトまでの秒数 |
メソッド名 | 内容 |
---|---|
await delete | メッセージ削除 |
await edit | メッセージ編集 |
set_callback | コールバック設定 |
clear_callback | コールバック解除 |
start_receive | イベント受信開始 |
stop_receive | イベント受信停止 |
await wait_for_press | イベント受信待受 |
bot, payload, id, channel_id, message, guild_idを直接編集することは望ましくない。
属性名 | 型 | 内容 |
---|---|---|
bot | Client系 | クライアント |
data | dict | イベントデータ |
REPLY_TOKEN | str | コールバック用ワンタイムトークン |
name | str | ボタンのID |
message | discord.Message | ボタンが置かれているメッセージオブジェクト |
original_message | discord.Message | 元のメッセージ(ユーザーのものなど) |
ctx | Context | コンテキストオブジェクト(クライアントにdiscord.Clientを使用時は常にNone) |
メソッド名 | 内容 |
---|---|
await reply | メッセージ返信 |
await ack | 受信確認通知 |
await custom_response | 手動でレスポンス送信 |
bot, data, REPLY_TOKEN, name, messageを直接編集することは望ましくない。
クライアントの変数名はbot
、チャンネルオブジェクトが入った変数をchannel
としている。
from discord_components import InteractionButton, InteractionButtonParts
context = InteractionButton(bot=bot)
button = InteractionButtonParts(name='sample1', label='ボタンだよ')
context.add_button(button)
context.build(content='↓ただのボタン')
await context.send(channel=channel)
from discord_components import InteractionButton, InteractionButtonStyles, InteractionButtonParts
context = InteractionButton(bot=bot)
button = InteractionButtonParts(name='sample2', label='操作を取り消す', style=InteractionButtonStyles.red())
context.add_button(button)
context.build(content='↓ただのボタン')
await context.send(channel=channel)
from discord_components import InteractionButton, InteractionButtonStyles, InteractionButtonParts
context = InteractionButton(bot=bot)
button = InteractionButtonParts(name='sample2', label='再生', emoji=u'\U000025b6\U0000fe0f')
context.add_button(button)
context.build(content='再生パネル')
await context.send(channel=channel)
from discord_components import InteractionButton, InteractionButtonStyles, InteractionButtonParts
context = InteractionButton(bot=bot)
button = InteractionButtonParts(name='sample3', label='検索結果を表示', url='https://www.google.com/', style=InteractionButtonStyles.url())
context.add_button(button)
context.build(content='Googleで調べる:')
await context.send(channel=channel)
from discord_components import InteractionButton, InteractionButtonStyles, InteractionButtonParts
context = InteractionButton(bot=bot)
button = InteractionButtonParts(name='sample4', label='ここをクリック')
context.add_button(button)
context.build(content='押してね↓')
obj = await context.send(channel=channel)
resp = await obj.wait_for_press(timeout=10.0)
await resp.reply('押されました')
from discord_components import InteractionButton, InteractionButtonStyles, InteractionButtonParts
async def reaction(ev):
if ev.name == 'sleep':
await ev.reply('(つ∀-)オヤスミー')
elif ev.name == 'cancel':
await ev.reply('発狂(は')
elif ev.name == 'noact':
await ev.ack()
context = InteractionButton(bot=bot)
button1 = InteractionButtonParts(name='sleep', label='寝る', style=InteractionButtonStyles.primary())
button2 = InteractionButtonParts(name='cancel', label='夜ふかしする', style=InteractionButtonStyles.grey())
button3 = InteractionButtonParts(name='noact', label='なにもしない', style=InteractionButtonStyles.grey())
context.add_buttons([button1, button2, button3])
em = discord.Embed(title='寝る')
em.description = '寝ることができます'
context.build(embed=em)
obj = await context.send(channel=channel)
obj.set_callback(reaction)
t = obj.start_receive()