from typing import ClassVar, Self

from . import Color, Translator
from .termco import AnsiColor, Colorant, EightBitColor, EmbeddedRgb, GrayGradient, Rgb


class Attribute:
    """A text formatting attribute."""
    Bold: ClassVar[Attribute] = ...
    Thin: ClassVar[Attribute] = ...
    Italic: ClassVar[Attribute] = ...
    Underlined: ClassVar[Attribute] = ...
    Blinking: ClassVar[Attribute] = ...
    Reversed: ClassVar[Attribute] = ...
    Hidden: ClassVar[Attribute] = ...
    Stricken: ClassVar[Attribute] = ...

    def enable_sgr(self) -> int: ...
    def disable_sgr(self) -> int: ...
    def __add__(self, other: Self) -> FormatUpdate: ...
    def __sub__(self, other: Self) -> FormatUpdate: ...
    def __neg__(self) -> FormatUpdate: ...
    def __repr__(self) -> str: ...


class Format:
    """A text format comprising zero or more attributes."""
    @staticmethod
    def of(formatting: Attribute | Format) -> Format: ...

    def __new__(cls) -> Self: ...
    def is_empty(self) -> bool: ...
    def len(self) -> int: ...
    def __len__(self) -> int: ...
    def attributes(self) -> AttributeIter: ...
    def __add__(self, other: Attribute | Self) -> FormatUpdate: ...
    def __sub__(self, other: Attribute | Self) -> FormatUpdate: ...
    def __neg__(self) -> FormatUpdate: ...
    def __repr__(self) -> str: ...


class AttributeIter:
    """An iterator over format attributes."""
    def __len__(self) -> int: ...
    def __iter__(self) -> Self: ...
    def __next__(self) -> Attribute: ...


class FormatUpdate:
    """
    A text format update comprising a format to disable and a format to enable.
    """
    @staticmethod
    def of(formatting: Attribute | Format | FormatUpdate) -> FormatUpdate: ...

    def __new__(cls) -> Self: ...
    def is_empty(self) -> bool: ...
    def disable(self) -> Format: ...
    def enable(self) -> Format: ...
    def cap(self, fidelity: Fidelity) -> Self: ...
    def __add__(self, other: Attribute | Self) -> FormatUpdate: ...
    def __sub__(self, other: Attribute | Self) -> FormatUpdate: ...
    def __neg__(self) -> FormatUpdate: ...
    def __repr__(self) -> str: ...


class Fidelity:
    """
    Levels of support for ANSI escape codes and colors.
    """
    Plain: ClassVar[Fidelity] = ...
    NoColor: ClassVar[Fidelity] = ...
    Ansi: ClassVar[Fidelity] = ...
    EightBit: ClassVar[Fidelity] = ...
    TwentyFourBit: ClassVar[Fidelity] = ...
    HiRes: ClassVar[Fidelity] = ...

    @staticmethod
    def from_color(
        color: (
            int | AnsiColor | EmbeddedRgb | GrayGradient | EightBitColor | Rgb
            | Color | Colorant
        )
    ) -> Fidelity: ...
    @staticmethod
    def from_environment(has_tty: bool) -> Fidelity: ...

    def __hash__(self) -> int: ...
    def __eq__(self, other: object) -> bool: ...
    def __ne__(self, other: object) -> bool: ...
    def __gt__(self, other: object) -> bool: ...
    def __ge__(self, other: object) -> bool: ...
    def __lt__(self, other: object) -> bool: ...
    def __le__(self, other: object) -> bool: ...
    def __repr__(self) -> str: ...


class Layer:
    """The render layer."""
    Foreground: ClassVar[Layer] = ...
    Background: ClassVar[Layer] = ...

    def is_foreground(self) -> bool: ...
    def is_background(self) -> bool: ...
    def offset(self) -> int: ...
    def __hash__(self) -> int: ...
    def __eq__(self, other: object) -> bool: ...
    def __ne__(self, other: object) -> bool: ...
    def __repr__(self) -> str: ...


class Style:
    """A style."""
    # Methods to configure styles
    def __new__(cls) -> Self: ...
    def bold(self) -> Self: ...
    def thin(self) -> Self: ...
    def italic(self) -> Self: ...
    def underlined(self) -> Self: ...
    def blinking(self) -> Self: ...
    def reversed(self) -> Self: ...
    def hidden(self) -> Self: ...
    def stricken(self) -> Self: ...
    def with_foreground(
        self,
        color: (
            int | AnsiColor | EmbeddedRgb | GrayGradient | EightBitColor | Rgb
            | Color | Colorant
        ),
    ) -> Self: ...
    def with_background(
        self,
        color: (
            int | AnsiColor | EmbeddedRgb | GrayGradient | EightBitColor | Rgb
            | Color | Colorant
        ),
    ) -> Self: ...

    # Method to inspect styles
    def is_default(self) -> bool: ...
    def format(self) -> Format: ...
    def foreground(self) -> None | Colorant: ...
    def background(self) -> None | Colorant: ...
    def fidelity(self) -> Fidelity: ...
    def cap(self, fidelity: Fidelity, translator: Translator) -> Self: ...
    def __hash__(self) -> int: ...
    def __eq__(self, other: object) -> bool: ...
    def __ne__(self, other: object) -> bool: ...
    def __neg__(self) -> Self: ...
    def __repr__(self) -> str: ...
    def __str__(self) -> str: ...
