Module textual.css.scalar

Expand source code
from __future__ import annotations

from enum import Enum, unique
from fractions import Fraction
from functools import lru_cache
import re
from typing import Iterable, NamedTuple

import rich.repr

from ..geometry import Offset, Size, clamp


class ScalarError(Exception):
    pass


class ScalarResolveError(ScalarError):
    pass


class ScalarParseError(ScalarError):
    pass


@unique
class Unit(Enum):
    """Enumeration of the various units inherited from CSS."""

    CELLS = 1
    FRACTION = 2
    PERCENT = 3
    WIDTH = 4
    HEIGHT = 5
    VIEW_WIDTH = 6
    VIEW_HEIGHT = 7
    AUTO = 8


UNIT_EXCLUDES_BORDER = {Unit.CELLS, Unit.FRACTION, Unit.VIEW_WIDTH, Unit.VIEW_HEIGHT}

UNIT_SYMBOL = {
    Unit.CELLS: "",
    Unit.FRACTION: "fr",
    Unit.PERCENT: "%",
    Unit.WIDTH: "w",
    Unit.HEIGHT: "h",
    Unit.VIEW_WIDTH: "vw",
    Unit.VIEW_HEIGHT: "vh",
}

SYMBOL_UNIT = {v: k for k, v in UNIT_SYMBOL.items()}

_MATCH_SCALAR = re.compile(r"^(-?\d+\.?\d*)(fr|%|w|h|vw|vh)?$").match


def _resolve_cells(
    value: float, size: Size, viewport: Size, fraction_unit: Fraction
) -> Fraction:
    """Resolves explicit cell size, i.e. width: 10

    Args:
        value (float): Scalar value.
        size (Size): Size of widget.
        viewport (Size): Size of viewport.
        fraction_unit (Fraction): Size of fraction, i.e. size of 1fr as a Fraction.

    Returns:
        Fraction: Resolved unit.
    """
    return Fraction(value)


def _resolve_fraction(
    value: float, size: Size, viewport: Size, fraction_unit: Fraction
) -> Fraction:
    """Resolves a fraction unit i.e. width: 2fr

    Args:
        value (float): Scalar value.
        size (Size): Size of widget.
        viewport (Size): Size of viewport.
        fraction_unit (Fraction): Size of fraction, i.e. size of 1fr as a Fraction.

    Returns:
        Fraction: Resolved unit.
    """
    return fraction_unit * Fraction(value)


def _resolve_width(
    value: float, size: Size, viewport: Size, fraction_unit: Fraction
) -> Fraction:
    """Resolves width unit i.e. width: 50w.

    Args:
        value (float): Scalar value.
        size (Size): Size of widget.
        viewport (Size): Size of viewport.
        fraction_unit (Fraction): Size of fraction, i.e. size of 1fr as a Fraction.

    Returns:
        Fraction: Resolved unit.
    """
    return Fraction(value) * Fraction(size.width, 100)


def _resolve_height(
    value: float, size: Size, viewport: Size, fraction_unit: Fraction
) -> Fraction:
    """Resolves height unit, i.e. height: 12h.

    Args:
        value (float): Scalar value.
        size (Size): Size of widget.
        viewport (Size): Size of viewport.
        fraction_unit (Fraction): Size of fraction, i.e. size of 1fr as a Fraction.

    Returns:
        Fraction: Resolved unit.
    """
    return Fraction(value) * Fraction(size.height, 100)


def _resolve_view_width(
    value: float, size: Size, viewport: Size, fraction_unit: Fraction
) -> Fraction:
    """Resolves view width unit, i.e. width: 25vw.

    Args:
        value (float): Scalar value.
        size (Size): Size of widget.
        viewport (Size): Size of viewport.
        fraction_unit (Fraction): Size of fraction, i.e. size of 1fr as a Fraction.

    Returns:
        Fraction: Resolved unit.
    """
    return Fraction(value) * Fraction(viewport.width, 100)


def _resolve_view_height(
    value: float, size: Size, viewport: Size, fraction_unit: Fraction
) -> Fraction:
    """Resolves view height unit, i.e. height: 25vh.

    Args:
        value (float): Scalar value.
        size (Size): Size of widget.
        viewport (Size): Size of viewport.
        fraction_unit (Fraction): Size of fraction, i.e. size of 1fr as a Fraction.

    Returns:
        Fraction: Resolved unit.
    """
    return Fraction(value) * Fraction(viewport.height, 100)


