feat: add appearance and keyboard shortcut settings - #397
Conversation
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 266bf1f808
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| return [ | ||
| event.ctrlKey || event.metaKey ? "Ctrl" : null, | ||
| event.altKey ? "Alt" : null, |
There was a problem hiding this comment.
Preserve the Command modifier for native macOS shortcuts
On macOS, recording Command+N is normalized to Ctrl+N, but the same string is sent unchanged to Tauri, where Ctrl means the physical Control modifier rather than Command. Consequently the renderer handles Command+N while the native menu advertises and handles Control+N, so one configured binding effectively has inconsistent shortcuts depending on which layer receives the event. Serialize a platform-neutral primary modifier such as CmdOrCtrl, or preserve Ctrl and Meta as distinct modifiers.
Useful? React with 👍 / 👎.
| return SHORTCUT_COMMAND_IDS.find((candidateId) => ( | ||
| candidateId !== commandId && preferences[candidateId] === shortcut | ||
| )) ?? null; |
There was a problem hiding this comment.
Reject collisions with fixed native menu accelerators
When a user assigns one of the configurable commands to a fixed menu accelerator such as Ctrl+F, Ctrl+/, or Ctrl+Shift+P, this conflict check succeeds because it only compares the six configurable preferences. The native menu still contains the fixed command with the same accelerator, leaving two menu items competing for one key combination; the fixed command's emitted ID is not handled by executeShortcutCommand, so the customized command can fail to run. Include the non-configurable menu accelerators in the conflict set or reserve them in the recorder.
Useful? React with 👍 / 👎.
| let result = match item { | ||
| MenuItemKind::MenuItem(item) => item | ||
| .set_accelerator(binding.accelerator.as_deref()) | ||
| .map_err(|error| error.to_string()), | ||
| MenuItemKind::Check(item) => item | ||
| .set_accelerator(binding.accelerator.as_deref()) | ||
| .map_err(|error| error.to_string()), |
There was a problem hiding this comment.
Actually clear native accelerators on macOS
When a macOS user clears a binding, this passes None to the locked muda 0.19.2 implementation, whose macOS set_key_accelerator only updates existing NSMenuItems when the new accelerator is Some; the prior key equivalent therefore remains installed. The UI and web handler show the command as unassigned, but its old native shortcut continues firing until restart. Clearing needs a macOS-safe removal path, such as rebuilding the menu or explicitly resetting the native key equivalent.
Useful? React with 👍 / 👎.
Summary
Impact
Users can customize Tinybot's appearance and keyboard shortcuts from Settings. The chat sidebar now follows the active interface language for regular chats that do not belong to a workspace.
Root cause
The no-workspace session label was hardcoded in the session grouping layer, so it could not react to locale changes. The grouping layer now exposes a locale-neutral general group and the React view resolves its translated label.
Validation
npm test: 88 files, 560 tests passednpm run buildcargo fmt --checkcargo checkgit diff --check origin/master...HEAD