mirror of
https://github.com/Textualize/textual.git
synced 2025-10-17 02:38:12 +03:00
@@ -10,6 +10,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
|
|||||||
### Fixed
|
### Fixed
|
||||||
|
|
||||||
- Fixed container not resizing when a widget is removed https://github.com/Textualize/textual/issues/2007
|
- Fixed container not resizing when a widget is removed https://github.com/Textualize/textual/issues/2007
|
||||||
|
- Fixes issue where the horizontal scrollbar would be incorrectly enabled https://github.com/Textualize/textual/pull/2024
|
||||||
|
|
||||||
### Added
|
### Added
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
from textual.app import App
|
from textual.app import App
|
||||||
from textual.containers import Vertical
|
from textual.containers import Container
|
||||||
from textual.widgets import Label
|
from textual.widgets import Label
|
||||||
|
|
||||||
TEXT = """I must not fear.
|
TEXT = """I must not fear.
|
||||||
@@ -14,7 +14,7 @@ Where the fear has gone there will be nothing. Only I will remain.
|
|||||||
|
|
||||||
class ScrollbarApp(App):
|
class ScrollbarApp(App):
|
||||||
def compose(self):
|
def compose(self):
|
||||||
yield Vertical(Label(TEXT * 5), classes="panel")
|
yield Container(Label(TEXT * 5), classes="panel")
|
||||||
|
|
||||||
|
|
||||||
app = ScrollbarApp(css_path="scrollbar_size.css")
|
app = ScrollbarApp(css_path="scrollbar_size.css")
|
||||||
|
|||||||
@@ -1010,11 +1010,11 @@ class Widget(DOMNode):
|
|||||||
show_vertical = self.virtual_size.height > height
|
show_vertical = self.virtual_size.height > height
|
||||||
|
|
||||||
# When a single scrollbar is shown, the other dimension changes, so we need to recalculate.
|
# When a single scrollbar is shown, the other dimension changes, so we need to recalculate.
|
||||||
if show_vertical and not show_horizontal:
|
if overflow_x == "auto" and show_vertical and not show_horizontal:
|
||||||
show_horizontal = self.virtual_size.width > (
|
show_horizontal = self.virtual_size.width > (
|
||||||
width - styles.scrollbar_size_vertical
|
width - styles.scrollbar_size_vertical
|
||||||
)
|
)
|
||||||
if show_horizontal and not show_vertical:
|
if overflow_y == "auto" and show_horizontal and not show_vertical:
|
||||||
show_vertical = self.virtual_size.height > (
|
show_vertical = self.virtual_size.height > (
|
||||||
height - styles.scrollbar_size_horizontal
|
height - styles.scrollbar_size_horizontal
|
||||||
)
|
)
|
||||||
|
|||||||
File diff suppressed because one or more lines are too long
189
tests/snapshot_tests/snapshot_apps/auto-table.py
Normal file
189
tests/snapshot_tests/snapshot_apps/auto-table.py
Normal file
@@ -0,0 +1,189 @@
|
|||||||
|
from os import urandom
|
||||||
|
from random import randrange
|
||||||
|
|
||||||
|
from textual.app import App
|
||||||
|
from textual.containers import Container, Horizontal, Vertical
|
||||||
|
from textual.screen import Screen
|
||||||
|
from textual.widgets import DataTable, Header, Label
|
||||||
|
|
||||||
|
|
||||||
|
class LabeledBox(Container):
|
||||||
|
DEFAULT_CSS = """
|
||||||
|
LabeledBox {
|
||||||
|
layers: base_ top_;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
LabeledBox > Container {
|
||||||
|
layer: base_;
|
||||||
|
border: round $primary;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
layout: vertical;
|
||||||
|
}
|
||||||
|
|
||||||
|
LabeledBox > Label {
|
||||||
|
layer: top_;
|
||||||
|
offset-x: 2;
|
||||||
|
}
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __init__(self, title, *args, **kwargs):
|
||||||
|
self.__label = Label(title)
|
||||||
|
|
||||||
|
super().__init__(self.__label, Container(*args, **kwargs))
|
||||||
|
|
||||||
|
@property
|
||||||
|
def label(self):
|
||||||
|
return self.__label
|
||||||
|
|
||||||
|
|
||||||
|
class StatusTable(DataTable):
|
||||||
|
def __init__(self):
|
||||||
|
super().__init__()
|
||||||
|
|
||||||
|
self.cursor_type = "row"
|
||||||
|
self.show_cursor = False
|
||||||
|
self.add_column("Foo")
|
||||||
|
self.add_column("Bar")
|
||||||
|
self.add_column("Baz")
|
||||||
|
|
||||||
|
for _ in range(50):
|
||||||
|
self.add_row(
|
||||||
|
"ABCDEFGH",
|
||||||
|
"0123456789",
|
||||||
|
"IJKLMNOPQRSTUVWXYZ",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
class Status(LabeledBox):
|
||||||
|
DEFAULT_CSS = """
|
||||||
|
Status {
|
||||||
|
width: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
Status Container {
|
||||||
|
width: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
Status StatusTable {
|
||||||
|
width: auto;
|
||||||
|
margin-top: 1;
|
||||||
|
scrollbar-gutter: stable;
|
||||||
|
overflow-x: hidden;
|
||||||
|
}
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __init__(self, name: str):
|
||||||
|
self.__name = name
|
||||||
|
self.__table = StatusTable()
|
||||||
|
|
||||||
|
super().__init__(f" {self.__name} ", self.__table)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def name(self) -> str:
|
||||||
|
return self.__name
|
||||||
|
|
||||||
|
@property
|
||||||
|
def table(self) -> StatusTable:
|
||||||
|
return self.__table
|
||||||
|
|
||||||
|
|
||||||
|
class Rendering(LabeledBox):
|
||||||
|
DEFAULT_CSS = """
|
||||||
|
#issue-info {
|
||||||
|
height: auto;
|
||||||
|
border-bottom: dashed #632CA6;
|
||||||
|
}
|
||||||
|
|
||||||
|
#statuses-box {
|
||||||
|
height: 1fr;
|
||||||
|
width: auto;
|
||||||
|
}
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __init__(self):
|
||||||
|
self.__info = Label("test")
|
||||||
|
|
||||||
|
super().__init__(
|
||||||
|
"",
|
||||||
|
Container(
|
||||||
|
Horizontal(self.__info, id="issue-info"),
|
||||||
|
Horizontal(*[Status(str(i)) for i in range(4)], id="statuses-box"),
|
||||||
|
id="issues-box",
|
||||||
|
),
|
||||||
|
)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def info(self) -> Label:
|
||||||
|
return self.__info
|
||||||
|
|
||||||
|
|
||||||
|
class Sidebar(LabeledBox):
|
||||||
|
DEFAULT_CSS = """
|
||||||
|
#sidebar-status {
|
||||||
|
height: auto;
|
||||||
|
border-bottom: dashed #632CA6;
|
||||||
|
}
|
||||||
|
|
||||||
|
#sidebar-options {
|
||||||
|
height: 1fr;
|
||||||
|
}
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __init__(self):
|
||||||
|
self.__status = Label("ok")
|
||||||
|
self.__options = Vertical()
|
||||||
|
|
||||||
|
super().__init__(
|
||||||
|
"",
|
||||||
|
Container(self.__status, id="sidebar-status"),
|
||||||
|
Container(self.__options, id="sidebar-options"),
|
||||||
|
)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def status(self) -> Label:
|
||||||
|
return self.__status
|
||||||
|
|
||||||
|
@property
|
||||||
|
def options(self) -> Vertical:
|
||||||
|
return self.__options
|
||||||
|
|
||||||
|
|
||||||
|
class MyScreen(Screen):
|
||||||
|
DEFAULT_CSS = """
|
||||||
|
#main-content {
|
||||||
|
layout: grid;
|
||||||
|
grid-size: 2;
|
||||||
|
grid-columns: 1fr 5fr;
|
||||||
|
grid-rows: 1fr;
|
||||||
|
}
|
||||||
|
|
||||||
|
#main-content-sidebar {
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
#main-content-rendering {
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
"""
|
||||||
|
|
||||||
|
def compose(self):
|
||||||
|
yield Header()
|
||||||
|
yield Container(
|
||||||
|
Container(Sidebar(), id="main-content-sidebar"),
|
||||||
|
Container(Rendering(), id="main-content-rendering"),
|
||||||
|
id="main-content",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
class MyApp(App):
|
||||||
|
async def on_mount(self):
|
||||||
|
self.install_screen(MyScreen(), "myscreen")
|
||||||
|
await self.push_screen("myscreen")
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
app = MyApp()
|
||||||
|
app.run()
|
||||||
@@ -17,7 +17,6 @@ from textual.widgets import (
|
|||||||
|
|
||||||
|
|
||||||
class WidgetDisableTestApp(App[None]):
|
class WidgetDisableTestApp(App[None]):
|
||||||
|
|
||||||
CSS = """
|
CSS = """
|
||||||
Horizontal {
|
Horizontal {
|
||||||
height: auto;
|
height: auto;
|
||||||
|
|||||||
@@ -305,3 +305,7 @@ def test_remove_with_auto_height(snap_compare):
|
|||||||
assert snap_compare(
|
assert snap_compare(
|
||||||
SNAPSHOT_APPS_DIR / "remove_auto.py", press=["a", "a", "a", "d", "d"]
|
SNAPSHOT_APPS_DIR / "remove_auto.py", press=["a", "a", "a", "d", "d"]
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def test_auto_table(snap_compare):
|
||||||
|
assert snap_compare(SNAPSHOT_APPS_DIR / "auto-table.py", terminal_size=(120, 40))
|
||||||
|
|||||||
Reference in New Issue
Block a user