RESOLVE_MAP = {
    Unit.CELLS: _resolve_cells,
    Unit.FRACTION: _resolve_fraction,
    Unit.WIDTH: _resolve_width,
    Unit.HEIGHT: _resolve_height,
    Unit.VIEW_WIDTH: _resolve_view_width,
    Unit.VIEW_HEIGHT: _resolve_view_height,
}


def get_symbols(units: Iterable[Unit]) -> list[str]:
    """Get symbols for an iterable of units.

    Args:
        units (Iterable[Unit]): A number of units.

    Returns:
        list[str]: List of symbols.
    """
    return [UNIT_SYMBOL[unit] for unit in units]


class Scalar(NamedTuple):
    """A numeric value and a unit."""

    value: float
    unit: Unit
    percent_unit: Unit

    def __str__(self) -> str:
        value, unit, _ = self
        if unit == Unit.AUTO:
            return "auto"
        return f"{int(value) if value.is_integer() else value}{self.symbol}"

    @property
    def is_cells(self) -> bool:
        """Check if the Scalar is explicit cells."""
        return self.unit == Unit.CELLS

    @property
    def is_percent(self) -> bool:
        """Check if the Scalar is a percentage unit."""
        return self.unit == Unit.PERCENT

    @property
    def is_fraction(self) -> bool:
        """Check if the unit is a fraction."""
        return self.unit == Unit.FRACTION

    @property
    def excludes_border(self) -> bool:
        return self.unit in UNIT_EXCLUDES_BORDER

    @property
    def cells(self) -> int | None:
        """Check if the unit is explicit cells."""
        value, unit, _ = self
        return int(value) if unit == Unit.CELLS else None

    @property
    def fraction(self) -> int | None:
        """Get the fraction value, or None if not a value."""
        value, unit, _ = self
        return int(value) if unit == Unit.FRACTION else None

    @property
    def symbol(self) -> str:
        """Get the symbol of this unit."""
        return UNIT_SYMBOL[self.unit]

    @property
    def is_auto(self) -> bool:
        """Check if this is an auto unit."""
        return self.unit == Unit.AUTO

    @classmethod
    def from_number(cls, value: float) -> Scalar:
        """Create a scalar with cells unit.

        Args:
            value (float): A number of cells.

        Returns:
            Scalar: New Scalar.
        """
        return cls(float(value), Unit.CELLS, Unit.WIDTH)

    @classmethod
    def parse(cls, token: str, percent_unit: Unit = Unit.WIDTH) -> Scalar:
        """Parse a string in to a Scalar

        Args:
            token (str): A string containing a scalar, e.g. "3.14fr"

        Raises:
            ScalarParseError: If the value is not a valid scalar

        Returns:
            Scalar: New scalar
        """
        if token.lower() == "auto":
            scalar = cls(1.0, Unit.AUTO, Unit.AUTO)
        else:
            match = _MATCH_SCALAR(token)
            if match is None:
                raise ScalarParseError(f"{token!r} is not a valid scalar")
            value, unit_name = match.groups()
            scalar = cls(float(value), SYMBOL_UNIT[unit_name or ""], percent_unit)
        return scalar

    @lru_cache(maxsize=4096)
    def resolve_dimension(
        self, size: Size, viewport: Size, fraction_unit: Fraction | None = None
    ) -> Fraction:
        """Resolve scalar with units in to a dimensions.

        Args:
            size (tuple[int, int]): Size of the container.
            viewport (tuple[int, int]): Size of the viewport (typically terminal size)

        Raises:
            ScalarResolveError: If the unit is unknown.

        Returns:
            int: A size (in cells)
        """
        value, unit, percent_unit = self

        if unit == Unit.PERCENT:
            unit = percent_unit
        try:
            dimension = RESOLVE_MAP[unit](
                value, size, viewport, fraction_unit or Fraction(1)
            )
        except KeyError:
            raise ScalarResolveError(f"expected dimensions; found {str(self)!r}")
        return dimension

    def copy_with(
        self,
        value: float | None = None,
        unit: Unit | None = None,
        percent_unit: Unit | None = None,
    ) -> Scalar:
        """Get a copy of this Scalar, with values optionally modified

        Args:
            value (float | None): The new value, or None to keep the same value
            unit (Unit | None): The new unit, or None to keep the same unit
            percent_unit (Unit | None): The new percent_unit, or None to keep the same percent_unit
        """
        return Scalar(
            value if value is not None else self.value,
            unit if unit is not None else self.unit,
            percent_unit if percent_unit is not None else self.percent_unit,
        )


