TCSS spillover #5346
-
Description: Expected Behavior: Actual Behavior: Environment:
from textual import on
from textual.app import App, ComposeResult
from textual.widgets import Button, Label, Placeholder
from textual.containers import Vertical
from textual.screen import Screen
from textual.containers import (
Horizontal,
Vertical,
)
class Screen1(Screen):
"""Screen to create a new configuration for the application."""
CSS_PATH = "first.tcss"
def compose(self) -> ComposeResult:
with Vertical():
yield Label("Welcome to the first screen")
yield Button("Dummy Button")
yield Button("Dummy Button")
yield Horizontal(
Button.error("Cancel", id="cancel"),
)
@on(Button.Pressed, "#cancel")
def on_button_pressed(self, event: Button.Pressed) -> None:
self.app.pop_screen()
class Screen2(Screen):
CSS_PATH = "second.tcss"
def compose(self) -> ComposeResult:
with Vertical():
yield Label("Welcome to the second screen")
yield Button("Dummy Button")
yield Button("Dummy Button")
yield Horizontal(
Button.error("Cancel", id="cancel"),
)
@on(Button.Pressed, "#cancel")
def on_button_pressed(self, event: Button.Pressed) -> None:
self.app.pop_screen()
class MainScreen(Screen):
"""Main Screen of the application"""
def compose(self) -> ComposeResult:
yield Vertical(
Label("Welcome to MainScreen!"),
Button("Button 1", id="button-1"),
Button("Button 2", id="button-2"),
)
def on_button_pressed(self, event: Button.Pressed) -> None:
match event.button.id:
case "button-1":
self.app.push_screen("screen-1")
case "button-2":
self.app.push_screen("screen-2")
class MainApp(App):
"""Main Application"""
CSS_PATH = "app.tcss"
SCREENS = {
"main": MainScreen,
"screen-1": Screen1,
"screen-2": Screen2,
}
async def on_mount(self) -> None:
"""Set the initial screen."""
await self.push_screen("main")
if __name__ == "__main__":
MainApp().run()
Screen{
align: center middle;
content-align: center middle;
background: gray;
}
Screen > Vertical{
width: auto;
height: auto;
align: center middle;
content-align: center middle;
background: black;
}
Screen > Vertical > Button{
width: 30;
height: auto;
margin: 1 1;
background: gray;
}
Screen > Vertical > Label {
min-width: 1fr;
height: auto;
align: center middle;
content-align: center middle;
}
Screen{
align: center middle;
content-align: center middle;
}
Screen > Vertical{
width: auto;
height: auto;
align: center middle;
content-align: center middle;
}
Screen > Vertical > Button{
width: 30;
height: auto;
margin: 1 1;
background: green;
}
Screen > Vertical > Label {
min-width: 1fr;
height: auto;
align: center middle;
content-align: center middle;
}
Screen {
layout: grid;
grid-size: 3 4;
grid-rows: 1fr;
grid-columns: 1fr;
grid-gutter: 1;
}
Screen > Vertical{
width: auto;
height: auto;
align: center middle;
content-align: center middle;
}
Screen > Vertical > Button{
width: 30;
height: auto;
margin: 1 1;
background: blue;
}
Screen > Vertical > Label {
min-width: 1fr;
height: auto;
align: center middle;
content-align: center middle;
} |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 2 replies
-
I think this is unfortunately a footgun that discussed in #2744 and also noted in the docs, where the screen CSS actually applies to the whole app. The workaround is simply scoping the CSS to your specific screen - i.e. |
Beta Was this translation helpful? Give feedback.
No problem, I probably just spend too much time lurking in the repo!
I linked to that PR (which added the
CSS
andCSS_PATH
to screens) just for context that the Textual maintainers recognized this might be a footgun. This obviously has the benefit of splitting up your CSS files, but you need to know to limit the scope to your specific screen. I agree that this probably could be better documented, or ideally remove this footgun!