Hiding an ephemeral view after user action? #8454
-
Hello, I'm migrating to Discord.py 2.0 app commands and UI views. See the following sample cog: import discord
from discord import app_commands
from discord.ext import commands
RED_IDENTIFIER = "COLOUR_BLOOD"
BLUE_IDENTIFIER = "COLOUR_SKY"
MAGENTA_IDENTIFIER = "COLOUR_TMOBILE_US"
class ColourDropdown(discord.ui.Select):
def __init__(self):
options = (
discord.SelectOption(
label="Red",
value=RED_IDENTIFIER,
description="Your favourite colour is red",
),
discord.SelectOption(
label="Blue",
value=BLUE_IDENTIFIER,
description="Your favourite colour is blue",
),
discord.SelectOption(
label="Magenta",
value=MAGENTA_IDENTIFIER,
description="Your favourite colour is magenta",
),
)
super().__init__(
placeholder="Choose a colour...",
min_values=1,
max_values=1,
options=options,
)
async def callback(self, interaction):
await interaction.response.defer(thinking=False)
self.view.colour = self.values[0]
if self.view:
self.view.stop()
class ColourAdvancedModal(discord.ui.Modal, title="Advanced options"):
def __init__(self, view):
self.view = view
super().__init__()
colour = discord.ui.TextInput(
label="Custom colour",
placeholder="Enter the identifier of a really exotic colour...",
required=True,
)
async def on_submit(self, interaction: discord.Interaction):
await interaction.response.defer(thinking=False)
self.view.colour = self.colour.value.strip()
if self.view:
self.view.stop()
class ColourView(discord.ui.View):
def __init__(self):
self.colour = None
super().__init__()
self.add_item(ColourDropdown())
@discord.ui.button(label="Advanced...", style=discord.ButtonStyle.red, row=1)
async def advanced(
self, interaction: discord.Interaction, button: discord.ui.Button
):
adv = ColourAdvancedModal(self)
await interaction.response.send_modal(adv)
class Colours(commands.Cog):
@app_commands.command()
async def colourpicker(self, interaction):
"Pick your favourite colour."
view = ColourView()
await interaction.response.send_message(
"Pick your favourite colour in the dropdown below:",
view=view,
ephemeral=True,
)
await view.wait()
# TODO: Here I'd like to get rid of the view.
# The user has made their choice, so the view shouldn't be visible any more.
# For debugging, just send the raw value as a follow-up.
await interaction.followup.send(
f"Got colour identifier {repr(view.colour)}", ephemeral=True
) Once the user chooses a colour in the dropdown, I'd like the view to disappear. How can I accomplish this? Calling Thanks in advance! |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment
-
I don't think deleting an ephemeral response is supported in general, however you can edit them to remove the view and edit the content which might work for you. You can either simply call |
Beta Was this translation helpful? Give feedback.
I don't think deleting an ephemeral response is supported in general, however you can edit them to remove the view and edit the content which might work for you.
You can either simply call
interaction.edit_original_response
at the point in the code where your TODO is and passview=None
, or you can replace theinteraction.response.defer
calls withinteraction.response.edit_message
instead. The latter might be advantageous since it counts as a response to the interaction (the user won't see the "Application did not respond" message), but you don't need to defer and only edit the ephemeral message later.