From 577ef6bd255506e9f9a63db40135dc6057c79533 Mon Sep 17 00:00:00 2001 From: Will McGugan Date: Wed, 25 Aug 2021 20:20:51 +0100 Subject: [PATCH] version bump --- CHANGELOG.md | 2 +- docs/examples/actions/colorizer.py | 2 +- examples/code_viewer.py | 2 +- src/textual/binding.py | 2 +- src/textual/geometry.py | 1 - src/textual/message_pump.py | 6 ++-- src/textual/messages.py | 4 +-- src/textual/views/_window_view.py | 7 ++++- src/textual/widget.py | 11 ++----- src/textual/widgets/_tree_control.py | 44 +++++++++++----------------- 10 files changed, 32 insertions(+), 49 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 79592cc96..ce1a09e93 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,7 +5,7 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](http://keepachangelog.com/) and this project adheres to [Semantic Versioning](http://semver.org/). -## [0.1.10] - Unreleased +## [0.1.10] - 2021-08-25 ### Added diff --git a/docs/examples/actions/colorizer.py b/docs/examples/actions/colorizer.py index 4034f7a8d..f0c3cc0f0 100644 --- a/docs/examples/actions/colorizer.py +++ b/docs/examples/actions/colorizer.py @@ -7,7 +7,7 @@ class Colorizer(App): await self.bind("g", "color('green')") await self.bind("b", "color('blue')") - async def action_color(self, color: str) -> None: + def action_color(self, color: str) -> None: self.background = f"on {color}" diff --git a/examples/code_viewer.py b/examples/code_viewer.py index 5b044ca42..132156e1c 100644 --- a/examples/code_viewer.py +++ b/examples/code_viewer.py @@ -41,7 +41,7 @@ class MyApp(App): # Note the directory is also in a scroll view await self.view.dock( - ScrollView(self.directory), edge="left", size=64, name="sidebar" + ScrollView(self.directory), edge="left", size=48, name="sidebar" ) await self.view.dock(self.body, edge="top") diff --git a/src/textual/binding.py b/src/textual/binding.py index f5ec828a2..eeaf7e22e 100644 --- a/src/textual/binding.py +++ b/src/textual/binding.py @@ -44,7 +44,7 @@ class Bindings: description, show=show, key_display=key_display, - allow_forward=True, + allow_forward=allow_forward, ) def get_key(self, key: str) -> Binding: diff --git a/src/textual/geometry.py b/src/textual/geometry.py index ff124280c..5f7bd1444 100644 --- a/src/textual/geometry.py +++ b/src/textual/geometry.py @@ -189,7 +189,6 @@ class Region(NamedTuple): Returns: tuple[int, int]: [description] """ - return (self.x, self.x + self.width) return (self.y, self.y + self.height) @property diff --git a/src/textual/message_pump.py b/src/textual/message_pump.py index 820696396..c8e216e4e 100644 --- a/src/textual/message_pump.py +++ b/src/textual/message_pump.py @@ -3,12 +3,9 @@ from __future__ import annotations import asyncio from asyncio import CancelledError from asyncio import Queue, QueueEmpty, Task -import inspect from typing import TYPE_CHECKING, Awaitable, Iterable, Callable from weakref import WeakSet -from rich.traceback import Traceback - from . import events from . import log from ._timer import Timer, TimerCallback @@ -174,7 +171,7 @@ class MessagePump: except CancelledError: pass finally: - self._runnning = False + self._running = False async def _process_messages(self) -> None: """Process messages until the queue is closed.""" @@ -195,6 +192,7 @@ class MessagePump: pending = self.peek_message() if pending is None or not message.can_replace(pending): break + # self.log(message, "replaced with", pending) try: message = await self.get_message() except MessagePumpClosed: diff --git a/src/textual/messages.py b/src/textual/messages.py index 290d49f76..f207c18f3 100644 --- a/src/textual/messages.py +++ b/src/textual/messages.py @@ -34,9 +34,7 @@ class UpdateMessage(Message, verbosity=3): @rich.repr.auto class LayoutMessage(Message, verbosity=3): def can_replace(self, message: Message) -> bool: - return isinstance( - message, LayoutMessage - ) # or isinstance(message, UpdateMessage) + return isinstance(message, LayoutMessage) @rich.repr.auto diff --git a/src/textual/views/_window_view.py b/src/textual/views/_window_view.py index 82eae136d..d8ae4dca2 100644 --- a/src/textual/views/_window_view.py +++ b/src/textual/views/_window_view.py @@ -13,7 +13,8 @@ from ..widgets import Static class WindowChange(Message): - pass + def can_replace(self, message: Message) -> bool: + return isinstance(message, WindowChange) class WindowView(View, layout=VerticalLayout): @@ -39,6 +40,10 @@ class WindowView(View, layout=VerticalLayout): self.refresh(layout=True) await self.emit(WindowChange(self)) + async def message_update(self, message: UpdateMessage) -> None: + message.prevent_default() + await self.emit(WindowChange(self)) + async def watch_virtual_size(self, size: Size) -> None: await self.emit(WindowChange(self)) diff --git a/src/textual/widget.py b/src/textual/widget.py index db9dbe1c2..42ebf994f 100644 --- a/src/textual/widget.py +++ b/src/textual/widget.py @@ -206,17 +206,10 @@ class Widget(MessagePump): self.render_cache = RenderCache(Size(width, len(lines)), lines) def _get_lines(self) -> Lines: - """Get render lines for given dimensions. - - Args: - width (int): [description] - height (int): [description] - - Returns: - Lines: [description] - """ + """Get segment lines to render the widget.""" if self.render_cache is None: self.render_lines() + assert self.render_cache is not None lines = self.render_cache.lines return lines diff --git a/src/textual/widgets/_tree_control.py b/src/textual/widgets/_tree_control.py index 0203baab0..f4c38f45c 100644 --- a/src/textual/widgets/_tree_control.py +++ b/src/textual/widgets/_tree_control.py @@ -35,7 +35,7 @@ class TreeNode(Generic[NodeDataType]): data: NodeDataType, ) -> None: self.parent = parent - self._node_id = node_id + self.id = node_id self._control = control self._tree = tree self.label = label @@ -46,10 +46,6 @@ class TreeNode(Generic[NodeDataType]): self._tree.expanded = False self.children: list[TreeNode] = [] - @property - def id(self) -> NodeID: - return self._node_id - @property def control(self) -> TreeControl: return self._control @@ -150,8 +146,8 @@ class TreeNode(Generic[NodeDataType]): await self.expand(not self._expanded) async def add(self, label: TextType, data: NodeDataType) -> None: - await self._control.add(self._node_id, label, data=data) - self._control.refresh() + await self._control.add(self.id, label, data=data) + self._control.refresh(layout=True) self._empty = False def __rich__(self) -> RenderableType: @@ -175,29 +171,29 @@ class TreeControl(Generic[NodeDataType], Widget): ) -> None: self.data = data - self._node_id = NodeID(0) + self.id = NodeID(0) self.nodes: dict[NodeID, TreeNode[NodeDataType]] = {} self._tree = Tree(label) self.root: TreeNode[NodeDataType] = TreeNode( - None, self._node_id, self, self._tree, label, data + None, self.id, self, self._tree, label, data ) self._tree.label = self.root - self.nodes[NodeID(self._node_id)] = self.root + self.nodes[NodeID(self.id)] = self.root super().__init__(name=name) self.padding = padding hover_node: Reactive[NodeID | None] = Reactive(None) - cursor: Reactive[NodeID] = Reactive(NodeID(0)) + cursor: Reactive[NodeID] = Reactive(NodeID(0), layout=True) cursor_line: Reactive[int] = Reactive(0, repaint=False) - show_cursor: Reactive[bool] = Reactive(False) + show_cursor: Reactive[bool] = Reactive(False, layout=True) def watch_show_cursor(self, value: bool) -> None: self.emit_no_wait(CursorMoveMessage(self, self.cursor_line)) - async def watch_cursor_line(self, value: int) -> None: + def watch_cursor_line(self, value: int) -> None: if self.show_cursor: - await self.emit(CursorMoveMessage(self, value + self.gutter.top)) + self.emit_no_wait(CursorMoveMessage(self, value + self.gutter.top)) async def add( self, @@ -206,14 +202,14 @@ class TreeControl(Generic[NodeDataType], Widget): data: NodeDataType, ) -> None: parent = self.nodes[node_id] - self._node_id = NodeID(self._node_id + 1) + self.id = NodeID(self.id + 1) child_tree = parent._tree.add(label) child_node: TreeNode[NodeDataType] = TreeNode( - parent, self._node_id, self, child_tree, label, data + parent, self.id, self, child_tree, label, data ) parent.children.append(child_node) child_tree.label = child_node - self.nodes[self._node_id] = child_node + self.nodes[self.id] = child_node self.refresh(layout=True) @@ -221,16 +217,10 @@ class TreeControl(Generic[NodeDataType], Widget): """Find the line location for the cursor node.""" node_id = self.cursor - node = self.root line = 0 - stack: list[Iterator[TreeNode[NodeDataType]]] = [] - - if node.id == node_id: - return line - - if node.expanded and node.children: - stack.append(iter(node.children)) + stack: list[Iterator[TreeNode[NodeDataType]]] + stack = [iter([self.root])] pop = stack.pop push = stack.append @@ -241,11 +231,11 @@ class TreeControl(Generic[NodeDataType], Widget): except StopIteration: continue else: - line += 1 if node.id == node_id: return line + line += 1 push(iter_children) - if node.expanded and node.children: + if node.children and node.expanded: push(iter(node.children)) return None