diff --git a/CHANGELOG.md b/CHANGELOG.md
index 84fa8fff9..3b7a424da 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -20,6 +20,9 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
- option `--port` to the command `textual console` to specify which port the console should connect to https://github.com/Textualize/textual/pull/2258
- `Widget.scroll_to_center` method to scroll children to the center of container widget https://github.com/Textualize/textual/pull/2255 and https://github.com/Textualize/textual/pull/2276
- Added `TabActivated` message to `TabbedContent` https://github.com/Textualize/textual/pull/2260
+- Added "panel" border style https://github.com/Textualize/textual/pull/2292
+- Added `border-title-color`, `border-title-background`, `border-title-style` rules https://github.com/Textualize/textual/issues/2289
+- Added `border-subtitle-color`, `border-subtitle-background`, `border-subtitle-style` rules https://github.com/Textualize/textual/issues/2289
### Fixed
diff --git a/docs/examples/styles/border_title_colors.css b/docs/examples/styles/border_title_colors.css
new file mode 100644
index 000000000..0ab890944
--- /dev/null
+++ b/docs/examples/styles/border_title_colors.css
@@ -0,0 +1,16 @@
+Screen {
+ align: center middle;
+}
+
+Label {
+ padding: 4 8;
+ border: heavy red;
+
+ border-title-color: green;
+ border-title-background: white;
+ border-title-style: bold;
+
+ border-subtitle-color: magenta;
+ border-subtitle-background: yellow;
+ border-subtitle-style: italic;
+}
diff --git a/docs/examples/styles/border_title_colors.py b/docs/examples/styles/border_title_colors.py
new file mode 100644
index 000000000..1af74ccc6
--- /dev/null
+++ b/docs/examples/styles/border_title_colors.py
@@ -0,0 +1,19 @@
+from textual.app import App, ComposeResult
+from textual.widgets import Label
+
+
+class BorderTitleApp(App):
+ CSS_PATH = "border_title_colors.css"
+
+ def compose(self) -> ComposeResult:
+ yield Label("Hello, World!")
+
+ def on_mount(self) -> None:
+ label = self.query_one(Label)
+ label.border_title = "Textual Rocks"
+ label.border_subtitle = "Textual Rocks"
+
+
+if __name__ == "__main__":
+ app = BorderTitleApp()
+ app.run()
diff --git a/docs/snippets/border_title_color.md b/docs/snippets/border_title_color.md
new file mode 100644
index 000000000..c2a69052c
--- /dev/null
+++ b/docs/snippets/border_title_color.md
@@ -0,0 +1,18 @@
+The following examples demonstrates customization of the border color and text style rules.
+
+=== "Output"
+
+ ```{.textual path="docs/examples/styles/border_title_colors.py"}
+ ```
+
+=== "border_title_colors.py"
+
+ ```python
+ --8<-- "docs/examples/styles/border_title_colors.py"
+ ```
+
+=== "border_title_colors.css"
+
+ ```sass
+ --8<-- "docs/examples/styles/border_title_colors.css"
+ ```
diff --git a/docs/snippets/see_also_border.md b/docs/snippets/see_also_border.md
new file mode 100644
index 000000000..83b09dbe3
--- /dev/null
+++ b/docs/snippets/see_also_border.md
@@ -0,0 +1,9 @@
+- [`border-title-align`](./border_title_align.md) to set the title's alignment.
+- [`border-title-color`](./border_subtitle_color.md) to set the title's color.
+- [`border-title-background`](./border_subtitle_background.md) to set the title's background color.
+- [`border-title-style`](./border_subtitle_style.md) to set the title's text style.
+
+- [`border-subtitle-align`](./border_subtitle_align.md) to set the sub-title's alignment.
+- [`border-subtitle-color`](./border_subtitle_color.md) to set the sub-title's color.
+- [`border-subtitle-background`](./border_subtitle_background.md) to set the sub-title's background color.
+- [`border-subtitle-style`](./border_subtitle_style.md) to set the sub-title's text style.
diff --git a/docs/styles/align.md b/docs/styles/align.md
index 76835389c..c32d004aa 100644
--- a/docs/styles/align.md
+++ b/docs/styles/align.md
@@ -13,12 +13,7 @@ align-vertical: <vertical>;
The `align` style takes a [``](../../css_types/horizontal) followed by a [``](../../css_types/vertical).
-You can specify the alignment of children on both the horizontal and vertical axes at the same time,
-or on each of the axis separately.
-To specify alignment on a single axis, use the respective style and type:
-
- - `align-horizontal` takes a [``](../../css_types/horizontal) and does alignment along the horizontal axis; and
- - `align-vertical` takes a [``](../../css_types/vertical) and does alignment along the vertical axis.
+You can also set the alignment for each axis individually with `align-horizontal` and `align-vertical`.
## Examples
diff --git a/docs/styles/border.md b/docs/styles/border.md
index 267c16347..6463c871d 100644
--- a/docs/styles/border.md
+++ b/docs/styles/border.md
@@ -2,9 +2,11 @@
The `border` style enables the drawing of a box around a widget.
+A border style may also be applied to individual edges with `border-top`, `border-right`, `border-bottom`, and `border-left`.
+
!!! note
- Due to a Textual limitation, [`border`](./border.md) and [`outline`](./outline.md) cannot coexist in the same edge of a widget.
+ [`border`](./border.md) and [`outline`](./outline.md) cannot coexist in the same edge of a widget.
## Syntax
@@ -17,31 +19,10 @@ border-bottom: [<border>] [<border>] [<color> [<percentage>]];
--8<-- "docs/snippets/syntax_block_end.md"
-The `border` style accepts an optional [``](../../css_types/border) that sets the visual style of the widget border, an optional [``](../../css_types/color) to set the color of the border, and an optional [``](../../css_types/percentage) to specify the color transparency.
+In CSS, the border is set with a [border style](./border.md) and a color. Both are optional. An optional percentage may be added to blend the border with the background color.
-Borders may also be set individually for the four edges of a widget with the `border-top`, `border-right`, `border-bottom` and `border-left` rules.
+In Python, the border is set with a tuple of [border style](./border.md) and a color.
-### Multiple edge rules
-
-If multiple border styles target the same edge, the last style that targets a specific edge is the one that is applied to that edge.
-For example, consider the CSS below:
-
-```sass
-Static {
- border-top: dashed red;
- border: solid green; /* overrides the border-top rule above */
- /* Change the border but just for the bottom edge: */
- border-bottom: double blue;
-}
-```
-
-The CSS snippet above will add a solid green border around `Static` widgets, except for the bottom edge, which will be double blue.
-
-### Defaults
-
-If `` is specified but `` is not, it defaults to `"solid"`.
-If `` is specified but ``is not, it defaults to green (RGB color `"#00FF00"`).
-If `` is not specified it defaults to `100%`.
## Border command
@@ -128,3 +109,4 @@ widget.styles.border_left = ("outer", "red")
- [`box-sizing`](./box_sizing.md) to specify how to account for the border in a widget's dimensions.
- [`outline`](./outline.md) to add an outline around the content of a widget.
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_subtitle_align.md b/docs/styles/border_subtitle_align.md
index d46c9f1e2..148918ca6 100644
--- a/docs/styles/border_subtitle_align.md
+++ b/docs/styles/border_subtitle_align.md
@@ -60,3 +60,7 @@ widget.styles.border_subtitle_align = "left"
widget.styles.border_subtitle_align = "center"
widget.styles.border_subtitle_align = "right"
```
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_subtitle_background.md b/docs/styles/border_subtitle_background.md
new file mode 100644
index 000000000..8d60b3e15
--- /dev/null
+++ b/docs/styles/border_subtitle_background.md
@@ -0,0 +1,34 @@
+# Border-subtitle-background
+
+The `border-subtitle-background` style sets the *background* color of the [border_subtitle][textual.widget.Widget.border_subtitle].
+
+## Syntax
+
+--8<-- "docs/snippets/syntax_block_start.md"
+border-subtitle-background: (<color> | auto) [<percentage>];
+--8<-- "docs/snippets/syntax_block_end.md"
+
+
+
+## Example
+
+--8<-- "docs/snippets/border_title_color.md"
+
+
+
+## CSS
+
+```sass
+border-subtitle-background: blue;
+```
+
+## Python
+
+```python
+widget.styles.border_subtitle_background = "blue"
+```
+
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_subtitle_color.md b/docs/styles/border_subtitle_color.md
new file mode 100644
index 000000000..388011159
--- /dev/null
+++ b/docs/styles/border_subtitle_color.md
@@ -0,0 +1,33 @@
+# Border-subtitle-color
+
+The `border-subtitle-color` style sets the color of the [border_subtitle][textual.widget.Widget.border_subtitle].
+
+## Syntax
+
+--8<-- "docs/snippets/syntax_block_start.md"
+border-subtitle-color: (<color> | auto) [<percentage>];
+--8<-- "docs/snippets/syntax_block_end.md"
+
+
+## Example
+
+--8<-- "docs/snippets/border_title_color.md"
+
+
+
+## CSS
+
+```sass
+border-subtitle-color: red;
+```
+
+## Python
+
+```python
+widget.styles.border_subtitle_color = "red"
+```
+
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_subtitle_style.md b/docs/styles/border_subtitle_style.md
new file mode 100644
index 000000000..3b826568f
--- /dev/null
+++ b/docs/styles/border_subtitle_style.md
@@ -0,0 +1,35 @@
+# Border-subtitle-style
+
+The `border-subtitle-style` style sets the text style of the [border_subtitle][textual.widget.Widget.border_subtitle].
+
+
+## Syntax
+
+--8<-- "docs/snippets/syntax_block_start.md"
+border-subtitle-style: <text-style>;
+--8<-- "docs/snippets/syntax_block_end.md"
+
+
+## Example
+
+--8<-- "docs/snippets/border_title_color.md"
+
+
+## CSS
+
+```sass
+border-subtitle-style: bold underline;
+```
+
+## Python
+
+```python
+widget.styles.border_subtitle_style = "bold underline"
+```
+
+
+
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_title_align.md b/docs/styles/border_title_align.md
index e410a771c..5f754fe39 100644
--- a/docs/styles/border_title_align.md
+++ b/docs/styles/border_title_align.md
@@ -60,3 +60,7 @@ widget.styles.border_title_align = "left"
widget.styles.border_title_align = "center"
widget.styles.border_title_align = "right"
```
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_title_background.md b/docs/styles/border_title_background.md
new file mode 100644
index 000000000..19d33e578
--- /dev/null
+++ b/docs/styles/border_title_background.md
@@ -0,0 +1,33 @@
+# Border-title-background
+
+The `border-title-background` style sets the *background* color of the [border_title][textual.widget.Widget.border_title].
+
+## Syntax
+
+--8<-- "docs/snippets/syntax_block_start.md"
+border-title-background: (<color> | auto) [<percentage>];
+--8<-- "docs/snippets/syntax_block_end.md"
+
+
+
+## Example
+
+--8<-- "docs/snippets/border_title_color.md"
+
+
+## CSS
+
+```sass
+border-title-background: blue;
+```
+
+## Python
+
+```python
+widget.styles.border_title_background = "blue"
+```
+
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_title_color.md b/docs/styles/border_title_color.md
new file mode 100644
index 000000000..2272de9c6
--- /dev/null
+++ b/docs/styles/border_title_color.md
@@ -0,0 +1,31 @@
+# Border-title-color
+
+The `border-title-color` style sets the color of the [border_title][textual.widget.Widget.border_title].
+
+## Syntax
+
+--8<-- "docs/snippets/syntax_block_start.md"
+border-title-color: (<color> | auto) [<percentage>];
+--8<-- "docs/snippets/syntax_block_end.md"
+
+## Example
+
+--8<-- "docs/snippets/border_title_color.md"
+
+
+## CSS
+
+```sass
+border-title-color: red;
+```
+
+## Python
+
+```python
+widget.styles.border_title_color = "red"
+```
+
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/border_title_style.md b/docs/styles/border_title_style.md
new file mode 100644
index 000000000..09e8319cc
--- /dev/null
+++ b/docs/styles/border_title_style.md
@@ -0,0 +1,35 @@
+# Border-title-style
+
+The `border-title-style` style sets the text style of the [border_title][textual.widget.Widget.border_title].
+
+
+## Syntax
+
+--8<-- "docs/snippets/syntax_block_start.md"
+border-title-style: <text-style>;
+--8<-- "docs/snippets/syntax_block_end.md"
+
+
+
+## Example
+
+--8<-- "docs/snippets/border_title_color.md"
+
+
+## CSS
+
+```sass
+border-title-style: bold underline;
+```
+
+## Python
+
+```python
+widget.styles.border_title_style = "bold underline"
+```
+
+
+
+## See also
+
+--8<-- "docs/snippets/see_also_border.md"
diff --git a/docs/styles/outline.md b/docs/styles/outline.md
index 5e5155f89..650619b05 100644
--- a/docs/styles/outline.md
+++ b/docs/styles/outline.md
@@ -4,7 +4,7 @@ The `outline` style enables the drawing of a box around the content of a widget,
!!! note
- Due to a Textual limitation, [`border`](./border.md) and [`outline`](./outline.md) cannot coexist in the same edge of a widget.
+ [`border`](./border.md) and [`outline`](./outline.md) cannot coexist in the same edge of a widget.
## Syntax
diff --git a/docs/styles/text_style.md b/docs/styles/text_style.md
index a0ee02f90..8e9cb4775 100644
--- a/docs/styles/text_style.md
+++ b/docs/styles/text_style.md
@@ -1,6 +1,6 @@
# Text-style
-The `text-style` sets the style for the text in a widget.
+The `text-style` style sets the style for the text in a widget.
## Syntax
diff --git a/mkdocs-nav.yml b/mkdocs-nav.yml
index c29934582..7b77d6f43 100644
--- a/mkdocs-nav.yml
+++ b/mkdocs-nav.yml
@@ -64,17 +64,23 @@ nav:
- "events/screen_suspend.md"
- "events/show.md"
- Styles:
- - "styles/index.md"
- "styles/align.md"
- "styles/background.md"
- - "styles/border.md"
- "styles/border_subtitle_align.md"
+ - "styles/border_subtitle_background.md"
+ - "styles/border_subtitle_color.md"
+ - "styles/border_subtitle_style.md"
- "styles/border_title_align.md"
+ - "styles/border_title_background.md"
+ - "styles/border_title_color.md"
+ - "styles/border_title_style.md"
+ - "styles/border.md"
- "styles/box_sizing.md"
- "styles/color.md"
- "styles/content_align.md"
- "styles/display.md"
- "styles/dock.md"
+ - "styles/index.md"
- Grid:
- "styles/grid/index.md"
- "styles/grid/column_span.md"
diff --git a/src/textual/_border.py b/src/textual/_border.py
index 3b3bf2670..5cbb61dee 100644
--- a/src/textual/_border.py
+++ b/src/textual/_border.py
@@ -102,9 +102,14 @@ BORDER_CHARS: dict[
("▊", " ", "▎"),
("▊", "▁", "▎"),
),
+ "panel": (
+ ("▊", "█", "▎"),
+ ("▊", " ", "▎"),
+ ("▊", "▁", "▎"),
+ ),
"wide": (
("▁", "▁", "▁"),
- ("▎", " ", "▋"),
+ ("▎", " ", "▊"),
("▔", "▔", "▔"),
),
}
@@ -195,6 +200,11 @@ BORDER_LOCATIONS: dict[
(2, 0, 1),
(2, 0, 1),
),
+ "panel": (
+ (2, 0, 1),
+ (2, 0, 1),
+ (2, 0, 1),
+ ),
"wide": (
(1, 1, 1),
(0, 1, 3),
@@ -202,6 +212,11 @@ BORDER_LOCATIONS: dict[
),
}
+# Some borders (such as panel) require that the title (and subtitle) be draw in reverse.
+# This is a mapping of the border type on to a tuple for the top and bottom borders, to indicate
+# reverse colors is required.
+BORDER_TITLE_FLIP: dict[str, tuple[bool, bool]] = {"panel": (True, False)}
+
# In a similar fashion, we extract the border _label_ locations for easier access when
# rendering a border label.
# The values are a pair with (title location, subtitle location).
@@ -283,7 +298,7 @@ def get_box(
def render_border_label(
- label: Text,
+ label: tuple[Text, Style],
is_title: bool,
name: EdgeType,
width: int,
@@ -300,7 +315,7 @@ def render_border_label(
account the inner, outer, and border-specific, styles.
Args:
- label: The label to display (that may contain markup).
+ label: Tuple of label and style to render in the border.
is_title: Whether we are rendering the title (`True`) or the subtitle (`False`).
name: Name of the box type.
width: The width, in cells, of the space available for the whole edge.
@@ -323,14 +338,21 @@ def render_border_label(
# How many cells do we need to reserve for surrounding blanks and corners?
corners_needed = has_left_corner + has_right_corner
cells_reserved = 2 * corners_needed
- if not label.cell_len or width <= cells_reserved:
+
+ text_label, label_style = label
+ if not text_label.cell_len or width <= cells_reserved:
return
- text_label = label.copy()
+ text_label = text_label.copy()
text_label.truncate(width - cells_reserved, overflow="ellipsis")
- segments = text_label.render(console)
+ if has_left_corner:
+ text_label.pad_left(1)
+ if has_right_corner:
+ text_label.pad_right(1)
+ text_label.stylize_before(label_style)
label_style_location = BORDER_LABEL_LOCATIONS[name][0 if is_title else 1]
+ flip_top, flip_bottom = BORDER_TITLE_FLIP.get(name, (False, False))
inner = inner_style + style
outer = outer_style + style
@@ -347,15 +369,14 @@ def render_border_label(
else:
assert False
- styled_segments = [
- Segment(segment.text, base_style + segment.style) for segment in segments
- ]
- blank = Segment(" ", base_style)
- if has_left_corner:
- yield blank
- yield from styled_segments
- if has_right_corner:
- yield blank
+ if (flip_top and is_title) or (flip_bottom and not is_title):
+ base_style = base_style.without_color + Style.from_color(
+ base_style.bgcolor, base_style.color
+ )
+
+ text_label.stylize_before(base_style + label_style)
+ segments = text_label.render(console)
+ yield from segments
def render_row(
diff --git a/src/textual/_styles_cache.py b/src/textual/_styles_cache.py
index 8092f0c45..a623c53f4 100644
--- a/src/textual/_styles_cache.py
+++ b/src/textual/_styles_cache.py
@@ -107,6 +107,10 @@ class StylesCache:
Returns:
Rendered lines.
"""
+
+ border_title = widget._border_title
+ border_subtitle = widget._border_subtitle
+
base_background, background = widget.background_colors
styles = widget.styles
strips = self.render(
@@ -116,8 +120,22 @@ class StylesCache:
background,
widget.render_line,
widget.app.console,
- widget._border_title,
- widget._border_subtitle,
+ (
+ None
+ if border_title is None
+ else (
+ border_title,
+ *widget._get_title_style_information(base_background),
+ )
+ ),
+ (
+ None
+ if border_subtitle is None
+ else (
+ border_subtitle,
+ *widget._get_subtitle_style_information(base_background),
+ )
+ ),
content_size=widget.content_region.size,
padding=styles.padding,
crop=crop,
@@ -147,8 +165,8 @@ class StylesCache:
background: Color,
render_content_line: RenderLineCallback,
console: Console,
- border_title: Text | None,
- border_subtitle: Text | None,
+ border_title: tuple[Text, Color, Color, Style] | None,
+ border_subtitle: tuple[Text, Color, Color, Style] | None,
content_size: Size | None = None,
padding: Spacing | None = None,
crop: Region | None = None,
@@ -163,8 +181,8 @@ class StylesCache:
background: Background color of widget.
render_content_line: Callback to render content line.
console: The console in use by the app.
- border_title: The title for the widget border.
- border_subtitle: The subtitle for the widget border.
+ border_title: Optional tuple of (title, color, background, style).
+ border_subtitle: Optional tuple of (subtitle, color, background, style).
content_size: Size of content or None to assume full size.
padding: Override padding from Styles, or None to use styles.padding.
crop: Region to crop to.
@@ -229,8 +247,8 @@ class StylesCache:
background: Color,
render_content_line: Callable[[int], Strip],
console: Console,
- border_title: Text | None,
- border_subtitle: Text | None,
+ border_title: tuple[Text, Color, Color, Style] | None,
+ border_subtitle: tuple[Text, Color, Color, Style] | None,
) -> Strip:
"""Render a styled line.
@@ -244,8 +262,8 @@ class StylesCache:
background: Background color of widget.
render_content_line: Callback to render a line of content.
console: The console in use by the app.
- border_title: The title for the widget border.
- border_subtitle: The subtitle for the widget border.
+ border_title: Optional tuple of (title, color, background, style).
+ border_subtitle: Optional tuple of (subtitle, color, background, style).
Returns:
A line of segments.
@@ -305,10 +323,26 @@ class StylesCache:
has_left = border_left != ""
has_right = border_right != ""
border_label = border_title if is_top else border_subtitle
+ if border_label is None:
+ render_label = None
+ else:
+ label, label_color, label_background, style = border_label
+ base_label_background = base_background + background
+ style += Style.from_color(
+ (
+ (base_label_background + label_color).rich_color
+ if label_color.a
+ else None
+ ),
+ (base_label_background + label_background).rich_color
+ if label_background.a
+ else None,
+ )
+ render_label = (label, style)
# Try to save time with expensive call to `render_border_label`:
- if border_label:
+ if render_label:
label_segments = render_border_label(
- border_label,
+ render_label,
is_top,
border_edge_type,
width - 2,
diff --git a/src/textual/css/_styles_builder.py b/src/textual/css/_styles_builder.py
index eb8546234..4e6ddcc1d 100644
--- a/src/textual/css/_styles_builder.py
+++ b/src/textual/css/_styles_builder.py
@@ -640,6 +640,11 @@ class StylesBuilder:
process_link_hover_color = process_color
process_link_hover_background = process_color
+ process_border_title_color = process_color
+ process_border_title_background = process_color
+ process_border_subtitle_color = process_color
+ process_border_subtitle_background = process_color
+
def process_text_style(self, name: str, tokens: list[Token]) -> None:
for token in tokens:
value = token.value
@@ -656,6 +661,9 @@ class StylesBuilder:
process_link_style = process_text_style
process_link_hover_style = process_text_style
+ process_border_title_style = process_text_style
+ process_border_subtitle_style = process_text_style
+
def process_text_align(self, name: str, tokens: list[Token]) -> None:
"""Process a text-align declaration"""
if not tokens:
diff --git a/src/textual/css/styles.py b/src/textual/css/styles.py
index e751033ae..2dcbb181e 100644
--- a/src/textual/css/styles.py
+++ b/src/textual/css/styles.py
@@ -167,6 +167,16 @@ class RulesMap(TypedDict, total=False):
link_hover_background: Color
link_hover_style: Style
+ auto_border_title_color: bool
+ border_title_color: Color
+ border_title_background: Color
+ border_title_style: Style
+
+ auto_border_subtitle_color: bool
+ border_subtitle_color: Color
+ border_subtitle_background: Color
+ border_subtitle_style: Style
+
RULE_NAMES = list(RulesMap.__annotations__.keys())
RULE_NAMES_SET = frozenset(RULE_NAMES)
@@ -321,6 +331,16 @@ class StylesBase(ABC):
link_hover_background = ColorProperty("transparent")
link_hover_style = StyleFlagsProperty()
+ auto_border_title_color = BooleanProperty(default=False)
+ border_title_color = ColorProperty(Color(255, 255, 255, 0))
+ border_title_background = ColorProperty(Color(0, 0, 0, 0))
+ border_title_style = StyleFlagsProperty()
+
+ auto_border_subtitle_color = BooleanProperty(default=False)
+ border_subtitle_color = ColorProperty(Color(255, 255, 255, 0))
+ border_subtitle_background = ColorProperty(Color(0, 0, 0, 0))
+ border_subtitle_style = StyleFlagsProperty()
+
def __textual_animation__(
self,
attribute: str,
@@ -990,6 +1010,22 @@ class Styles(StylesBase):
if "link_hover_style" in rules:
append_declaration("link-hover-style", str(self.link_hover_style))
+ if "border_title_color" in rules:
+ append_declaration("title-color", self.border_title_color.css)
+ if "border_title_background" in rules:
+ append_declaration("title-background", self.border_title_background.css)
+ if "border_title_style" in rules:
+ append_declaration("title-text-style", str(self.border_title_style))
+
+ if "border_subtitle_color" in rules:
+ append_declaration("subtitle-color", self.border_subtitle_color.css)
+ if "border_subtitle_background" in rules:
+ append_declaration(
+ "subtitle-background", self.border_subtitle_background.css
+ )
+ if "border_subtitle_text_style" in rules:
+ append_declaration("subtitle-text-style", str(self.border_subtitle_style))
+
lines.sort()
return lines
diff --git a/src/textual/css/types.py b/src/textual/css/types.py
index 48f8433b3..395b549e0 100644
--- a/src/textual/css/types.py
+++ b/src/textual/css/types.py
@@ -25,6 +25,7 @@ EdgeType = Literal[
"hkey",
"vkey",
"tall",
+ "panel",
"wide",
]
Visibility = Literal["visible", "hidden", "initial", "inherit"]
diff --git a/src/textual/dom.py b/src/textual/dom.py
index 1e7282748..430ebeb43 100644
--- a/src/textual/dom.py
+++ b/src/textual/dom.py
@@ -765,6 +765,52 @@ class DOMNode(MessagePump):
)
return style
+ def _get_title_style_information(
+ self, background: Color
+ ) -> tuple[Color, Color, Style]:
+ """Get a Rich Style object for for titles.
+
+ Args:
+ background: The background color.
+
+ Returns:
+ A Rich style.
+
+ """
+ styles = self.styles
+ if styles.auto_border_title_color:
+ color = background.get_contrast_text(styles.border_title_color.a)
+ else:
+ color = styles.border_title_color
+ return (
+ color,
+ styles.border_title_background,
+ styles.border_title_style,
+ )
+
+ def _get_subtitle_style_information(
+ self, background: Color
+ ) -> tuple[Color, Color, Style]:
+ """Get a Rich Style object for for titles.
+
+ Args:
+ background: The background color.
+
+ Returns:
+ A Rich style.
+
+ """
+ styles = self.styles
+ if styles.auto_border_subtitle_color:
+ color = background.get_contrast_text(styles.border_subtitle_color.a)
+ else:
+ color = styles.border_subtitle_color
+ return (
+ color,
+ styles.border_subtitle_background,
+ styles.border_subtitle_style,
+ )
+
@property
def background_colors(self) -> tuple[Color, Color]:
"""The background color and the color of the parent's background.
diff --git a/tests/snapshot_tests/__snapshots__/test_snapshots.ambr b/tests/snapshot_tests/__snapshots__/test_snapshots.ambr
index b591ed28a..5cd124486 100644
--- a/tests/snapshot_tests/__snapshots__/test_snapshots.ambr
+++ b/tests/snapshot_tests/__snapshots__/test_snapshots.ambr
@@ -893,140 +893,141 @@
font-weight: 700;
}
- .terminal-3953159668-matrix {
+ .terminal-4039043553-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-3953159668-title {
+ .terminal-4039043553-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-3953159668-r1 { fill: #05080f }
- .terminal-3953159668-r2 { fill: #e1e1e1 }
- .terminal-3953159668-r3 { fill: #c5c8c6 }
- .terminal-3953159668-r4 { fill: #1e2226;font-weight: bold }
- .terminal-3953159668-r5 { fill: #35393d }
- .terminal-3953159668-r6 { fill: #454a50 }
- .terminal-3953159668-r7 { fill: #fea62b }
- .terminal-3953159668-r8 { fill: #e2e3e3;font-weight: bold }
- .terminal-3953159668-r9 { fill: #000000 }
- .terminal-3953159668-r10 { fill: #e2e3e3 }
+ .terminal-4039043553-r1 { fill: #05080f }
+ .terminal-4039043553-r2 { fill: #e1e1e1 }
+ .terminal-4039043553-r3 { fill: #c5c8c6 }
+ .terminal-4039043553-r4 { fill: #1e2226;font-weight: bold }
+ .terminal-4039043553-r5 { fill: #35393d }
+ .terminal-4039043553-r6 { fill: #454a50 }
+ .terminal-4039043553-r7 { fill: #fea62b }
+ .terminal-4039043553-r8 { fill: #e2e3e3;font-weight: bold }
+ .terminal-4039043553-r9 { fill: #000000 }
+ .terminal-4039043553-r10 { fill: #e2e3e3 }
+ .terminal-4039043553-r11 { fill: #14191f }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- BorderApp
+ BorderApp
-
-
-
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- ascii
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔+-------------------ascii--------------------+
- none||
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁||
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|I must not fear.|
- hidden|Fear is the mind-killer.|
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁|Fear is the little-death that brings |
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|total obliteration.|
- blank|I will face my fear.|
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁|I will permit it to pass over me and |
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|through me.|
- round|And when it has gone past, I will turn|
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁|the inner eye to see its path.|
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|Where the fear has gone there will be |
- solid|nothing. Only I will remain.|
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁||
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔||
- double+----------------------------------------------+
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- dashed
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+
+
+
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ ascii
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔+------------------- ascii --------------------+
+ none||
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁||
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|I must not fear.|
+ hidden|Fear is the mind-killer.|
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁|Fear is the little-death that brings |
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|total obliteration.|
+ blank|I will face my fear.|
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▅▅|I will permit it to pass over me and |
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|through me.|
+ round|And when it has gone past, I will turn|
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁|the inner eye to see its path.|
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔|Where the fear has gone there will be |
+ solid|nothing. Only I will remain.|
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁||
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔||
+ double+----------------------------------------------+
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ dashed
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
@@ -1901,246 +1902,246 @@
font-weight: 700;
}
- .terminal-1921368926-matrix {
+ .terminal-797557575-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-1921368926-title {
+ .terminal-797557575-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-1921368926-r1 { fill: #c5c8c6 }
- .terminal-1921368926-r2 { fill: #e1e1e1 }
- .terminal-1921368926-r3 { fill: #454a50 }
- .terminal-1921368926-r4 { fill: #e2e3e3;font-weight: bold }
- .terminal-1921368926-r5 { fill: #24292f;font-weight: bold }
- .terminal-1921368926-r6 { fill: #000000 }
- .terminal-1921368926-r7 { fill: #004578 }
- .terminal-1921368926-r8 { fill: #121212 }
- .terminal-1921368926-r9 { fill: #e2e3e3 }
- .terminal-1921368926-r10 { fill: #0053aa }
- .terminal-1921368926-r11 { fill: #dde8f3;font-weight: bold }
- .terminal-1921368926-r12 { fill: #ffff00;font-weight: bold }
- .terminal-1921368926-r13 { fill: #24292f }
+ .terminal-797557575-r1 { fill: #c5c8c6 }
+ .terminal-797557575-r2 { fill: #e1e1e1 }
+ .terminal-797557575-r3 { fill: #454a50 }
+ .terminal-797557575-r4 { fill: #e2e3e3;font-weight: bold }
+ .terminal-797557575-r5 { fill: #24292f;font-weight: bold }
+ .terminal-797557575-r6 { fill: #000000 }
+ .terminal-797557575-r7 { fill: #004578 }
+ .terminal-797557575-r8 { fill: #121212 }
+ .terminal-797557575-r9 { fill: #e2e3e3 }
+ .terminal-797557575-r10 { fill: #0053aa }
+ .terminal-797557575-r11 { fill: #dde8f3;font-weight: bold }
+ .terminal-797557575-r12 { fill: #ffff00;font-weight: bold }
+ .terminal-797557575-r13 { fill: #24292f }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- ContentSwitcherApp
+ ContentSwitcherApp
-
+
-
-
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- DataTableMarkdown
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ╭─────────────────────────────────────────╮
- │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
- │▎▋│
- │▎Three Flavours Cornetto▋│
- │▎▋│
- │▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔│
- │The Three Flavours Cornetto │
- │trilogy is an anthology series │
- │of Britishcomedic genre films │
- │directed by Edgar Wright.│
- ││
- │Shaun of the Dead│
- ││
- │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
- │▎▋│
- │▎UK ▋│
- │▎Release ▋│
- │▎FlavourDateDirector▋│
- │▎ ━━━━━━━━━━━━━━━━━━━━━━━━━━━ ▋│
- │▎Strawbe…2004-04…Edgar ▋│
- │▎Wright▋│
- │▎▋│
- │▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔│
- ││
- │Hot Fuzz│
- ││
- │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
- │▎▋│
- │▎UK ▋│
- │▎Release ▋│
- │▎FlavourDateDirector▋│
- │▎ ━━━━━━━━━━━━━━━━━━━━━━━━━━━ ▋│
- │▎Classico2007-02…Edgar ▋│
- │▎Wright▋│
- │▎▋│
- │▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔│
- ││
- │The World's End│
- ││
- │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
- │▎▋│
- │▎UK ▋│
- │▎Release ▋│
- │▎FlavourDateDirector▋│
- ╰─────────────────────────────────────────╯
+
+
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ DataTableMarkdown
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ╭─────────────────────────────────────────╮
+ │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
+ │▎▊│
+ │▎Three Flavours Cornetto▊│
+ │▎▊│
+ │▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔│
+ │The Three Flavours Cornetto │
+ │trilogy is an anthology series │
+ │of Britishcomedic genre films │
+ │directed by Edgar Wright.│
+ ││
+ │Shaun of the Dead│
+ ││
+ │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
+ │▎▊│
+ │▎UK ▊│
+ │▎Release ▊│
+ │▎FlavourDateDirector▊│
+ │▎ ━━━━━━━━━━━━━━━━━━━━━━━━━━━ ▊│
+ │▎Strawbe…2004-04…Edgar ▊│
+ │▎Wright▊│
+ │▎▊│
+ │▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔│
+ ││
+ │Hot Fuzz│
+ ││
+ │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
+ │▎▊│
+ │▎UK ▊│
+ │▎Release ▊│
+ │▎FlavourDateDirector▊│
+ │▎ ━━━━━━━━━━━━━━━━━━━━━━━━━━━ ▊│
+ │▎Classico2007-02…Edgar ▊│
+ │▎Wright▊│
+ │▎▊│
+ │▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔│
+ ││
+ │The World's End│
+ ││
+ │▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁│
+ │▎▊│
+ │▎UK ▊│
+ │▎Release ▊│
+ │▎FlavourDateDirector▊│
+ ╰─────────────────────────────────────────╯
@@ -3119,133 +3120,133 @@
font-weight: 700;
}
- .terminal-1917293938-matrix {
+ .terminal-1717278065-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-1917293938-title {
+ .terminal-1717278065-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-1917293938-r1 { fill: #c5c8c6 }
- .terminal-1917293938-r2 { fill: #0178d4 }
- .terminal-1917293938-r3 { fill: #e1e1e1 }
- .terminal-1917293938-r4 { fill: #1e1e1e }
+ .terminal-1717278065-r1 { fill: #c5c8c6 }
+ .terminal-1717278065-r2 { fill: #0178d4 }
+ .terminal-1717278065-r3 { fill: #e1e1e1 }
+ .terminal-1717278065-r4 { fill: #1e1e1e }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- AllBordersApp
+ AllBordersApp
-
+
-
- +------------------+┏╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┓
- |ascii|blank╏dashed╏
- +------------------+┗╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┛
-
-
- ╔══════════════════╗┏━━━━━━━━━━━━━━━━━━┓
- ║double║┃heavy┃hidden/none
- ╚══════════════════╝┗━━━━━━━━━━━━━━━━━━┛
-
-
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▗▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▖▛▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▜
- hkey▐inner▌▌outer▐
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▝▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▘▙▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▟
-
-
- ╭──────────────────╮┌──────────────────┐▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▎
- │round││solid│▊tall▎
- ╰──────────────────╯└──────────────────┘▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▎
-
-
- █▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀█▏▕▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- █thick█▏vkey▕▎wide▋
- █▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄█▏▕▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+
+ +------------------+┏╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┓
+ |ascii|blank╏dashed╏
+ +------------------+┗╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┛
+
+
+ ╔══════════════════╗┏━━━━━━━━━━━━━━━━━━┓
+ ║double║┃heavy┃hidden/none
+ ╚══════════════════╝┗━━━━━━━━━━━━━━━━━━┛
+
+
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▗▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▖▛▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▜
+ hkey▐inner▌▌outer▐
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▝▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▘▙▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▟
+
+
+ ╭──────────────────╮┌──────────────────┐▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▎
+ │round││solid│▊tall▎
+ ╰──────────────────╯└──────────────────┘▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▎
+
+
+ █▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀█▏▕▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ █thick█▏vkey▕▎wide▊
+ █▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄█▏▕▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
@@ -3276,141 +3277,141 @@
font-weight: 700;
}
- .terminal-3714773288-matrix {
+ .terminal-1997861159-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-3714773288-title {
+ .terminal-1997861159-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-3714773288-r1 { fill: #e1e1e1 }
- .terminal-3714773288-r2 { fill: #c5c8c6 }
- .terminal-3714773288-r3 { fill: #fea62b }
- .terminal-3714773288-r4 { fill: #fea62b;font-weight: bold }
- .terminal-3714773288-r5 { fill: #fea62b;font-weight: bold;font-style: italic; }
- .terminal-3714773288-r6 { fill: #cc555a;font-weight: bold }
- .terminal-3714773288-r7 { fill: #1e1e1e }
- .terminal-3714773288-r8 { fill: #1e1e1e;text-decoration: underline; }
- .terminal-3714773288-r9 { fill: #fea62b;text-decoration: underline; }
- .terminal-3714773288-r10 { fill: #4b4e55;text-decoration: underline; }
- .terminal-3714773288-r11 { fill: #4ebf71 }
- .terminal-3714773288-r12 { fill: #b93c5b }
+ .terminal-1997861159-r1 { fill: #e1e1e1 }
+ .terminal-1997861159-r2 { fill: #c5c8c6 }
+ .terminal-1997861159-r3 { fill: #fea62b }
+ .terminal-1997861159-r4 { fill: #fea62b;font-weight: bold }
+ .terminal-1997861159-r5 { fill: #fea62b;font-weight: bold;font-style: italic; }
+ .terminal-1997861159-r6 { fill: #cc555a;font-weight: bold }
+ .terminal-1997861159-r7 { fill: #1e1e1e }
+ .terminal-1997861159-r8 { fill: #1e1e1e;text-decoration: underline; }
+ .terminal-1997861159-r9 { fill: #fea62b;text-decoration: underline; }
+ .terminal-1997861159-r10 { fill: #4b4e55;text-decoration: underline; }
+ .terminal-1997861159-r11 { fill: #4ebf71 }
+ .terminal-1997861159-r12 { fill: #b93c5b }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- BorderSubTitleAlignAll
+ BorderSubTitleAlignAll
-
+
-
-
-
- ▏Border title▕╭─Lef…─╮▁▁▁▁▁Left▁▁▁▁▁
- ▏This is the story of▕│a Python│▎developer that▋
- ▏Border subtitle▕╰─Cen…─╯▔▔▔▔▔@@@▔▔▔▔▔▔
-
-
-
-
-
- +--------------+─Title─────────────────
- |had to fill up|nine labelsand ended up redoing it
- +-Left-------+──────────────Subtitle─
-
-
-
-
- ─Title, but really looo…─
- ─Title, but r…──Title, but reall…─
- because the first tryhad some labelsthat were too long.
- ─Subtitle, bu…──Subtitle, but re…─
- ─Subtitle, but really l…─
-
+
+
+
+ ▏Border title▕╭─Lef…─╮▁▁▁▁▁Left▁▁▁▁▁
+ ▏This is the story of▕│a Python│▎developer that▊
+ ▏Border subtitle▕╰─Cen…─╯▔▔▔▔▔@@@▔▔▔▔▔▔
+
+
+
+
+
+ +--------------+─Title─────────────────
+ |had to fill up|nine labelsand ended up redoing it
+ +-Left-------+──────────────Subtitle─
+
+
+
+
+ ─Title, but really looo…─
+ ─Title, but r…──Title, but reall…─
+ because the first tryhad some labelsthat were too long.
+ ─Subtitle, bu…──Subtitle, but re…─
+ ─Subtitle, but really l…─
+
@@ -3441,134 +3442,134 @@
font-weight: 700;
}
- .terminal-1044533580-matrix {
+ .terminal-1601354540-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-1044533580-title {
+ .terminal-1601354540-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-1044533580-r1 { fill: #e1e1e1 }
- .terminal-1044533580-r2 { fill: #c5c8c6 }
- .terminal-1044533580-r3 { fill: #fea62b }
- .terminal-1044533580-r4 { fill: #ffffff }
- .terminal-1044533580-r5 { fill: #1e1e1e }
+ .terminal-1601354540-r1 { fill: #e1e1e1 }
+ .terminal-1601354540-r2 { fill: #c5c8c6 }
+ .terminal-1601354540-r3 { fill: #fea62b }
+ .terminal-1601354540-r4 { fill: #ffffff }
+ .terminal-1601354540-r5 { fill: #1e1e1e }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- BorderSubtitleAlignApp
+ BorderSubtitleAlignApp
-
-
-
-
- ┌────────────────────────────────────────────────────────────────────────────┐
- ││
- │My subtitle is on the left.│
- ││
- └─< Left───────────────────────────────────────────────────────────────────┘
-
- ┏╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┓
- ╏╏
- ╏My subtitle is centered╏
- ╏╏
- ┗╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍Centered!╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┛
-
- ▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▎
- ▊▎
- ▊My subtitle is on the right▎
- ▊▎
- ▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁Right >▁▎
-
-
-
-
-
+
+
+
+
+ ┌────────────────────────────────────────────────────────────────────────────┐
+ ││
+ │My subtitle is on the left.│
+ ││
+ └─ < Left ───────────────────────────────────────────────────────────────────┘
+
+ ┏╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┓
+ ╏╏
+ ╏My subtitle is centered╏
+ ╏╏
+ ┗╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍ Centered! ╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┛
+
+ ▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▎
+ ▊▎
+ ▊My subtitle is on the right▎
+ ▊▎
+ ▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁ Right > ▁▎
+
+
+
+
+
@@ -3599,134 +3600,292 @@
font-weight: 700;
}
- .terminal-304237721-matrix {
+ .terminal-2047325817-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-304237721-title {
+ .terminal-2047325817-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-304237721-r1 { fill: #e1e1e1 }
- .terminal-304237721-r2 { fill: #c5c8c6 }
- .terminal-304237721-r3 { fill: #fea62b }
- .terminal-304237721-r4 { fill: #ffffff }
- .terminal-304237721-r5 { fill: #1e1e1e }
+ .terminal-2047325817-r1 { fill: #e1e1e1 }
+ .terminal-2047325817-r2 { fill: #c5c8c6 }
+ .terminal-2047325817-r3 { fill: #fea62b }
+ .terminal-2047325817-r4 { fill: #ffffff }
+ .terminal-2047325817-r5 { fill: #1e1e1e }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- BorderTitleAlignApp
+ BorderTitleAlignApp
-
-
-
-
- ┌─< Left───────────────────────────────────────────────────────────────────┐
- ││
- │My title is on the left.│
- ││
- └────────────────────────────────────────────────────────────────────────────┘
-
- ┏╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍Centered!╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┓
- ╏╏
- ╏My title is centered╏
- ╏╏
- ┗╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┛
-
- ▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔Right >▔▎
- ▊▎
- ▊My title is on the right▎
- ▊▎
- ▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▎
-
-
-
-
-
+
+
+
+
+ ┌─ < Left ───────────────────────────────────────────────────────────────────┐
+ ││
+ │My title is on the left.│
+ ││
+ └────────────────────────────────────────────────────────────────────────────┘
+
+ ┏╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍ Centered! ╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┓
+ ╏╏
+ ╏My title is centered╏
+ ╏╏
+ ┗╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍╍┛
+
+ ▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔ Right > ▔▎
+ ▊▎
+ ▊My title is on the right▎
+ ▊▎
+ ▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▎
+
+
+
+
+
+
+
+
+
+
+ '''
+# ---
+# name: test_css_property[border_title_colors.py]
+ '''
+
@@ -13410,169 +13569,169 @@
font-weight: 700;
}
- .terminal-832370059-matrix {
+ .terminal-1975973248-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-832370059-title {
+ .terminal-1975973248-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-832370059-r1 { fill: #c5c8c6 }
- .terminal-832370059-r2 { fill: #e3e3e3 }
- .terminal-832370059-r3 { fill: #e1e1e1 }
- .terminal-832370059-r4 { fill: #23568b }
- .terminal-832370059-r5 { fill: #e2e2e2 }
- .terminal-832370059-r6 { fill: #004578 }
- .terminal-832370059-r7 { fill: #14191f }
- .terminal-832370059-r8 { fill: #262626 }
- .terminal-832370059-r9 { fill: #e2e2e2;font-weight: bold;text-decoration: underline; }
- .terminal-832370059-r10 { fill: #e2e2e2;font-weight: bold }
- .terminal-832370059-r11 { fill: #7ae998 }
- .terminal-832370059-r12 { fill: #4ebf71;font-weight: bold }
- .terminal-832370059-r13 { fill: #008139 }
- .terminal-832370059-r14 { fill: #dde8f3;font-weight: bold }
- .terminal-832370059-r15 { fill: #ddedf9 }
+ .terminal-1975973248-r1 { fill: #c5c8c6 }
+ .terminal-1975973248-r2 { fill: #e3e3e3 }
+ .terminal-1975973248-r3 { fill: #e1e1e1 }
+ .terminal-1975973248-r4 { fill: #23568b }
+ .terminal-1975973248-r5 { fill: #e2e2e2 }
+ .terminal-1975973248-r6 { fill: #004578 }
+ .terminal-1975973248-r7 { fill: #14191f }
+ .terminal-1975973248-r8 { fill: #262626 }
+ .terminal-1975973248-r9 { fill: #e2e2e2;font-weight: bold;text-decoration: underline; }
+ .terminal-1975973248-r10 { fill: #e2e2e2;font-weight: bold }
+ .terminal-1975973248-r11 { fill: #7ae998 }
+ .terminal-1975973248-r12 { fill: #4ebf71;font-weight: bold }
+ .terminal-1975973248-r13 { fill: #008139 }
+ .terminal-1975973248-r14 { fill: #dde8f3;font-weight: bold }
+ .terminal-1975973248-r15 { fill: #ddedf9 }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- Textual Demo
+ Textual Demo
-
+
-
- ⭘Textual Demo
- ▅▅
-
- TOP
-
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▃▃
- ▎▋
- Widgets▎▋
- ▎Textual Demo▋
- ▎▋
- ▎Welcome! Textual is a framework for creating sophisticated▋
- Rich content▎applications with the terminal.▋
- ▎▋
- ▎▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▋
- ▎Start▋
- CSS▎▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▋
- ▎▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
-
-
-
-
-
-
-
-
-
-
- Widgets
- CTRL+C Quit CTRL+B Sidebar CTRL+T Toggle Dark mode CTRL+S Screenshot F1 Notes
+
+ ⭘Textual Demo
+ ▅▅
+
+ TOP
+
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▃▃
+ ▎▊
+ Widgets▎▊
+ ▎Textual Demo▊
+ ▎▊
+ ▎Welcome! Textual is a framework for creating sophisticated▊
+ Rich content▎applications with the terminal.▊
+ ▎▊
+ ▎▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▊
+ ▎Start▊
+ CSS▎▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▊
+ ▎▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+
+
+
+
+
+
+
+
+
+
+ Widgets
+ CTRL+C Quit CTRL+B Sidebar CTRL+T Toggle Dark mode CTRL+S Screenshot F1 Notes
@@ -14107,148 +14266,148 @@
font-weight: 700;
}
- .terminal-1506359380-matrix {
+ .terminal-391329861-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-1506359380-title {
+ .terminal-391329861-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-1506359380-r1 { fill: #454a50 }
- .terminal-1506359380-r2 { fill: #e1e1e1 }
- .terminal-1506359380-r3 { fill: #c5c8c6 }
- .terminal-1506359380-r4 { fill: #e2e3e3;font-weight: bold }
- .terminal-1506359380-r5 { fill: #262626 }
- .terminal-1506359380-r6 { fill: #000000 }
- .terminal-1506359380-r7 { fill: #e2e2e2 }
- .terminal-1506359380-r8 { fill: #e3e3e3 }
- .terminal-1506359380-r9 { fill: #14191f }
- .terminal-1506359380-r10 { fill: #b93c5b }
- .terminal-1506359380-r11 { fill: #121212 }
- .terminal-1506359380-r12 { fill: #1e1e1e }
- .terminal-1506359380-r13 { fill: #e2e3e3 }
- .terminal-1506359380-r14 { fill: #fea62b }
- .terminal-1506359380-r15 { fill: #211505;font-weight: bold }
- .terminal-1506359380-r16 { fill: #211505 }
- .terminal-1506359380-r17 { fill: #dde8f3;font-weight: bold }
- .terminal-1506359380-r18 { fill: #ddedf9 }
+ .terminal-391329861-r1 { fill: #454a50 }
+ .terminal-391329861-r2 { fill: #e1e1e1 }
+ .terminal-391329861-r3 { fill: #c5c8c6 }
+ .terminal-391329861-r4 { fill: #e2e3e3;font-weight: bold }
+ .terminal-391329861-r5 { fill: #262626 }
+ .terminal-391329861-r6 { fill: #000000 }
+ .terminal-391329861-r7 { fill: #e2e2e2 }
+ .terminal-391329861-r8 { fill: #e3e3e3 }
+ .terminal-391329861-r9 { fill: #14191f }
+ .terminal-391329861-r10 { fill: #b93c5b }
+ .terminal-391329861-r11 { fill: #121212 }
+ .terminal-391329861-r12 { fill: #1e1e1e }
+ .terminal-391329861-r13 { fill: #e2e3e3 }
+ .terminal-391329861-r14 { fill: #fea62b }
+ .terminal-391329861-r15 { fill: #211505;font-weight: bold }
+ .terminal-391329861-r16 { fill: #211505 }
+ .terminal-391329861-r17 { fill: #dde8f3;font-weight: bold }
+ .terminal-391329861-r18 { fill: #ddedf9 }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- EasingApp
+ EasingApp
-
+
-
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- round▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▎
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁Animation Duration:▊1.0▎
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▎
- out_sine
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- out_quint▏▎▋
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎Welcome to Textual!▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎▋
- out_quart▏▎I must not fear.▋
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎Fear is the ▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎mind-killer.▋
- out_quad▏▎Fear is the ▋
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎little-death that ▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎brings total ▋
- out_expo▏▎obliteration.▋▆▆
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎I will face my fear.▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎I will permit it to ▋
- out_elastic▏▎pass over me and ▋
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎through me.▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎And when it has gone ▋
- out_cubic▏
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁ CTRL+P Focus: Duration Input CTRL+B Toggle Dark
+
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ round▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▎
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁Animation Duration:▊1.0▎
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▎
+ out_sine
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ out_quint▏▎▊
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎Welcome to Textual!▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎▊
+ out_quart▏▎I must not fear.▊
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎Fear is the ▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎mind-killer.▊
+ out_quad▏▎Fear is the ▊
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎little-death that ▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎brings total ▊
+ out_expo▏▎obliteration.▊▆▆
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎I will face my fear.▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎I will permit it to ▊
+ out_elastic▏▎pass over me and ▊
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▏▎through me.▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▏▎And when it has gone ▊
+ out_cubic▏
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁ CTRL+P Focus: Duration Input CTRL+B Toggle Dark
@@ -17287,140 +17446,140 @@
font-weight: 700;
}
- .terminal-4078770422-matrix {
+ .terminal-1636374768-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-4078770422-title {
+ .terminal-1636374768-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-4078770422-r1 { fill: #e1e1e1 }
- .terminal-4078770422-r2 { fill: #121212 }
- .terminal-4078770422-r3 { fill: #c5c8c6 }
- .terminal-4078770422-r4 { fill: #0053aa }
- .terminal-4078770422-r5 { fill: #dde8f3;font-weight: bold }
- .terminal-4078770422-r6 { fill: #939393;font-weight: bold }
- .terminal-4078770422-r7 { fill: #24292f }
- .terminal-4078770422-r8 { fill: #e2e3e3;font-weight: bold }
- .terminal-4078770422-r9 { fill: #4ebf71;font-weight: bold }
- .terminal-4078770422-r10 { fill: #e1e1e1;font-style: italic; }
- .terminal-4078770422-r11 { fill: #e1e1e1;font-weight: bold }
+ .terminal-1636374768-r1 { fill: #e1e1e1 }
+ .terminal-1636374768-r2 { fill: #121212 }
+ .terminal-1636374768-r3 { fill: #c5c8c6 }
+ .terminal-1636374768-r4 { fill: #0053aa }
+ .terminal-1636374768-r5 { fill: #dde8f3;font-weight: bold }
+ .terminal-1636374768-r6 { fill: #939393;font-weight: bold }
+ .terminal-1636374768-r7 { fill: #24292f }
+ .terminal-1636374768-r8 { fill: #e2e3e3;font-weight: bold }
+ .terminal-1636374768-r9 { fill: #4ebf71;font-weight: bold }
+ .terminal-1636374768-r10 { fill: #e1e1e1;font-style: italic; }
+ .terminal-1636374768-r11 { fill: #e1e1e1;font-weight: bold }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- MarkdownExampleApp
+ MarkdownExampleApp
-
+
-
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ▎▋
- ▎Markdown Document▋
- ▎▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- This is an example of Textual's Markdown widget.
-
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ▎▋
- ▎Features▋
- ▎▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- Markdown syntax and extensions are supported.
-
- ● Typography emphasis, strong, inline code etc.
- ● Headers
- ● Lists (bullet and ordered)
- ● Syntax highlighted code blocks
- ● Tables!
-
-
-
-
+
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ▎▊
+ ▎Markdown Document▊
+ ▎▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ This is an example of Textual's Markdown widget.
+
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ▎▊
+ ▎Features▊
+ ▎▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ Markdown syntax and extensions are supported.
+
+ ● Typography emphasis, strong, inline code etc.
+ ● Headers
+ ● Lists (bullet and ordered)
+ ● Syntax highlighted code blocks
+ ● Tables!
+
+
+
+
@@ -17451,145 +17610,145 @@
font-weight: 700;
}
- .terminal-971113808-matrix {
+ .terminal-873465137-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-971113808-title {
+ .terminal-873465137-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-971113808-r1 { fill: #c5c8c6 }
- .terminal-971113808-r2 { fill: #24292f }
- .terminal-971113808-r3 { fill: #121212 }
- .terminal-971113808-r4 { fill: #e1e1e1 }
- .terminal-971113808-r5 { fill: #e2e3e3 }
- .terminal-971113808-r6 { fill: #96989b }
- .terminal-971113808-r7 { fill: #0053aa }
- .terminal-971113808-r8 { fill: #008139 }
- .terminal-971113808-r9 { fill: #dde8f3;font-weight: bold }
- .terminal-971113808-r10 { fill: #939393;font-weight: bold }
- .terminal-971113808-r11 { fill: #14191f }
- .terminal-971113808-r12 { fill: #e2e3e3;font-weight: bold }
- .terminal-971113808-r13 { fill: #4ebf71;font-weight: bold }
- .terminal-971113808-r14 { fill: #e1e1e1;font-style: italic; }
- .terminal-971113808-r15 { fill: #e1e1e1;font-weight: bold }
+ .terminal-873465137-r1 { fill: #c5c8c6 }
+ .terminal-873465137-r2 { fill: #24292f }
+ .terminal-873465137-r3 { fill: #121212 }
+ .terminal-873465137-r4 { fill: #e1e1e1 }
+ .terminal-873465137-r5 { fill: #e2e3e3 }
+ .terminal-873465137-r6 { fill: #96989b }
+ .terminal-873465137-r7 { fill: #0053aa }
+ .terminal-873465137-r8 { fill: #008139 }
+ .terminal-873465137-r9 { fill: #dde8f3;font-weight: bold }
+ .terminal-873465137-r10 { fill: #939393;font-weight: bold }
+ .terminal-873465137-r11 { fill: #14191f }
+ .terminal-873465137-r12 { fill: #e2e3e3;font-weight: bold }
+ .terminal-873465137-r13 { fill: #4ebf71;font-weight: bold }
+ .terminal-873465137-r14 { fill: #e1e1e1;font-style: italic; }
+ .terminal-873465137-r15 { fill: #e1e1e1;font-weight: bold }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- MarkdownExampleApp
+ MarkdownExampleApp
-
+
-
- ▋▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ▼ Ⅰ Markdown Viewer▋▎▋
- ├── Ⅱ Features▋▎Markdown Viewer▋
- ├── Ⅱ Tables▋▎▋
- └── Ⅱ Code Blocks▋▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- ▋This is an example of Textual's MarkdownViewer
- ▋widget.
- ▋
- ▋▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▅▅
- ▋▎▋
- ▋▎Features▋
- ▋▎▋
- ▋▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- ▋Markdown syntax and extensions are supported.
- ▋
- ▋● Typography emphasis, strong, inline code
- ▋etc.
- ▋● Headers
- ▋● Lists (bullet and ordered)
- ▋● Syntax highlighted code blocks
- ▋● Tables!
- ▋
- ▋▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ▋▎▋
+
+ ▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ▼ Ⅰ Markdown Viewer▊▎▊
+ ├── Ⅱ Features▊▎Markdown Viewer▊
+ ├── Ⅱ Tables▊▎▊
+ └── Ⅱ Code Blocks▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ ▊This is an example of Textual's MarkdownViewer
+ ▊widget.
+ ▊
+ ▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▅▅
+ ▊▎▊
+ ▊▎Features▊
+ ▊▎▊
+ ▊▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ ▊Markdown syntax and extensions are supported.
+ ▊
+ ▊● Typography emphasis, strong, inline code
+ ▊etc.
+ ▊● Headers
+ ▊● Lists (bullet and ordered)
+ ▊● Syntax highlighted code blocks
+ ▊● Tables!
+ ▊
+ ▊▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ▊▎▊
@@ -20181,135 +20340,134 @@
font-weight: 700;
}
- .terminal-1405474793-matrix {
+ .terminal-2499454553-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-1405474793-title {
+ .terminal-2499454553-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-1405474793-r1 { fill: #004578 }
- .terminal-1405474793-r2 { fill: #c5c8c6 }
- .terminal-1405474793-r3 { fill: #e1e1e1 }
- .terminal-1405474793-r4 { fill: #23568b }
- .terminal-1405474793-r5 { fill: #14191f }
+ .terminal-2499454553-r1 { fill: #004578 }
+ .terminal-2499454553-r2 { fill: #c5c8c6 }
+ .terminal-2499454553-r3 { fill: #e1e1e1 }
+ .terminal-2499454553-r4 { fill: #23568b }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- MyApp
+ MyApp
-
-
-
- ╭──────────────────────────────────────────────────────────────────────────────╮
- ││SPAM││
- ││SPAM││
- ││SPAM▂▂││
- ││SPAM││
- ││SPAM││
- ││SPAM││
- │╰──────────────────────────────────────────────────────────────────────────╯│
- │SPAM│
- │SPAM▆▆│
- │SPAM│
- │SPAM│
- │SPAM│
- │SPAM▁▁│
- │SPAM│
- │SPAM│
- │SPAM│
- │SPAM│
- │SPAM│
- │SPAM│
- │SPAM│
- │SPAM│
- │SPAM│
- ╰──────────────────────────────────────────────────────────────────────────────╯
+
+
+
+ ╭──────────────────────────────────────────────────────────────────────────────╮
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM│
+ │SPAM▆▆│
+ │SPAM│
+ ╰──────────────────────────────────────────────────────────────────────────────╯
@@ -20495,134 +20653,134 @@
font-weight: 700;
}
- .terminal-2452225303-matrix {
+ .terminal-1647606097-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-2452225303-title {
+ .terminal-1647606097-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-2452225303-r1 { fill: #c5c8c6 }
- .terminal-2452225303-r2 { fill: #e3e3e3 }
- .terminal-2452225303-r3 { fill: #ff0000 }
- .terminal-2452225303-r4 { fill: #dde2e8 }
- .terminal-2452225303-r5 { fill: #ddedf9 }
+ .terminal-1647606097-r1 { fill: #c5c8c6 }
+ .terminal-1647606097-r2 { fill: #e3e3e3 }
+ .terminal-1647606097-r3 { fill: #ff0000 }
+ .terminal-1647606097-r4 { fill: #dde2e8 }
+ .terminal-1647606097-r5 { fill: #ddedf9 }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- ScrollViewTester
+ ScrollViewTester
-
-
-
- ⭘ScrollViewTester
- ╭─1──────────────────────────────────────────────────────────────────────────╮
- │Welcome to line 980│
- │Welcome to line 981│
- │Welcome to line 982│
- │Welcome to line 983│
- │Welcome to line 984│
- │Welcome to line 985│
- │Welcome to line 986│
- │Welcome to line 987│
- │Welcome to line 988│
- │Welcome to line 989│
- │Welcome to line 990│
- │Welcome to line 991│
- │Welcome to line 992│
- │Welcome to line 993│
- │Welcome to line 994│
- │Welcome to line 995│
- │Welcome to line 996│
- │Welcome to line 997│
- │Welcome to line 998│
- │Welcome to line 999│
- ╰──────────────────────────────────────────────────────────────────────────────╯
+
+
+
+ ⭘ScrollViewTester
+ ╭─ 1 ──────────────────────────────────────────────────────────────────────────╮
+ │Welcome to line 980│
+ │Welcome to line 981│
+ │Welcome to line 982│
+ │Welcome to line 983│
+ │Welcome to line 984│
+ │Welcome to line 985│
+ │Welcome to line 986│
+ │Welcome to line 987│
+ │Welcome to line 988│
+ │Welcome to line 989│
+ │Welcome to line 990│
+ │Welcome to line 991│
+ │Welcome to line 992│
+ │Welcome to line 993│
+ │Welcome to line 994│
+ │Welcome to line 995│
+ │Welcome to line 996│
+ │Welcome to line 997│
+ │Welcome to line 998│
+ │Welcome to line 999│
+ ╰──────────────────────────────────────────────────────────────────────────────╯
@@ -20813,140 +20971,140 @@
font-weight: 700;
}
- .terminal-4003130388-matrix {
+ .terminal-1328081937-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
- .terminal-4003130388-title {
+ .terminal-1328081937-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
- .terminal-4003130388-r1 { fill: #c5c8c6 }
- .terminal-4003130388-r2 { fill: #737373 }
- .terminal-4003130388-r3 { fill: #e1e1e1;font-weight: bold }
- .terminal-4003130388-r4 { fill: #323232 }
- .terminal-4003130388-r5 { fill: #0178d4 }
- .terminal-4003130388-r6 { fill: #121212 }
- .terminal-4003130388-r7 { fill: #0053aa }
- .terminal-4003130388-r8 { fill: #dde8f3;font-weight: bold }
- .terminal-4003130388-r9 { fill: #e1e1e1 }
- .terminal-4003130388-r10 { fill: #ddedf9 }
+ .terminal-1328081937-r1 { fill: #c5c8c6 }
+ .terminal-1328081937-r2 { fill: #737373 }
+ .terminal-1328081937-r3 { fill: #e1e1e1;font-weight: bold }
+ .terminal-1328081937-r4 { fill: #323232 }
+ .terminal-1328081937-r5 { fill: #0178d4 }
+ .terminal-1328081937-r6 { fill: #121212 }
+ .terminal-1328081937-r7 { fill: #0053aa }
+ .terminal-1328081937-r8 { fill: #dde8f3;font-weight: bold }
+ .terminal-1328081937-r9 { fill: #e1e1e1 }
+ .terminal-1328081937-r10 { fill: #ddedf9 }
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
- TabbedApp
+ TabbedApp
-
+
-
-
- LetoJessicaPaul
- ━━━━━━━━╸━━━━━━━╺━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
-
- ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
- ▎▋
- ▎Lady Jessica▋
- ▎▋
- ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
- Bene Gesserit and concubine of Leto, and mother of Paul and Alia.
-
-
-
- PaulAlia
- ━╸━━━━╺━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
-
- First child
-
-
-
-
-
-
- L Leto J Jessica P Paul
+
+
+ LetoJessicaPaul
+ ━━━━━━━━╸━━━━━━━╺━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
+
+ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁
+ ▎▊
+ ▎Lady Jessica▊
+ ▎▊
+ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
+ Bene Gesserit and concubine of Leto, and mother of Paul and Alia.
+
+
+
+ PaulAlia
+ ━╸━━━━╺━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
+
+ First child
+
+
+
+
+
+
+ L Leto J Jessica P Paul
diff --git a/tests/test_border.py b/tests/test_border.py
index fe02d5e28..5d2518244 100644
--- a/tests/test_border.py
+++ b/tests/test_border.py
@@ -105,7 +105,7 @@ def test_render_border_label_empty_label_skipped(
assert [] == list(
render_border_label(
- Text(""),
+ (Text(""), Style()),
True,
"round",
width,
@@ -142,7 +142,7 @@ def test_render_border_label_skipped_if_narrow(
assert [] == list(
render_border_label(
- Text.from_markup(label),
+ (Text.from_markup(label), Style()),
True,
"round",
width,
@@ -180,11 +180,10 @@ def test_render_border_label_wide_plain(label: str):
True,
True,
)
- left, original_text, right = render_border_label(Text.from_markup(label), *args)
+ segments = render_border_label((Text.from_markup(label), Style()), *args)
+ (segment,) = segments
- assert left == _BLANK_SEGMENT
- assert right == _BLANK_SEGMENT
- assert original_text == Segment(label, _EMPTY_STYLE)
+ assert segment == Segment(f" {label} ", None)
@pytest.mark.parametrize(
@@ -200,7 +199,7 @@ def test_render_border_empty_text_with_markup(label: str):
"""Test label rendering if there is no text but some markup."""
assert [] == list(
render_border_label(
- Text.from_markup(label),
+ (Text.from_markup(label), Style()),
True,
"round",
999,
@@ -222,7 +221,7 @@ def test_render_border_label():
# Implicit test on the number of segments returned:
blank1, what, is_up, with_you, blank2 = render_border_label(
- Text.from_markup(label),
+ (Text.from_markup(label), Style()),
True,
"round",
9999,
@@ -251,7 +250,7 @@ def test_render_border_label():
assert with_you == expected_with_you
blank1, what, blank2 = render_border_label(
- Text.from_markup(label),
+ (Text.from_markup(label), Style()),
True,
"round",
5 + 4, # 5 where "What…" fits + 2 for the blank spaces + 2 for the corners.
diff --git a/tests/test_styles_cache.py b/tests/test_styles_cache.py
index e1cb37c65..6567de4ea 100644
--- a/tests/test_styles_cache.py
+++ b/tests/test_styles_cache.py
@@ -72,8 +72,8 @@ def test_border():
Color.parse("green"),
content.__getitem__,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
)
@@ -106,8 +106,8 @@ def test_padding():
Color.parse("green"),
content.__getitem__,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
)
@@ -141,8 +141,8 @@ def test_padding_border():
Color.parse("green"),
content.__getitem__,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
)
@@ -177,8 +177,8 @@ def test_outline():
Color.parse("green"),
content.__getitem__,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
)
@@ -208,8 +208,8 @@ def test_crop():
Color.parse("green"),
content.__getitem__,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
crop=Region(2, 2, 3, 3),
)
@@ -247,8 +247,8 @@ def test_dirty_cache() -> None:
Color.parse("green"),
get_content_line,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
)
assert rendered_lines == [0, 1, 2]
@@ -275,8 +275,8 @@ def test_dirty_cache() -> None:
Color.parse("green"),
get_content_line,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
)
assert rendered_lines == []
@@ -294,8 +294,8 @@ def test_dirty_cache() -> None:
Color.parse("green"),
get_content_line,
Console(),
- "",
- "",
+ None,
+ None,
content_size=Size(3, 3),
)
assert rendered_lines == [0, 1]