Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/toad/keymap.py
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,7 @@ def capture(cls, modes: tuple[type[KeyMode], ...]) -> KeymapCatalog:
for binding in declaration.exclusive_bindings(native_mode))
owned = [application]
for owner in DOMNode.contexts():
defaults = (*owner.declared_bindings(native_mode),
defaults = (*(binding for _, binding in owner.binding_defaults(native_mode)),
*owner.editor_command_bindings(native_mode))
if not issubclass(owner, ModalScreen):
defaults = (*defaults, *application)
Expand Down
7 changes: 4 additions & 3 deletions src/toad/screens/keymap.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
from textual import on
from textual.app import ComposeResult
from textual.containers import Horizontal, Vertical
from textual.keys import KeyInvocation
from textual.widgets import Button, Checkbox, DataTable, Input, Static
from textual.document._editing import EditingMode

Expand Down Expand Up @@ -70,15 +69,17 @@ def populate(self, term: str) -> None:
table.clear()
focused_only = self.query_one("#keymap-focused", Checkbox).value
self.visible_declarations = tuple(declaration for declaration in self.declarations
if (not focused_only or KeyInvocation.in_mode(declaration, self.focus_mode) in self.focused_ids)
if (not focused_only or self.catalog.require(declaration).visible_for_focus(
self.focus_mode, self.focused_ids))
and term.casefold() in (self.catalog.require(declaration).key_title() + " "
+ self.catalog.require(declaration).key_summary()).casefold())
keymap = self.app.settings.ui.keymap
conflicts = {row.binding_id for mode in self.modes for conflict in keymap.conflicts(mode)
for row in (conflict.first, conflict.second)}
for declaration in self.visible_declarations:
title = Text(self.catalog.require(declaration).key_title(),
style="" if KeyInvocation.in_mode(declaration, self.focus_mode) in self.focused_ids else "dim")
style="" if self.catalog.require(declaration).visible_for_focus(
self.focus_mode, self.focused_ids) else "dim")
table.add_row(title, *(Text(", ".join(self.catalog.effective(row, keymap)) or "—",
style="bold red" if row.binding_id in conflicts else "")
for mode in self.modes for row in (KeymapRow(declaration, mode),)))
Expand Down
18 changes: 10 additions & 8 deletions src/toad/widget_actions.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
from agent_comms.command import Command
from agent_comms.declared_family import DeclaredFamily
from agent_comms.field_codec import FieldCodec, FieldPlan
from textual.binding import Binding, CommandBinding, ModeBinding
from textual.binding import Binding, BindingsMap, CommandBinding, ModeBinding
from textual import events
from textual._activation import PrimaryActivation
from textual._callback import invoke
Expand Down Expand Up @@ -73,27 +73,27 @@ def bindings(cls) -> tuple[Binding, ...]:
@classmethod
def mode_binding(cls, mode: type[EditingMode], key: str) -> ModeBinding:
command = cls.command_for_key(mode, key)
return cls.command_binding(mode, key, command, mode)
return cls.command_binding(mode, key, command)

@classmethod
def command_binding(cls, capability: type[EditingMode], key: str, command: Self,
mode: type[EditingMode]) -> ModeBinding:
def command_binding(cls, capability: type[EditingMode], key: str, command: Self) -> ModeBinding:
return CommandBinding(
key=key, action=command, description=cls.title,
available=command.key_available, mode=capability,
tooltip=cls.summary(), show=cls.show, priority=cls.priority,
system=cls.system, group=cls.group, key_display=cls.key_display,
id=command.binding_identity(mode),
)

@classmethod
def bindings_for(cls, mode: type[EditingMode]) -> tuple[Binding, ...]:
"""The nearest declared capability supplies defaults; identity follows active mode."""
for capability in mode.__mro__:
if capability in cls.keys:
return tuple(cls.command_binding(capability, key,
cls.command_for_key(capability, key), mode)
for key in cls.keys[capability])
return tuple(binding for _, binding in BindingsMap(
cls.command_binding(capability, key,
cls.command_for_key(capability, key))
for key in cls.keys[capability]
).project(mode))
return ()

@classmethod
Expand Down Expand Up @@ -196,6 +196,8 @@ class VimWorkspaceAction(ApplicationAction, declared_name=None):
priority = True

def key_available(self, app):
if app.current_mode != "workspace":
return False
return (app.screen is app.workspace_screen
and app.screen.allows_application_commands)

Expand Down
Loading