diff --git a/sandbox/will/basic.css b/sandbox/will/basic.css index d0406b4e9..ff16021de 100644 --- a/sandbox/will/basic.css +++ b/sandbox/will/basic.css @@ -2,10 +2,10 @@ - * { + /* * { transition: color 300ms linear, background 300ms linear; } - + */ *:hover { /* tint: 30% red; diff --git a/src/textual/_compositor.py b/src/textual/_compositor.py index 86f8fe7ba..b44d83190 100644 --- a/src/textual/_compositor.py +++ b/src/textual/_compositor.py @@ -609,6 +609,7 @@ class Compositor: Returns: SegmentLines: A renderable """ + width, height = self.size screen_region = Region(0, 0, width, height) @@ -706,7 +707,7 @@ class Compositor: region, clip = self.regions[widget] offset = region.offset intersection = clip.intersection - for dirty_region in widget.get_dirty_regions(): + for dirty_region in widget._exchange_repaint_regions(): update_region = intersection(dirty_region.translate(offset)) if update_region: add_region(update_region) diff --git a/src/textual/scroll_view.py b/src/textual/scroll_view.py index ffeca2421..8312be117 100644 --- a/src/textual/scroll_view.py +++ b/src/textual/scroll_view.py @@ -40,16 +40,6 @@ class ScrollView(Widget): """Not transparent, i.e. renders something.""" return False - def get_dirty_regions(self) -> Collection[Region]: - """Get regions which require a repaint. - - Returns: - Collection[Region]: Regions to repaint. - """ - regions = self._dirty_regions.copy() - self._dirty_regions.clear() - return regions - def on_mount(self): self._refresh_scrollbars() diff --git a/src/textual/widget.py b/src/textual/widget.py index 2e8247fce..74ffa4884 100644 --- a/src/textual/widget.py +++ b/src/textual/widget.py @@ -106,7 +106,10 @@ class Widget(DOMNode): self._horizontal_scrollbar: ScrollBar | None = None self._render_cache = RenderCache(Size(0, 0), []) + # Regions which need to be updated (in Widget) self._dirty_regions: set[Region] = set() + # Regions which need to be transferred from cache to screen + self._repaint_regions: set[Region] = set() # Cache the auto content dimensions # TODO: add mechanism to explicitly clear this @@ -549,24 +552,27 @@ class Widget(DOMNode): *regions (Region): Regions which require a repaint. """ - if regions: content_offset = self.content_offset widget_regions = [region.translate(content_offset) for region in regions] self._dirty_regions.update(widget_regions) + self._repaint_regions.update(widget_regions) self._styles_cache.set_dirty(*widget_regions) else: self._dirty_regions.clear() + self._repaint_regions.clear() self._styles_cache.clear() self._dirty_regions.add(self.outer_size.region) + self._repaint_regions.add(self.outer_size.region) - def get_dirty_regions(self) -> Collection[Region]: - """Get regions which require a repaint. + def _exchange_repaint_regions(self) -> Collection[Region]: + """Get a copy of the regions which need a repaint, and clear internal cache. Returns: Collection[Region]: Regions to repaint. """ - regions = self._dirty_regions.copy() + regions = self._repaint_regions.copy() + self._repaint_regions.clear() return regions def scroll_to( @@ -956,10 +962,10 @@ class Widget(DOMNode): """Render the widget in to lines. Args: - crop (Region): Region within visible area to. + crop (Region): Region within visible area to render. Returns: - Lines: A list of list of segments + Lines: A list of list of segments. """ lines = self._styles_cache.render_widget(self, crop) return lines