From 465db82bd9e9ac61aeac8778040836c7dd4d289b Mon Sep 17 00:00:00 2001 From: Priec Date: Mon, 18 Aug 2025 21:00:14 +0200 Subject: [PATCH] prod comments in the codebase --- canvas/src/canvas/actions/mod.rs | 1 + canvas/src/canvas/actions/movement/char.rs | 1 + canvas/src/canvas/actions/movement/line.rs | 1 + canvas/src/canvas/actions/movement/mod.rs | 1 + canvas/src/canvas/actions/movement/word.rs | 2 +- canvas/src/canvas/actions/types.rs | 68 +++++++++++++++++----- canvas/src/canvas/cursor.rs | 14 ++++- canvas/src/canvas/gui.rs | 19 +++++- canvas/src/canvas/mod.rs | 4 ++ canvas/src/canvas/modes/highlight.rs | 12 +++- canvas/src/canvas/modes/manager.rs | 43 +++++++++++--- canvas/src/canvas/state.rs | 26 +++++++++ 12 files changed, 163 insertions(+), 29 deletions(-) diff --git a/canvas/src/canvas/actions/mod.rs b/canvas/src/canvas/actions/mod.rs index 412d758..7001579 100644 --- a/canvas/src/canvas/actions/mod.rs +++ b/canvas/src/canvas/actions/mod.rs @@ -1,4 +1,5 @@ // src/canvas/actions/mod.rs +//! Canvas action definitions and movement utilities pub mod types; pub mod movement; diff --git a/canvas/src/canvas/actions/movement/char.rs b/canvas/src/canvas/actions/movement/char.rs index 8898c01..49593e5 100644 --- a/canvas/src/canvas/actions/movement/char.rs +++ b/canvas/src/canvas/actions/movement/char.rs @@ -1,4 +1,5 @@ // src/canvas/actions/movement/char.rs +//! Character-level cursor movement functions /// Calculate new position when moving left pub fn move_left(current_pos: usize) -> usize { diff --git a/canvas/src/canvas/actions/movement/line.rs b/canvas/src/canvas/actions/movement/line.rs index 4aceaee..f87373f 100644 --- a/canvas/src/canvas/actions/movement/line.rs +++ b/canvas/src/canvas/actions/movement/line.rs @@ -1,4 +1,5 @@ // src/canvas/actions/movement/line.rs +//! Line-level cursor movement and positioning /// Calculate cursor position for line start pub fn line_start_position() -> usize { diff --git a/canvas/src/canvas/actions/movement/mod.rs b/canvas/src/canvas/actions/movement/mod.rs index 8f17cfb..c3f4f20 100644 --- a/canvas/src/canvas/actions/movement/mod.rs +++ b/canvas/src/canvas/actions/movement/mod.rs @@ -1,4 +1,5 @@ // src/canvas/actions/movement/mod.rs +//! Movement utilities for character, word, and line navigation pub mod word; pub mod line; diff --git a/canvas/src/canvas/actions/movement/word.rs b/canvas/src/canvas/actions/movement/word.rs index 80e01b7..4b49a30 100644 --- a/canvas/src/canvas/actions/movement/word.rs +++ b/canvas/src/canvas/actions/movement/word.rs @@ -1,5 +1,5 @@ // src/canvas/actions/movement/word.rs -// Replace the entire file with this corrected version: +//! Word-based cursor movement with vim-like semantics #[derive(PartialEq, Copy, Clone)] enum CharType { diff --git a/canvas/src/canvas/actions/types.rs b/canvas/src/canvas/actions/types.rs index 2251e56..ddaada4 100644 --- a/canvas/src/canvas/actions/types.rs +++ b/canvas/src/canvas/actions/types.rs @@ -1,79 +1,121 @@ // src/canvas/actions/types.rs +//! Core action types and result handling for canvas operations. -/// All available canvas actions +/// All available canvas actions. +/// +/// This enum lists high-level actions that can be performed on the canvas. +/// Consumers can match on variants to implement custom handling or map input +/// events to these canonical actions. #[non_exhaustive] #[derive(Debug, Clone, PartialEq)] pub enum CanvasAction { // Movement actions + /// Move the cursor left by one character (or logical unit). MoveLeft, + /// Move the cursor right by one character (or logical unit). MoveRight, + /// Move the cursor up a visual line/field. MoveUp, + /// Move the cursor down a visual line/field. MoveDown, // Word movement + /// Move to the start of the next word. MoveWordNext, + /// Move to the start of the previous word. MoveWordPrev, + /// Move to the end of the current/next word. MoveWordEnd, + /// Move to the previous word end (vim `ge`). MoveWordEndPrev, // Line movement + /// Move to the start of the current line. MoveLineStart, + /// Move to the end of the current line. MoveLineEnd, // Field movement + /// Move to the next field. NextField, + /// Move to the previous field. PrevField, + /// Move to the first field. MoveFirstLine, + /// Move to the last field. MoveLastLine, // Editing actions + /// Insert a character at the cursor. InsertChar(char), + /// Delete character before the cursor. DeleteBackward, + /// Delete character under/after the cursor. DeleteForward, // Suggestions actions - TriggerSuggestions, - SuggestionUp, - SuggestionDown, - SelectSuggestion, - ExitSuggestions, + /// Trigger suggestions dropdown (e.g. Tab). + TriggerSuggestions, + /// Move selection up in suggestions dropdown. + SuggestionUp, + /// Move selection down in suggestions dropdown. + SuggestionDown, + /// Accept the selected suggestion. + SelectSuggestion, + /// Exit suggestions UI. + ExitSuggestions, // Custom actions + /// Custom named action for application-specific behavior. Custom(String), } -/// Result type for canvas actions +/// Result type for canvas actions. +/// +/// Action handlers return an ActionResult to indicate success, user-facing +/// messages, or errors. The enum is non-exhaustive to allow extension. #[non_exhaustive] #[derive(Debug, Clone)] pub enum ActionResult { + /// Action completed successfully. Success, + /// Action completed with a user-facing message. Message(String), + /// Action was handled by the application with an associated message. HandledByApp(String), + /// Action was handled by a feature with an associated message. HandledByFeature(String), // Keep for compatibility + /// An error occurred while handling the action. Error(String), } impl ActionResult { + /// Convenience constructor for Success. pub fn success() -> Self { Self::Success } + /// Convenience constructor for Message. pub fn success_with_message(msg: &str) -> Self { Self::Message(msg.to_string()) } + /// Convenience constructor for HandledByApp. pub fn handled_by_app(msg: &str) -> Self { Self::HandledByApp(msg.to_string()) } + /// Convenience constructor for Error. pub fn error(msg: &str) -> Self { Self::Error(msg.to_string()) } + /// Returns true for any variant representing a success-like outcome. pub fn is_success(&self) -> bool { matches!(self, Self::Success | Self::Message(_) | Self::HandledByApp(_) | Self::HandledByFeature(_)) } + /// Extract a message from the result when present. pub fn message(&self) -> Option<&str> { match self { Self::Message(msg) | Self::HandledByApp(msg) | Self::HandledByFeature(msg) | Self::Error(msg) => Some(msg), @@ -83,7 +125,7 @@ impl ActionResult { } impl CanvasAction { - /// Get a human-readable description of this action + /// Get a human-readable description of this action. pub fn description(&self) -> &'static str { match self { Self::MoveLeft => "move left", @@ -112,7 +154,7 @@ impl CanvasAction { } } - /// Get all movement-related actions + /// Get all movement-related actions. pub fn movement_actions() -> Vec { vec![ Self::MoveLeft, @@ -132,7 +174,7 @@ impl CanvasAction { ] } - /// Get all editing-related actions + /// Get all editing-related actions. pub fn editing_actions() -> Vec { vec![ Self::InsertChar(' '), // Example char @@ -141,7 +183,7 @@ impl CanvasAction { ] } - /// Get all suggestions-related actions + /// Get all suggestions-related actions. pub fn suggestions_actions() -> Vec { vec![ Self::TriggerSuggestions, @@ -152,7 +194,7 @@ impl CanvasAction { ] } - /// Check if this action modifies text content + /// Check if this action modifies text content. pub fn is_editing_action(&self) -> bool { matches!(self, Self::InsertChar(_) | @@ -161,7 +203,7 @@ impl CanvasAction { ) } - /// Check if this action moves the cursor + /// Check if this action moves the cursor. pub fn is_movement_action(&self) -> bool { matches!(self, Self::MoveLeft | Self::MoveRight | Self::MoveUp | Self::MoveDown | diff --git a/canvas/src/canvas/cursor.rs b/canvas/src/canvas/cursor.rs index c11dd4f..88372ac 100644 --- a/canvas/src/canvas/cursor.rs +++ b/canvas/src/canvas/cursor.rs @@ -1,5 +1,9 @@ // src/canvas/cursor.rs //! Cursor style management for different canvas modes +//! +//! Provides helpers to update and reset terminal cursor style when the +//! `cursor-style` feature is enabled. When the feature is disabled the +//! functions are no-ops. #[cfg(feature = "cursor-style")] use crossterm::{cursor::SetCursorStyle, execute}; @@ -12,7 +16,10 @@ use crate::canvas::modes::AppMode; pub struct CursorManager; impl CursorManager { - /// Update cursor style based on current mode + /// Update cursor style based on current mode. + /// + /// When the `textmode-normal` feature is enabled a fixed style is applied. + /// Otherwise, the cursor style is mapped to the provided AppMode. #[cfg(feature = "cursor-style")] pub fn update_for_mode(mode: AppMode) -> io::Result<()> { // NORMALMODE: force underscore for every mode @@ -37,18 +44,19 @@ impl CursorManager { } } - /// No-op when cursor-style feature is disabled + /// No-op when cursor-style feature is disabled. #[cfg(not(feature = "cursor-style"))] pub fn update_for_mode(_mode: AppMode) -> io::Result<()> { Ok(()) } - /// Reset cursor to default on cleanup + /// Reset cursor to default on cleanup. #[cfg(feature = "cursor-style")] pub fn reset() -> io::Result<()> { execute!(io::stdout(), SetCursorStyle::DefaultUserShape) } + /// Reset is a no-op when the cursor-style feature is disabled. #[cfg(not(feature = "cursor-style"))] pub fn reset() -> io::Result<()> { Ok(()) diff --git a/canvas/src/canvas/gui.rs b/canvas/src/canvas/gui.rs index bcb7aa2..23ee61d 100644 --- a/canvas/src/canvas/gui.rs +++ b/canvas/src/canvas/gui.rs @@ -1,5 +1,9 @@ // src/canvas/gui.rs //! Canvas GUI updated to work with FormEditor +//! +//! This module provides rendering helpers for the canvas UI when the `gui` +//! feature is enabled. It exposes high-level functions to render the canvas +//! and convenience types for display options. #[cfg(feature = "gui")] use ratatui::{ @@ -22,14 +26,20 @@ use std::cmp::{max, min}; #[cfg(feature = "gui")] #[derive(Debug, Clone, Copy)] +/// How to handle overflow when rendering a field's content. pub enum OverflowMode { - Indicator(char), // default '$' + /// Show an indicator character at the left/right when text is truncated. + /// Common default is '$'. + Indicator(char), + /// Wrap content into multiple visual lines. Wrap, } #[cfg(feature = "gui")] #[derive(Debug, Clone, Copy)] +/// Display options controlling canvas rendering behavior. pub struct CanvasDisplayOptions { + /// How to handle horizontal overflow for fields. pub overflow: OverflowMode, } @@ -191,6 +201,9 @@ fn render_active_line_with_indicator( } #[cfg(feature = "gui")] +/// Render the canvas into the provided frame using default display options. +/// +/// Returns the rectangle of the active input field if present. pub fn render_canvas( f: &mut Frame, area: Rect, @@ -202,6 +215,10 @@ pub fn render_canvas( } #[cfg(feature = "gui")] +/// Render the canvas into the provided frame with explicit display options. +/// +/// This is the more configurable entrypoint for rendering and is useful for +/// tests or when callers need to override overflow handling. pub fn render_canvas_with_options( f: &mut Frame, area: Rect, diff --git a/canvas/src/canvas/mod.rs b/canvas/src/canvas/mod.rs index 7485443..42c8b6e 100644 --- a/canvas/src/canvas/mod.rs +++ b/canvas/src/canvas/mod.rs @@ -1,4 +1,8 @@ // src/canvas/mod.rs +//! Top-level canvas module. +//! +//! Re-exports commonly used canvas types and modules so that downstream +//! consumers can import them from `crate::canvas`. pub mod actions; pub mod state; diff --git a/canvas/src/canvas/modes/highlight.rs b/canvas/src/canvas/modes/highlight.rs index 7bf63c0..aeee886 100644 --- a/canvas/src/canvas/modes/highlight.rs +++ b/canvas/src/canvas/modes/highlight.rs @@ -1,12 +1,18 @@ -// src/state/app/highlight.rs -// canvas/src/modes/highlight.rs +// src/canvas/modes/highlight.rs +//! Highlight state definitions for canvas visual/selection modes. #[derive(Debug, Clone, PartialEq, Eq)] #[derive(Default)] +/// Represents the current highlight/visual selection state. +/// +/// This enum is used by the GUI and selection logic to track whether a visual +/// selection is active and its anchor position. pub enum HighlightState { + /// No highlighting active. #[default] Off, + /// Characterwise selection with an anchor (field_index, char_position). Characterwise { anchor: (usize, usize) }, // (field_index, char_position) + /// Linewise selection anchored at a field index. Linewise { anchor_line: usize }, // field_index } - diff --git a/canvas/src/canvas/modes/manager.rs b/canvas/src/canvas/modes/manager.rs index 3ad9d4b..fcf320f 100644 --- a/canvas/src/canvas/modes/manager.rs +++ b/canvas/src/canvas/modes/manager.rs @@ -1,40 +1,61 @@ // src/modes/handlers/mode_manager.rs // canvas/src/modes/manager.rs +//! Mode manager utilities and the AppMode enum. +//! +//! This module defines the available canvas modes and provides helper +//! functions to validate mode transitions and perform required side-effects +//! such as updating cursor style when enabled. #[cfg(feature = "cursor-style")] use crate::canvas::CursorManager; #[derive(Debug, Clone, Copy, PartialEq, Eq)] +/// Top-level application modes used by the canvas UI. +/// +/// These modes control input handling, cursor behavior, and how the UI should +/// respond to user actions. pub enum AppMode { - General, // For intro and admin screens - ReadOnly, // Canvas read-only mode - Edit, // Canvas edit mode - Highlight, // Canvas highlight/visual mode - Command, // Command mode overlay + /// For intro and admin screens + General, + /// Canvas read-only mode (navigation) + ReadOnly, + /// Canvas edit mode (insertion/modification) + Edit, + /// Canvas highlight/visual mode (selection) + Highlight, + /// Command mode overlay (for commands) + Command, } pub struct ModeManager; impl ModeManager { // Mode transition rules + + /// Return true if the system can enter Command mode from the given current mode. pub fn can_enter_command_mode(current_mode: AppMode) -> bool { !matches!(current_mode, AppMode::Edit) } + /// Return true if the system can enter Edit mode from the given current mode. pub fn can_enter_edit_mode(current_mode: AppMode) -> bool { matches!(current_mode, AppMode::ReadOnly) } + /// Return true if the system can enter ReadOnly mode from the given current mode. pub fn can_enter_read_only_mode(current_mode: AppMode) -> bool { matches!(current_mode, AppMode::Edit | AppMode::Command | AppMode::Highlight) } + /// Return true if the system can enter Highlight mode from the given current mode. pub fn can_enter_highlight_mode(current_mode: AppMode) -> bool { matches!(current_mode, AppMode::ReadOnly) } - /// Transition to new mode with automatic cursor update (when cursor-style feature enabled) + /// Transition to new mode with automatic cursor update (when cursor-style feature enabled). + /// + /// Returns the resulting mode or an I/O error if cursor style update fails. pub fn transition_to_mode(current_mode: AppMode, new_mode: AppMode) -> std::io::Result { #[cfg(feature = "textmode-normal")] { @@ -54,7 +75,10 @@ impl ModeManager { } } - /// Enter highlight mode with cursor styling + /// Enter highlight mode with cursor styling. + /// + /// Returns Ok(true) if the transition succeeded (and cursor style was updated + /// when enabled), otherwise Ok(false) if the transition is not allowed. pub fn enter_highlight_mode_with_cursor(current_mode: AppMode) -> std::io::Result { if Self::can_enter_highlight_mode(current_mode) { #[cfg(feature = "cursor-style")] @@ -67,7 +91,10 @@ impl ModeManager { } } - /// Exit highlight mode with cursor styling + /// Exit highlight mode with cursor styling and return the next mode. + /// + /// This helper returns the mode to switch to (ReadOnly) and updates cursor + /// style if the feature is enabled. pub fn exit_highlight_mode_with_cursor() -> std::io::Result { let new_mode = AppMode::ReadOnly; #[cfg(feature = "cursor-style")] diff --git a/canvas/src/canvas/state.rs b/canvas/src/canvas/state.rs index a39ec55..3d8f5ba 100644 --- a/canvas/src/canvas/state.rs +++ b/canvas/src/canvas/state.rs @@ -1,10 +1,20 @@ // src/canvas/state.rs //! Library-owned UI state - user never directly modifies this +//! +//! This module exposes the EditorState type (and related selection and +//! suggestions types) which represent the internal UI state maintained by the +//! canvas library. These types are intended for read-only access by callers +//! and are mutated only through the library's APIs. use crate::canvas::modes::AppMode; /// Library-owned UI state - user never directly modifies this #[derive(Debug, Clone)] +/// Internal editor UI state managed by the canvas library. +/// +/// The fields are `pub(crate)` because they should only be modified by the +/// library's internal action handlers. Consumers can use the provided getter +/// methods to observe the state. pub struct EditorState { // Navigation state pub(crate) current_field: usize, @@ -32,6 +42,7 @@ pub struct EditorState { #[cfg(feature = "suggestions")] #[derive(Debug, Clone)] +/// Internal suggestions UI state used to manage the suggestions dropdown. pub struct SuggestionsUIState { pub(crate) is_active: bool, pub(crate) is_loading: bool, @@ -42,13 +53,19 @@ pub struct SuggestionsUIState { } #[derive(Debug, Clone)] +/// SelectionState represents the current selection/visual mode state used by +/// the canvas (for example, Vim-like visual modes). pub enum SelectionState { + /// No selection is active. None, + /// Characterwise selection: (field_index, char_position) Characterwise { anchor: (usize, usize) }, + /// Linewise selection anchored at a field (field index). Linewise { anchor_field: usize }, } impl EditorState { + /// Create a new EditorState with default initial values. pub fn new() -> Self { Self { current_field: 0, @@ -139,6 +156,10 @@ impl EditorState { // INTERNAL MUTATIONS: Only library modifies these // =================================================================== + /// Move internal pointer to another field index. + /// + /// This method is intended for internal library use to change the current + /// field and reset the cursor to a safe value. pub(crate) fn move_to_field(&mut self, field_index: usize, field_count: usize) { if field_index < field_count { self.current_field = field_index; @@ -147,6 +168,11 @@ impl EditorState { } } + /// Set the cursor position with appropriate clamping depending on mode. + /// + /// If `for_edit_mode` is true the cursor may be positioned at the end of + /// the text (allowing insertion); otherwise it will be kept within the + /// bounds of the existing text for read-only/highlight modes. pub(crate) fn set_cursor( &mut self, position: usize,