@rich.repr.auto(angular=True)
class ScalarOffset(NamedTuple):
    """An Offset with two scalars, used to animate between to Scalars."""

    x: Scalar
    y: Scalar

    @classmethod
    def null(cls) -> ScalarOffset:
        """Get a null scalar offset (0, 0)."""
        return NULL_SCALAR

    @classmethod
    def from_offset(cls, offset: tuple[int, int]) -> ScalarOffset:
        """Create a Scalar offset from a tuple of integers.

        Args:
            offset (tuple[int, int]): Offset in cells.

        Returns:
            ScalarOffset: New offset.
        """
        x, y = offset
        return cls(
            Scalar(x, Unit.CELLS, Unit.WIDTH),
            Scalar(y, Unit.CELLS, Unit.HEIGHT),
        )

    def __bool__(self) -> bool:
        x, y = self
        return bool(x.value or y.value)

    def __rich_repr__(self) -> rich.repr.Result:
        yield None, str(self.x)
        yield None, str(self.y)

    def resolve(self, size: Size, viewport: Size) -> Offset:
        """Resolve the offset in to cells.

        Args:
            size (Size): Size of container.
            viewport (Size): Size of viewport.

        Returns:
            Offset: Offset in cells.
        """
        x, y = self
        return Offset(
            round(x.resolve_dimension(size, viewport)),
            round(y.resolve_dimension(size, viewport)),
        )


NULL_SCALAR = ScalarOffset(Scalar.from_number(0), Scalar.from_number(0))


def percentage_string_to_float(string: str) -> float:
    """Convert a string percentage e.g. '20%' to a float e.g. 20.0.

    Args:
        string (str): The percentage string to convert.
    """
    string = string.strip()
    if string.endswith("%"):
        float_percentage = clamp(float(string[:-1]) / 100.0, 0.0, 1.0)
    else:
        float_percentage = float(string)
    return float_percentage


if __name__ == "__main__":
    print(Scalar.parse("3.14fr"))
    s = Scalar.parse("23")
    print(repr(s))
    print(repr(s.cells))

Functions

def get_symbols(units: Iterable[Unit]) ‑> list[str]

Get symbols for an iterable of units.

Args

units : Iterable[Unit]
A number of units.

Returns

list[str]
List of symbols.
Expand source code
def get_symbols(units: Iterable[Unit]) -> list[str]:
    """Get symbols for an iterable of units.

    Args:
        units (Iterable[Unit]): A number of units.

    Returns:
        list[str]: List of symbols.
    """
    return [UNIT_SYMBOL[unit] for unit in units]
def percentage_string_to_float(string: str) ‑> float

Convert a string percentage e.g. '20%' to a float e.g. 20.0.

Args

string : str
The percentage string to convert.
Expand source code
def percentage_string_to_float(string: str) -> float:
    """Convert a string percentage e.g. '20%' to a float e.g. 20.0.

    Args:
        string (str): The percentage string to convert.
    """
    string = string.strip()
    if string.endswith("%"):
        float_percentage = clamp(float(string[:-1]) / 100.0, 0.0, 1.0)
    else:
        float_percentage = float(string)
    return float_percentage

Classes

class Scalar (value: float, unit: Unit, percent_unit: Unit)

A numeric value and a unit.

