Buttons
The first type of interactive component we'll cover creating is a Button. Buttons are available in a variety of styles and can be used to provide permanent interfaces, temporary confirmation workflows, and other forms of additional interaction with your bot.
TIP
This page is a follow-up to the slash commands section and action rows page. Please carefully read those pages first so that you can understand the methods used here.
Building buttons
Buttons are one of the MessageComponent
classes, which can be sent via messages or interaction responses.
For this example, you're going to expand on the ban
command that was previously covered on the parsing options page with a confirmation workflow.
To create your buttons, use the ButtonBuilder
open in new window class, defining at least the customId
, style
and label
.
const { ButtonBuilder, ButtonStyle, SlashCommandBuilder } = require('discord.js');
module.exports = {
// data: new SlashCommandBuilder()...
async execute(interaction) {
const target = interaction.options.getUser('target');
const reason = interaction.options.getString('reason') ?? 'No reason provided';
const confirm = new ButtonBuilder()
.setCustomId('confirm')
.setLabel('Confirm Ban')
.setStyle(ButtonStyle.Danger);
const cancel = new ButtonBuilder()
.setCustomId('cancel')
.setLabel('Cancel')
.setStyle(ButtonStyle.Secondary);
},
};
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
TIP
The custom id is a developer-defined string of up to 100 characters. Use this field to ensure you can uniquely define all incoming interactions from your buttons!
Sending buttons
To send your buttons, create an action row and add the buttons as components. Then, send the row in the components
property of InteractionReplyOptions
open in new window (extends BaseMessageOptions
open in new window).
const { ActionRowBuilder, ButtonBuilder, ButtonStyle, SlashCommandBuilder } = require('discord.js');
module.exports = {
// data: new SlashCommandBuilder()...
async execute(interaction) {
const target = interaction.options.getUser('target');
const reason = interaction.options.getString('reason') ?? 'No reason provided';
const confirm = new ButtonBuilder()
.setCustomId('confirm')
.setLabel('Confirm Ban')
.setStyle(ButtonStyle.Danger);
const cancel = new ButtonBuilder()
.setCustomId('cancel')
.setLabel('Cancel')
.setStyle(ButtonStyle.Secondary);
const row = new ActionRowBuilder()
.addComponents(cancel, confirm);
await interaction.reply({
content: `Are you sure you want to ban ${target} for reason: ${reason}?`,
components: [row],
});
},
};
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
Restart your bot and then send the command to a channel your bot has access to. If all goes well, you should see something like this:
Button styles
You'll notice in the above example that two different styles of buttons have been used, the grey Secondary style and the red Danger style. These were chosen specifically to support good UI/UX principles. In total, there are five button styles that can be used as appropriate to the action of the button:
Primary
style buttons are blue. These are suitable for most general purpose actions, where it's the primary or most significant action expected.Secondary
style buttons are grey. Use these for less important actions like the "Cancel" button in the example above.Success
style buttons are green. Similar to the Primary button, these are a good choice for "positive" confirmation actions.Danger
style buttons are red. Where the action being confirmed is "destructive", such a ban or delete, using a red button helps alert the user to the risk of the action.Link
style buttons are also grey, but are tagged with the "external link" symbol. These buttons will open the provided link in the browser without sending an interaction to the bot.
Link buttons
Link buttons are a little different to the other styles. Link
buttons must have a url
, cannot have a customId
and do not send an interaction event when clicked.
const button = new ButtonBuilder()
.setLabel('discord.js docs')
.setURL('https://discord.js.org')
.setStyle(ButtonStyle.Link);
2
3
4
Disabled buttons
If you want to prevent a button from being used, but not remove it from the message, you can disable it with the ButtonBuilder#setDisabled()
open in new window method:
const button = new ButtonBuilder()
.setCustomId('disabled')
.setLabel('Click me?')
.setStyle(ButtonStyle.Primary)
.setDisabled(true);
2
3
4
5
Emoji buttons
If you want to use a guild emoji within a ButtonBuilder
open in new window, you can use the ButtonBuilder#setEmoji()
open in new window method:
const button = new ButtonBuilder()
.setCustomId('primary')
.setLabel('Primary')
.setStyle(ButtonStyle.Primary)
.setEmoji('123456789012345678');
2
3
4
5
Next steps
That's everything you need to know about building and sending buttons! From here you can learn about the other type of message component, select menus, or have your bot start listening to component interactions from your buttons.