|
@@ -2,79 +2,112 @@
|
|
|
|
|
|
|
|
## Overview
|
|
## Overview
|
|
|
|
|
|
|
|
-Lumacs is designed as a modular, extensible editor engine inspired by Emacs. It strictly separates the core logic (buffer management, text editing, key bindings) from the user interface (GTK, TUI).
|
|
|
|
|
|
|
+Lumacs is a modular, extensible text editor engine inspired by Emacs, written in C++20 and scriptable via Lua 5.4. It strictly separates core logic from the user interface, allowing for multiple frontends (GTK4, TUI).
|
|
|
|
|
|
|
|
-## High-Level Diagram
|
|
|
|
|
|
|
+## High-Level Design
|
|
|
|
|
+
|
|
|
|
|
+The system follows a **Core-Manager-View** architecture. The `EditorCore` acts as the central hub but delegates actual logic to specialized Manager classes. Dependencies are managed via Dependency Injection (DI) and interfaces to prevent circular coupling.
|
|
|
|
|
|
|
|
```mermaid
|
|
```mermaid
|
|
|
graph TD
|
|
graph TD
|
|
|
- User[User Input] -->|Key/Mouse| UI[UI Frontend]
|
|
|
|
|
- UI -->|Key Event| Lua[Lua API]
|
|
|
|
|
- Lua -->|Key Sequence| KeyBinding[KeyBindingManager]
|
|
|
|
|
|
|
+ User[User Input] -->|Events| UI[UI Frontend]
|
|
|
|
|
+ UI -->|Key Strings| LuaAPI[Lua API]
|
|
|
|
|
+ LuaAPI -->|Process| KeyBinding[KeyBindingManager]
|
|
|
KeyBinding -->|Command Name| CommandSystem[CommandSystem]
|
|
KeyBinding -->|Command Name| CommandSystem[CommandSystem]
|
|
|
- CommandSystem -->|Action| EditorCore[EditorCore]
|
|
|
|
|
- EditorCore -->|Modify| Buffer[Buffer]
|
|
|
|
|
- EditorCore -->|Modify| Window[Window]
|
|
|
|
|
- EditorCore -->|Event| UI
|
|
|
|
|
- UI -->|Render| Display[Display]
|
|
|
|
|
|
|
+ CommandSystem -->|Execute| Core[EditorCore]
|
|
|
|
|
+
|
|
|
|
|
+ subgraph Core Subsystems
|
|
|
|
|
+ Core -->|Delegate| BufferMgr[BufferManager]
|
|
|
|
|
+ Core -->|Delegate| WindowMgr[WindowManager]
|
|
|
|
|
+ Core -->|Delegate| MinibufferMgr[MinibufferManager]
|
|
|
|
|
+ Core -->|Delegate| MacroMgr[MacroManager]
|
|
|
|
|
+ end
|
|
|
|
|
+
|
|
|
|
|
+ BufferMgr -->|Manage| Buffer[Buffer]
|
|
|
|
|
+ WindowMgr -->|Manage| Window[Window]
|
|
|
|
|
+
|
|
|
|
|
+ Core -.->|Notify| IEditorNotifier
|
|
|
|
|
+ IEditorNotifier -.-> UI
|
|
|
|
|
+
|
|
|
|
|
+ UI -->|Render| Renderer[Renderer (GTK/TUI)]
|
|
|
|
|
+ Renderer -->|Read| Buffer
|
|
|
```
|
|
```
|
|
|
|
|
|
|
|
## Core Components
|
|
## Core Components
|
|
|
|
|
|
|
|
### 1. EditorCore (`editor_core.hpp`)
|
|
### 1. EditorCore (`editor_core.hpp`)
|
|
|
-The central hub of the application. It orchestrates all subsystems and holds the state of the editor.
|
|
|
|
|
-- **Responsibilities**: Buffer management, Window layout (splits), Global Kill Ring, Event dispatching.
|
|
|
|
|
-- **Dependencies**: `Buffer`, `Window`, `CommandSystem`, `LuaApi`, `ThemeManager`.
|
|
|
|
|
-
|
|
|
|
|
-### 2. Buffer (`buffer.hpp`)
|
|
|
|
|
-Represents a text file or scratch space.
|
|
|
|
|
-- **Data**: List of strings (lines), file path, modification flag.
|
|
|
|
|
-- **Features**: Gap buffer (conceptually), Styling attributes (syntax highlighting), Undo/Redo stack, Mark/Region.
|
|
|
|
|
-
|
|
|
|
|
-### 3. Window (`window.hpp`)
|
|
|
|
|
-A view into a Buffer.
|
|
|
|
|
-- **Data**: Reference to a Buffer, Cursor position, Viewport (scroll offset).
|
|
|
|
|
-- **Logic**: Cursor clamping, Scrolling logic.
|
|
|
|
|
-
|
|
|
|
|
-### 4. Command System (`command_system.hpp`)
|
|
|
|
|
-Registry of executable commands.
|
|
|
|
|
-- **Features**: Command registration, Execution by name, Argument parsing, Autocompletion providers.
|
|
|
|
|
-- **Lua Integration**: Commands can be defined in C++ or Lua.
|
|
|
|
|
-
|
|
|
|
|
-### 5. Lua API (`lua_api.hpp`)
|
|
|
|
|
-Bridge to the Lua 5.4 scripting environment.
|
|
|
|
|
-- **Role**: `init.lua` loading, Key binding definitions, Exposing Core API to scripts.
|
|
|
|
|
-
|
|
|
|
|
-### 6. Modeline Framework (`modeline.hpp`)
|
|
|
|
|
-Generates the status line for each window.
|
|
|
|
|
-- **Design**: Modular segments (`ModelineSegment`) managed by `ModelineManager`.
|
|
|
|
|
|
|
+The application root.
|
|
|
|
|
+- **Role**: Owner of all Manager subsystems.
|
|
|
|
|
+- **Interfaces**: Implements `IEditorNotifier` (events) and `IWindowManager` (layout access).
|
|
|
|
|
+- **State**: Holds the global editor configuration and theme manager.
|
|
|
|
|
+
|
|
|
|
|
+### 2. Managers (The Logic Layer)
|
|
|
|
|
+Functionality is partitioned into specialized managers:
|
|
|
|
|
+- **`BufferManager`**: Creates, loads, and manages the lifecycle of `Buffer` objects.
|
|
|
|
|
+- **`WindowManager`**: Manages the window layout tree (`LayoutNode`), splits, and focus.
|
|
|
|
|
+- **`CommandSystem`**: Registry of commands (C++ and Lua). Handles execution and interactive argument reading.
|
|
|
|
|
+- **`KeyBindingManager`**: Trie-based key sequence resolution. Maps `C-x C-f` -> `find-file`.
|
|
|
|
|
+- **`MinibufferManager`**: Handles the command line / prompt area logic, including completion and interactive search (ISearch).
|
|
|
|
|
+- **`MacroManager`**: Records and plays back keyboard macros.
|
|
|
|
|
+- **`PluginManager`**: Discovers and loads Lua plugins.
|
|
|
|
|
+
|
|
|
|
|
+### 3. Data Structures
|
|
|
|
|
+- **`Buffer`**: Stores text as a list of strings (Gap Buffer concept abstract). Manages syntax highlighting (`StyledRange`), undo/redo stack, and mark/region.
|
|
|
|
|
+- **`Window`**: A view into a buffer. Tracks cursor position (`Position`) and scroll viewport (`Viewport`).
|
|
|
|
|
+- **`LayoutNode`**: A node in the binary tree representing window splits.
|
|
|
|
|
+
|
|
|
|
|
+### 4. Interfaces & Decoupling
|
|
|
|
|
+To avoid circular dependencies (e.g., `BufferManager` needing `EditorCore` needing `BufferManager`), we use interfaces:
|
|
|
|
|
+- **`IEditorNotifier`**: Allows subsystems to emit events (`BufferModified`, `Message`) without knowing about `EditorCore`.
|
|
|
|
|
+- **`IWindowManager`**: Allows `BufferManager` to query window state without depending on the concrete `WindowManager`.
|
|
|
|
|
+- **`ICommandTarget`**: Abstract interface for objects that can receive commands.
|
|
|
|
|
+- **`IEditorView`**: Abstract base for UI frontends.
|
|
|
|
|
+
|
|
|
|
|
+### 5. Lua Integration (`lua_api.cpp`)
|
|
|
|
|
+- **Binding**: Uses `sol2` to bind C++ classes (`EditorCore`, `Buffer`, `Window`, `Config`, `Theme`) to Lua.
|
|
|
|
|
+- **Extension**: `init.lua` implements the "Standard Library" of the editor (Major Modes, default keybindings).
|
|
|
|
|
|
|
|
## User Interface (Frontends)
|
|
## User Interface (Frontends)
|
|
|
|
|
|
|
|
-The UI interacts with the core via the `IEditorView` interface (`ui_interface.hpp`).
|
|
|
|
|
-
|
|
|
|
|
-### GTK Frontend (`gtk_editor.cpp`)
|
|
|
|
|
-- Uses GTK4 and Cairo for rendering.
|
|
|
|
|
-- Pango for text layout and font handling.
|
|
|
|
|
-- Supports window splits using `Gtk::Paned`.
|
|
|
|
|
-
|
|
|
|
|
-### TUI Frontend (`tui_editor.cpp`)
|
|
|
|
|
-- Uses Ncurses.
|
|
|
|
|
-- Fallback for terminal environments.
|
|
|
|
|
-
|
|
|
|
|
-## Event Loop
|
|
|
|
|
-
|
|
|
|
|
-1. **Input**: UI captures input (e.g., `Gtk::EventControllerKey`).
|
|
|
|
|
-2. **Processing**: Input is passed to `LuaApi::process_key`.
|
|
|
|
|
-3. **Binding**: `KeyBindingManager` resolves the sequence to a command.
|
|
|
|
|
-4. **Execution**: `CommandSystem` executes the command.
|
|
|
|
|
-5. **State Change**: Command modifies `Buffer` or `EditorCore` state.
|
|
|
|
|
-6. **Notification**: `EditorCore` emits `EditorEvent` (e.g., `BufferModified`).
|
|
|
|
|
-7. **Rendering**: UI observes the event and requests a redraw.
|
|
|
|
|
-
|
|
|
|
|
-## Design Patterns
|
|
|
|
|
-
|
|
|
|
|
-- **Observer**: `IEditorView` observes `EditorCore`.
|
|
|
|
|
-- **Factory**: UI creation via factory functions.
|
|
|
|
|
-- **Command**: Encapsulated actions in `CommandSystem`.
|
|
|
|
|
-- **Composite**: Window layout tree (`LayoutNode`).
|
|
|
|
|
|
|
+### GTK4 Frontend (`src/ui/`)
|
|
|
|
|
+- **`GtkEditor`**: The main application window. Handles input events and forwards them to Core.
|
|
|
|
|
+- **`GtkRenderer`**: High-performance text renderer using **Cairo** and **Pango**.
|
|
|
|
|
+ - **Caching**: Implements a line-based cache (`Cairo::ImageSurface`) to minimize Pango layout re-computation.
|
|
|
|
|
+ - **Layers**: Background -> Cached Text -> Syntax Highlighting -> Selection -> Cursor.
|
|
|
|
|
+- **`GtkCompletionPopup`**: A `Gtk::Popover` widget for showing autocompletion candidates.
|
|
|
|
|
+
|
|
|
|
|
+### TUI Frontend
|
|
|
|
|
+- **`TuiEditor`**: Ncurses-based fallback. Renders text grid and handles terminal input sequences.
|
|
|
|
|
+
|
|
|
|
|
+## Event Flow (The "Golden Path")
|
|
|
|
|
+
|
|
|
|
|
+1. **Input**: User presses a key (e.g., `C-f`).
|
|
|
|
|
+2. **Capture**: `GtkEditor` captures the event via `Gtk::EventControllerKey` (Phase: Capture).
|
|
|
|
|
+3. **Normalization**: Key is converted to a string `"C-f"`.
|
|
|
|
|
+4. **Processing**: Passed to `KeyBindingManager::process_key`.
|
|
|
|
|
+5. **Resolution**: Trie traversal finds command `"forward-char"`.
|
|
|
|
|
+6. **Recording**: If macro recording is active, `KeyBindingManager` notifies `MacroManager`.
|
|
|
|
|
+7. **Execution**: `CommandSystem` executes the C++ lambda for `forward-char`.
|
|
|
|
|
+8. **Update**: `EditorCore::move_right` modifies the `Window` cursor.
|
|
|
|
|
+9. **Notification**: `EditorCore` emits `EditorEvent::CursorMoved`.
|
|
|
|
|
+10. **Render**: `GtkEditor` receives event, queues redraw. `GtkRenderer` updates the screen.
|
|
|
|
|
+
|
|
|
|
|
+## Styling System
|
|
|
|
|
+
|
|
|
|
|
+- **Themes**: JSON-like structures (in C++ or Lua) defining colors for semantic tags (`ThemeElement`).
|
|
|
|
|
+- **Faces**: Specific style attributes (foreground, background, bold, italic).
|
|
|
|
|
+- **Application**:
|
|
|
|
|
+ 1. `Buffer` stores `StyledRange` (semantic tag + range).
|
|
|
|
|
+ 2. `GtkRenderer` queries the active `Theme` to map tags to Pango attributes.
|
|
|
|
|
+ 3. Pango renders the text with attributes.
|
|
|
|
|
+
|
|
|
|
|
+## Build System
|
|
|
|
|
+
|
|
|
|
|
+- **CMake**: Manages build configuration.
|
|
|
|
|
+- **Dependencies**:
|
|
|
|
|
+ - `gtkmm-4.0` (UI)
|
|
|
|
|
+ - `lua` (Scripting)
|
|
|
|
|
+ - `sol2` (Bindings)
|
|
|
|
|
+ - `spdlog` (Logging)
|
|
|
|
|
+ - `ncurses` (TUI)
|
|
|
|
|
+ - `gtest` (Testing)
|