Expand source code
class Scalar(NamedTuple):
    """A numeric value and a unit."""

    value: float
    unit: Unit
    percent_unit: Unit

    def __str__(self) -> str:
        value, unit, _ = self
        if unit == Unit.AUTO:
            return "auto"
        return f"{int(value) if value.is_integer() else value}{self.symbol}"

    @property
    def is_cells(self) -> bool:
        """Check if the Scalar is explicit cells."""
        return self.unit == Unit.CELLS

    @property
    def is_percent(self) -> bool:
        """Check if the Scalar is a percentage unit."""
        return self.unit == Unit.PERCENT

    @property
    def is_fraction(self) -> bool:
        """Check if the unit is a fraction."""
        return self.unit == Unit.FRACTION

    @property
    def excludes_border(self) -> bool:
        return self.unit in UNIT_EXCLUDES_BORDER

    @property
    def cells(self) -> int | None:
        """Check if the unit is explicit cells."""
        value, unit, _ = self
        return int(value) if unit == Unit.CELLS else None

    @property
    def fraction(self) -> int | None:
        """Get the fraction value, or None if not a value."""
        value, unit, _ = self
        return int(value) if unit == Unit.FRACTION else None

    @property
    def symbol(self) -> str:
        """Get the symbol of this unit."""
        return UNIT_SYMBOL[self.unit]

    @property
    def is_auto(self) -> bool:
        """Check if this is an auto unit."""
        return self.unit == Unit.AUTO

    @classmethod
    def from_number(cls, value: float) -> Scalar:
        """Create a scalar with cells unit.

        Args:
            value (float): A number of cells.

        Returns:
            Scalar: New Scalar.
        """
        return cls(float(value), Unit.CELLS, Unit.WIDTH)

    @classmethod
    def parse(cls, token: str, percent_unit: Unit = Unit.WIDTH) -> Scalar:
        """Parse a string in to a Scalar

        Args:
            token (str): A string containing a scalar, e.g. "3.14fr"

        Raises:
            ScalarParseError: If the value is not a valid scalar

        Returns:
            Scalar: New scalar
        """
        if token.lower() == "auto":
            scalar = cls(1.0, Unit.AUTO, Unit.AUTO)
        else:
            match = _MATCH_SCALAR(token)
            if match is None:
                raise ScalarParseError(f"{token!r} is not a valid scalar")
            value, unit_name = match.groups()
            scalar = cls(float(value), SYMBOL_UNIT[unit_name or ""], percent_unit)
        return scalar

    @lru_cache(maxsize=4096)
    def resolve_dimension(
        self, size: Size, viewport: Size, fraction_unit: Fraction | None = None
    ) -> Fraction:
        """Resolve scalar with units in to a dimensions.

        Args:
            size (tuple[int, int]): Size of the container.
            viewport (tuple[int, int]): Size of the viewport (typically terminal size)

        Raises:
            ScalarResolveError: If the unit is unknown.

        Returns:
            int: A size (in cells)
        """
        value, unit, percent_unit = self

        if unit == Unit.PERCENT:
            unit = percent_unit
        try:
            dimension = RESOLVE_MAP[unit](
                value, size, viewport, fraction_unit or Fraction(1)
            )
        except KeyError:
            raise ScalarResolveError(f"expected dimensions; found {str(self)!r}")
        return dimension

    def copy_with(
        self,
        value: float | None = None,
        unit: Unit | None = None,
        percent_unit: Unit | None = None,
    ) -> Scalar:
        """Get a copy of this Scalar, with values optionally modified

        Args:
            value (float | None): The new value, or None to keep the same value
            unit (Unit | None): The new unit, or None to keep the same unit
            percent_unit (Unit | None): The new percent_unit, or None to keep the same percent_unit
        """
        return Scalar(
            value if value is not None else self.value,
            unit if unit is not None else self.unit,
            percent_unit if percent_unit is not None else self.percent_unit,
        )

Ancestors

  • builtins.tuple

Static methods

def from_number(value: float) ‑> Scalar

Create a scalar with cells unit.

Args

value : float
A number of cells.

Returns

Scalar
New Scalar.
Expand source code
@classmethod
def from_number(cls, value: float) -> Scalar:
    """Create a scalar with cells unit.

    Args:
        value (float): A number of cells.

    Returns:
        Scalar: New Scalar.
    """
    return cls(float(value), Unit.CELLS, Unit.WIDTH)
def parse(token: str, percent_unit: Unit = Unit.WIDTH) ‑> Scalar

Parse a string in to a Scalar

Args

token : str
A string containing a scalar, e.g. "3.14fr"

Raises

ScalarParseError
If the value is not a valid scalar

Returns

Scalar
New scalar
Expand source code
@classmethod
def parse(cls, token: str, percent_unit: Unit = Unit.WIDTH) -> Scalar:
    """Parse a string in to a Scalar

    Args:
        token (str): A string containing a scalar, e.g. "3.14fr"

    Raises:
        ScalarParseError: If the value is not a valid scalar

    Returns:
        Scalar: New scalar
    """
    if token.lower() == "auto":
        scalar = cls(1.0, Unit.AUTO, Unit.AUTO)
    else:
        match = _MATCH_SCALAR(token)
        if match is None:
            raise ScalarParseError(f"{token!r} is not a valid scalar")
        value, unit_name = match.groups()
        scalar = cls(float(value), SYMBOL_UNIT[unit_name or ""], percent_unit)
    return scalar

