Source code for bacommon.bs._clienteffect

# Released under the MIT License. See LICENSE for details.
#
"""ClientEffect related functionality."""

from __future__ import annotations

import datetime
from enum import Enum
from dataclasses import dataclass, field
from typing import Annotated, override, assert_never

from efro.dataclassio import ioprepped, IOAttrs, IOMultiType


[docs] class ClientEffectTypeID(Enum): """Type ID for each of our subclasses.""" UNKNOWN = 'u' SCREEN_MESSAGE = 'm' SOUND = 's' DELAY = 'd' CHEST_WAIT_TIME_ANIMATION = 't' TICKETS_ANIMATION = 'ta' TOKENS_ANIMATION = 'toa'
[docs] class ClientEffect(IOMultiType[ClientEffectTypeID]): """Something that can happen on the client. This can include screen messages, sounds, visual effects, etc. """
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: # Require child classes to supply this themselves. If we did a # full type registry/lookup here it would require us to import # everything and would prevent lazy loading. raise NotImplementedError()
[docs] @override @classmethod def get_type(cls, type_id: ClientEffectTypeID) -> type[ClientEffect]: """Return the subclass for each of our type-ids.""" # pylint: disable=cyclic-import # pylint: disable=too-many-return-statements t = ClientEffectTypeID if type_id is t.UNKNOWN: return ClientEffectUnknown if type_id is t.SCREEN_MESSAGE: return ClientEffectScreenMessage if type_id is t.SOUND: return ClientEffectSound if type_id is t.DELAY: return ClientEffectDelay if type_id is t.CHEST_WAIT_TIME_ANIMATION: return ClientEffectChestWaitTimeAnimation if type_id is t.TICKETS_ANIMATION: return ClientEffectTicketsAnimation if type_id is t.TOKENS_ANIMATION: return ClientEffectTokensAnimation # Important to make sure we provide all types. assert_never(type_id)
[docs] @override @classmethod def get_unknown_type_fallback(cls) -> ClientEffect: # If we encounter some future message type we don't know # anything about, drop in a placeholder. return ClientEffectUnknown()
[docs] @ioprepped @dataclass class ClientEffectUnknown(ClientEffect): """Fallback substitute for types we don't recognize."""
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: return ClientEffectTypeID.UNKNOWN
[docs] @ioprepped @dataclass class ClientEffectScreenMessage(ClientEffect): """Display a screen-message.""" message: str subs: list[str] = field(default_factory=list) color: tuple[float, float, float] = (1.0, 1.0, 1.0)
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: return ClientEffectTypeID.SCREEN_MESSAGE
[docs] @ioprepped @dataclass class ClientEffectSound(ClientEffect): """Play a sound."""
[docs] class Sound(Enum): """Sounds that can be made alongside the message.""" UNKNOWN = 'u' CASH_REGISTER = 'c' ERROR = 'e' POWER_DOWN = 'p' GUN_COCKING = 'g'
sound: Sound volume: float = 1.0
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: return ClientEffectTypeID.SOUND
[docs] @ioprepped @dataclass class ClientEffectChestWaitTimeAnimation(ClientEffect): """Animate chest wait time changing.""" chestid: str duration: float startvalue: datetime.datetime endvalue: datetime.datetime
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: return ClientEffectTypeID.CHEST_WAIT_TIME_ANIMATION
[docs] @ioprepped @dataclass class ClientEffectTicketsAnimation(ClientEffect): """Animate tickets count.""" duration: float startvalue: int endvalue: int
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: return ClientEffectTypeID.TICKETS_ANIMATION
[docs] @ioprepped @dataclass class ClientEffectTokensAnimation(ClientEffect): """Animate tokens count.""" duration: float startvalue: int endvalue: int
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: return ClientEffectTypeID.TOKENS_ANIMATION
[docs] @ioprepped @dataclass class ClientEffectDelay(ClientEffect): """Delay effect processing.""" seconds: float
[docs] @override @classmethod def get_type_id(cls) -> ClientEffectTypeID: return ClientEffectTypeID.DELAY
# Docs-generation hack; import some stuff that we likely only forward-declared # in our actual source code so that docs tools can find it. from typing import (Coroutine, Any, Literal, Callable, Generator, Awaitable, Sequence, Self) import asyncio from concurrent.futures import Future from pathlib import Path from enum import Enum