Implement StageInstance
This commit is contained in:
@@ -30,11 +30,12 @@ from typing import Callable, Dict, List, Optional, TYPE_CHECKING, Union, overloa
|
||||
|
||||
import discord.abc
|
||||
from .permissions import PermissionOverwrite, Permissions
|
||||
from .enums import ChannelType, try_enum, VoiceRegion, VideoQualityMode
|
||||
from .enums import ChannelType, StagePrivacyLevel, try_enum, VoiceRegion, VideoQualityMode
|
||||
from .mixins import Hashable
|
||||
from . import utils
|
||||
from .asset import Asset
|
||||
from .errors import ClientException, NoMoreItems, InvalidArgument
|
||||
from .stage_instance import StageInstance
|
||||
|
||||
__all__ = (
|
||||
'TextChannel',
|
||||
@@ -49,7 +50,7 @@ __all__ = (
|
||||
|
||||
if TYPE_CHECKING:
|
||||
from .role import Role
|
||||
from .member import Member
|
||||
from .member import Member, VoiceState
|
||||
from .abc import Snowflake
|
||||
from .message import Message
|
||||
from .webhook import Webhook
|
||||
@@ -611,7 +612,7 @@ class VocalGuildChannel(discord.abc.Connectable, discord.abc.GuildChannel, Hasha
|
||||
return ChannelType.voice.value
|
||||
|
||||
@property
|
||||
def members(self):
|
||||
def members(self) -> List[Member]:
|
||||
"""List[:class:`Member`]: Returns all members that are currently inside this voice channel."""
|
||||
ret = []
|
||||
for user_id, state in self.guild._voice_states.items():
|
||||
@@ -622,7 +623,7 @@ class VocalGuildChannel(discord.abc.Connectable, discord.abc.GuildChannel, Hasha
|
||||
return ret
|
||||
|
||||
@property
|
||||
def voice_states(self):
|
||||
def voice_states(self) -> Dict[int, VoiceState]:
|
||||
"""Returns a mapping of member IDs who have voice states in this channel.
|
||||
|
||||
.. versionadded:: 1.3
|
||||
@@ -640,7 +641,7 @@ class VocalGuildChannel(discord.abc.Connectable, discord.abc.GuildChannel, Hasha
|
||||
return {key: value for key, value in self.guild._voice_states.items() if value.channel.id == self.id}
|
||||
|
||||
@utils.copy_doc(discord.abc.GuildChannel.permissions_for)
|
||||
def permissions_for(self, member):
|
||||
def permissions_for(self, member: Union[Role, Member], /) -> Permissions:
|
||||
base = super().permissions_for(member)
|
||||
|
||||
# voice channels cannot be edited by people who can't connect to them
|
||||
@@ -875,10 +876,35 @@ class StageChannel(VocalGuildChannel):
|
||||
self.topic = data.get('topic')
|
||||
|
||||
@property
|
||||
def requesting_to_speak(self):
|
||||
def requesting_to_speak(self) -> List[Member]:
|
||||
"""List[:class:`Member`]: A list of members who are requesting to speak in the stage channel."""
|
||||
return [member for member in self.members if member.voice.requested_to_speak_at is not None]
|
||||
|
||||
@property
|
||||
def speakers(self) -> List[Member]:
|
||||
"""List[:class:`Member`]: A list of members who have been permitted to speak in the stage channel.
|
||||
|
||||
.. versionadded:: 2.0
|
||||
"""
|
||||
return [member for member in self.members if not member.voice.suppress and member.voice.requested_to_speak_at is None]
|
||||
|
||||
@property
|
||||
def listeners(self) -> List[Member]:
|
||||
"""List[:class:`Member`]: A list of members who are listening in the stage channel.
|
||||
|
||||
.. versionadded:: 2.0
|
||||
"""
|
||||
return [member for member in self.members if member.voice.suppress]
|
||||
|
||||
@property
|
||||
def moderators(self) -> List[Member]:
|
||||
"""List[:class:`Member`]: A list of members who are moderating the stage channel.
|
||||
|
||||
.. versionadded:: 2.0
|
||||
"""
|
||||
required_permissions = Permissions.stage_moderator()
|
||||
return [member for member in self.members if self.permissions_for(member) >= required_permissions]
|
||||
|
||||
@property
|
||||
def type(self):
|
||||
""":class:`ChannelType`: The channel's Discord type."""
|
||||
@@ -886,9 +912,83 @@ class StageChannel(VocalGuildChannel):
|
||||
|
||||
@utils.copy_doc(discord.abc.GuildChannel.clone)
|
||||
async def clone(self, *, name: str = None, reason: Optional[str] = None) -> StageChannel:
|
||||
return await self._clone_impl({
|
||||
'topic': self.topic,
|
||||
}, name=name, reason=reason)
|
||||
return await self._clone_impl({}, name=name, reason=reason)
|
||||
|
||||
@property
|
||||
def instance(self) -> Optional[StageInstance]:
|
||||
"""Optional[:class:`StageInstance`]: The running stage instance of the stage channel.
|
||||
|
||||
.. versionadded:: 2.0
|
||||
"""
|
||||
return utils.get(self.guild.stage_instances, channel_id=self.id)
|
||||
|
||||
async def create_instance(self, *, topic: str, privacy_level: StagePrivacyLevel = utils.MISSING) -> StageInstance:
|
||||
"""|coro|
|
||||
|
||||
Create a stage instance.
|
||||
|
||||
You must have the :attr:`~Permissions.manage_channels` permission to
|
||||
use this.
|
||||
|
||||
.. versionadded:: 2.0
|
||||
|
||||
Parameters
|
||||
-----------
|
||||
topic: :class:`str`
|
||||
The stage instance's topic.
|
||||
privacy_level: :class:`StagePrivacyLevel`
|
||||
The stage instance's privacy level. Defaults to :attr:`PrivacyLevel.guild_only`.
|
||||
|
||||
Raises
|
||||
------
|
||||
InvalidArgument
|
||||
If the ``privacy_level`` parameter is not the proper type.
|
||||
Forbidden
|
||||
You do not have permissions to create a stage instance.
|
||||
HTTPException
|
||||
Creating a stage instance failed.
|
||||
|
||||
Returns
|
||||
--------
|
||||
:class:`StageInstance`
|
||||
The newly created stage instance.
|
||||
"""
|
||||
|
||||
payload = {
|
||||
'channel_id': self.id,
|
||||
'topic': topic
|
||||
}
|
||||
|
||||
if privacy_level is not utils.MISSING:
|
||||
if not isinstance(privacy_level, StagePrivacyLevel):
|
||||
raise InvalidArgument('privacy_level field must be of type PrivacyLevel')
|
||||
|
||||
payload['privacy_level'] = privacy_level.value
|
||||
|
||||
data = await self._state.http.create_stage_instance(**payload)
|
||||
return StageInstance(guild=self.guild, state=self._state, data=data)
|
||||
|
||||
async def fetch_instance(self) -> StageInstance:
|
||||
"""|coro|
|
||||
|
||||
Gets the running :class:`StageInstance`.
|
||||
|
||||
.. versionadded:: 2.0
|
||||
|
||||
Raises
|
||||
-------
|
||||
:exc:`.NotFound`
|
||||
The stage instance or channel could not be found.
|
||||
:exc:`.HTTPException`
|
||||
Getting the stage instance failed.
|
||||
|
||||
Returns
|
||||
--------
|
||||
:class:`StageInstance`
|
||||
The stage instance.
|
||||
"""
|
||||
data = await self._state.http.get_stage_instance(self.id)
|
||||
return StageInstance(guild=self.guild, state=self._state, data=data)
|
||||
|
||||
@overload
|
||||
async def edit(
|
||||
@@ -918,12 +1018,13 @@ class StageChannel(VocalGuildChannel):
|
||||
You must have the :attr:`~Permissions.manage_channels` permission to
|
||||
use this.
|
||||
|
||||
.. versionchanged:: 2.0
|
||||
The ``topic`` parameter must now be set via :attr:`create_instance`.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
name: :class:`str`
|
||||
The new channel's name.
|
||||
topic: Optional[:class:`str`]
|
||||
The new channel's topic.
|
||||
position: :class:`int`
|
||||
The new channel's position.
|
||||
sync_permissions: :class:`bool`
|
||||
|
||||
Reference in New Issue
Block a user