Instance variables

var cells : int | None

Check if the unit is explicit cells.

Expand source code
@property
def cells(self) -> int | None:
    """Check if the unit is explicit cells."""
    value, unit, _ = self
    return int(value) if unit == Unit.CELLS else None
var excludes_border : bool
Expand source code
@property
def excludes_border(self) -> bool:
    return self.unit in UNIT_EXCLUDES_BORDER
var fraction : int | None

Get the fraction value, or None if not a value.

Expand source code
@property
def fraction(self) -> int | None:
    """Get the fraction value, or None if not a value."""
    value, unit, _ = self
    return int(value) if unit == Unit.FRACTION else None
var is_auto : bool

Check if this is an auto unit.

Expand source code
@property
def is_auto(self) -> bool:
    """Check if this is an auto unit."""
    return self.unit == Unit.AUTO
var is_cells : bool

Check if the Scalar is explicit cells.

Expand source code
@property
def is_cells(self) -> bool:
    """Check if the Scalar is explicit cells."""
    return self.unit == Unit.CELLS
var is_fraction : bool

Check if the unit is a fraction.

Expand source code
@property
def is_fraction(self) -> bool:
    """Check if the unit is a fraction."""
    return self.unit == Unit.FRACTION
var is_percent : bool

Check if the Scalar is a percentage unit.

Expand source code
@property
def is_percent(self) -> bool:
    """Check if the Scalar is a percentage unit."""
    return self.unit == Unit.PERCENT
var percent_unitUnit

Alias for field number 2

var symbol : str

Get the symbol of this unit.

Expand source code
@property
def symbol(self) -> str:
    """Get the symbol of this unit."""
    return UNIT_SYMBOL[self.unit]
var unitUnit

Alias for field number 1

var value : float

Alias for field number 0

Methods

def copy_with(self, value: float | None = None, unit: Unit | None = None, percent_unit: Unit | None = None) ‑> Scalar

Get a copy of this Scalar, with values optionally modified

Args

value (float | None): The new value, or None to keep the same value unit (Unit | None): The new unit, or None to keep the same unit percent_unit (Unit | None): The new percent_unit, or None to keep the same percent_unit

Expand source code
def copy_with(
    self,
    value: float | None = None,
    unit: Unit | None = None,
    percent_unit: Unit | None = None,
) -> Scalar:
    """Get a copy of this Scalar, with values optionally modified

    Args:
        value (float | None): The new value, or None to keep the same value
        unit (Unit | None): The new unit, or None to keep the same unit
        percent_unit (Unit | None): The new percent_unit, or None to keep the same percent_unit
    """
    return Scalar(
        value if value is not None else self.value,
        unit if unit is not None else self.unit,
        percent_unit if percent_unit is not None else self.percent_unit,
    )
def resolve_dimension(self, size: Size, viewport: Size, fraction_unit: Fraction | None = None) ‑> Fraction

Resolve scalar with units in to a dimensions.

Args

size : tuple[int, int]
Size of the container.
viewport : tuple[int, int]
Size of the viewport (typically terminal size)

Raises

ScalarResolveError
If the unit is unknown.

Returns

int
A size (in cells)
Expand source code
@lru_cache(maxsize=4096)
def resolve_dimension(
    self, size: Size, viewport: Size, fraction_unit: Fraction | None = None
) -> Fraction:
    """Resolve scalar with units in to a dimensions.

    Args:
        size (tuple[int, int]): Size of the container.
        viewport (tuple[int, int]): Size of the viewport (typically terminal size)

    Raises:
        ScalarResolveError: If the unit is unknown.

    Returns:
        int: A size (in cells)
    """
    value, unit, percent_unit = self

    if unit == Unit.PERCENT:
        unit = percent_unit
    try:
        dimension = RESOLVE_MAP[unit](
            value, size, viewport, fraction_unit or Fraction(1)
        )
    except KeyError:
        raise ScalarResolveError(f"expected dimensions; found {str(self)!r}")
    return dimension
class ScalarError (*args, **kwargs)

Common base class for all non-exit exceptions.

Expand source code
class ScalarError(Exception):
    pass

Ancestors

  • builtins.Exception
  • builtins.BaseException

Subclasses

class ScalarOffset (x: Scalar, y: Scalar)

An Offset with two scalars, used to animate between to Scalars.

Expand source code
class ScalarOffset(NamedTuple):
    """An Offset with two scalars, used to animate between to Scalars."""

    x: Scalar
    y: Scalar

    @classmethod
    def null(cls) -> ScalarOffset:
        """Get a null scalar offset (0, 0)."""
        return NULL_SCALAR

    @classmethod
    def from_offset(cls, offset: tuple[int, int]) -> ScalarOffset:
        """Create a Scalar offset from a tuple of integers.

        Args:
            offset (tuple[int, int]): Offset in cells.

        Returns:
            ScalarOffset: New offset.
        """
        x, y = offset
        return cls(
            Scalar(x, Unit.CELLS, Unit.WIDTH),
            Scalar(y, Unit.CELLS, Unit.HEIGHT),
        )

    def __bool__(self) -> bool:
        x, y = self
        return bool(x.value or y.value)

    def __rich_repr__(self) -> rich.repr.Result:
        yield None, str(self.x)
        yield None, str(self.y)

    def resolve(self, size: Size, viewport: Size) -> Offset:
        """Resolve the offset in to cells.

        Args:
            size (Size): Size of container.
            viewport (Size): Size of viewport.

        Returns:
            Offset: Offset in cells.
        """
        x, y = self
        return Offset(
            round(x.resolve_dimension(size, viewport)),
            round(y.resolve_dimension(size, viewport)),
        )

Ancestors

  • builtins.tuple

Static methods

def from_offset(offset: tuple[int, int]) ‑> ScalarOffset

Create a Scalar offset from a tuple of integers.

Args

offset : tuple[int, int]
Offset in cells.

Returns

ScalarOffset
New offset.
Expand source code
@classmethod
def from_offset(cls, offset: tuple[int, int]) -> ScalarOffset:
    """Create a Scalar offset from a tuple of integers.

    Args:
        offset (tuple[int, int]): Offset in cells.

    Returns:
        ScalarOffset: New offset.
    """
    x, y = offset
    return cls(
        Scalar(x, Unit.CELLS, Unit.WIDTH),
        Scalar(y, Unit.CELLS, Unit.HEIGHT),
    )
def null() ‑> ScalarOffset

Get a null scalar offset (0, 0).

Expand source code
@classmethod
def null(cls) -> ScalarOffset:
    """Get a null scalar offset (0, 0)."""
    return NULL_SCALAR

Instance variables

var xScalar

Alias for field number 0

var yScalar

Alias for field number 1

Methods

def resolve(self, size: Size, viewport: Size) ‑> Offset

Resolve the offset in to cells.

Args

size : Size
Size of container.
viewport : Size
Size of viewport.

Returns

Offset
Offset in cells.
Expand source code
def resolve(self, size: Size, viewport: Size) -> Offset:
    """Resolve the offset in to cells.

    Args:
        size (Size): Size of container.
        viewport (Size): Size of viewport.

    Returns:
        Offset: Offset in cells.
    """
    x, y = self
    return Offset(
        round(x.resolve_dimension(size, viewport)),
        round(y.resolve_dimension(size, viewport)),
    )
class ScalarParseError (*args, **kwargs)

Common base class for all non-exit exceptions.

Expand source code
class ScalarParseError(ScalarError):
    pass

Ancestors

  • ScalarError
  • builtins.Exception
  • builtins.BaseException
class ScalarResolveError (*args, **kwargs)

Common base class for all non-exit exceptions.

Expand source code
class ScalarResolveError(ScalarError):
    pass

Ancestors

  • ScalarError
  • builtins.Exception
  • builtins.BaseException
class Unit (value, names=None, *, module=None, qualname=None, type=None, start=1)

Enumeration of the various units inherited from CSS.

Expand source code
class Unit(Enum):
    """Enumeration of the various units inherited from CSS."""

    CELLS = 1
    FRACTION = 2
    PERCENT = 3
    WIDTH = 4
    HEIGHT = 5
    VIEW_WIDTH = 6
    VIEW_HEIGHT = 7
    AUTO = 8

Ancestors

  • enum.Enum

Class variables

var AUTO
var CELLS
var FRACTION
var HEIGHT
var PERCENT
var VIEW_HEIGHT
var VIEW_WIDTH
var WIDTH