v0.2.7 focuses on features deferred from v0.2.6 to allow focus on the custom text editor, plus checking for updates and quality improvements.
Theme: Performance, linking, editing modes, updates, and polish.
Scope: Bug fixes, markdown linking (wikilinks, backlinks), optional Vim mode, manual check-for-updates, large file performance, flowchart refactoring, executable code blocks (opt-in), and GitHub-style callouts.
Problem: When "Which CJK font to prioritize" is set to a non-Auto value and the app restarts, Chinese can render as tofu in restored tabs. Root cause: we only lazy-load CJK for the active tab and don't preload the user's preferred font at startup.
Fix:
- Preload the single preferred CJK font at startup when preference is explicit
- Same approach as Auto + system locale (preload at app init)
- Ensures restored documents render correctly regardless of which tab is active
Location: CJK font loading logic (likely src/editor/ferrite/ or theme/font module)
Test:
- Set CJK font preference to explicit value (e.g., Noto Sans SC)
- Restart app with restored session containing Chinese text
- Switch between tabs → Chinese should render correctly in all tabs
Scope: Additional issues reported post-v0.2.6.1 release. To be populated from GitHub issues as they emerge.
Feature: [[wikilinks]] syntax — standard Obsidian/wiki-style internal links.
Requirements:
- Parse
[[target]]and[[target|display text]]syntax - Resolve target relative to current file or workspace root
- Resolution tie-breaker (ambiguous
[[note]]when ProjectA/note.md and ProjectB/note.md exist): Same-folder-first, then shortest path; if still ambiguous, prompt user to choose - Spaces in filenames: Support
[[My Note]](Obsidian convention); internally resolve to file path — no%20required in source - Click-to-navigate in rendered/split view
- Support in outline/backlinks
Implementation notes:
- Extend markdown parser (pulldown-cmark or custom in
src/markdown/) - Store link targets for resolution; handle broken links gracefully
- Use existing
Tab.content/ FerriteEditor buffer for resolution
Test:
- Create
note-a.mdwith[[note-b]]and[[note-b|Link to B]] - Rendered view: click link → opens note-b.md
- Display text variant shows "Link to B" as link label
[[My Document]]with spaces → resolves toMy Document.md
Feature: Show documents that link to the current file.
Requirements:
- New panel (or extend outline) listing files containing
[[current_file]]or[text](current_file.md) - Update when switching tabs or on file change
- Click entry → navigate to that file (and ideally scroll to link)
Implementation notes:
- Small workspaces (≤50 files): Scan on tab switch or debounced
- Large workspaces (>50 files): Build lightweight in-memory graph on workspace load:
HashMap<filename, [referencing_files]>; update incrementally on save. Avoid O(N) scan on every tab switch. - UI:
ui/— could extendoutline_panel.rsor addbacklinks_panel.rs
Test:
- File A links to B, C links to B
- Open B → backlinks panel shows A and C
- Click A → navigates to A
Feature: Optional Vim-style modal editing: Normal / Insert / Visual modes.
Requirements:
- Setting to enable/disable (default: disabled)
- Normal mode: hjkl movement, dd (delete line), yy (yank), p (paste), / (search), etc.
- Insert mode: type normally, Esc to Normal
- Visual mode: v for char-wise, V for line-wise selection
- Status bar indicator: Show
[NORMAL]or[INSERT](or block vs line cursor) so users know which mode is active — avoids "keyboard broken" confusion - Essential subset first; expand in later releases
Implementation notes:
- Integrate with FerriteEditor in
src/editor/ferrite/ - Modal state machine; key handling differs by mode
- Key conflict handling: Vim keys (e.g. Ctrl+C) conflict with standard shortcuts. In egui, handle focus and key consumption priority so Vim mode consumes keys in editor when active; standard shortcuts take precedence when not in Vim or when modal doesn't use the key
- Consider
editor/vim.rsmodule or similar
Test:
- Enable Vim mode in settings
- Open file → Normal mode; status bar shows
[NORMAL]; hjkl moves cursor - i → Insert mode; status bar shows
[INSERT]; type; Esc → Normal - v → Visual; select; y → yank; p → paste
Feature: Settings panel button that checks GitHub and prompts to install if an update is found.
Requirements:
- "Check for Updates" button in Settings (e.g., About/General section)
- Fetches latest release from GitHub API (e.g.,
https://api.github.com/repos/OlaProeis/Ferrite/releases/latest) - Compare version with current; if newer, show dialog with download link
- Manual trigger only — no automatic background checking (offline-first)
Implementation notes:
- Add to
src/ui/settings.rs - Use
reqwestor similar for HTTP (blocking or async via workers) - Version comparison: semver or simple string compare
- Handle network errors gracefully (toast)
Test:
- Click "Check for Updates" → if up to date, show "You're on the latest version"
- If update available, show version + download link
- Offline / API error → user-friendly message
Feature: Auto-detect files > 10MB on open; show warning toast.
Requirements:
- On file open: if size > 10MB, show toast: "Large file (X MB). Performance may be affected."
- Non-blocking; user can proceed
- Configurable threshold in settings (optional, v0.2.8+)
Implementation notes:
- Check file size in open flow (
app.rsor file loading) - Use
std::fs::metadata().len()before loading content
Test: Open 15MB file → toast appears; file still opens.
Feature: Parse CSV rows on-demand using byte-offset index for massive CSVs.
Requirements:
- For large CSVs, build byte-offset index of row boundaries
- Parse rows only when visible (virtual scrolling)
- Avoid loading entire CSV into memory as parsed grid
Implementation notes:
- CSV viewer in
src/(locate existing CSV handling) - Index:
Vec<u64>of byte offsets per row - Parse row N:
buffer[offsets[n]..offsets[n+1]]with CSV parsing
Test: Open 100MB CSV → memory stays low; scrolling is smooth.
Scope: Modularize src/markdown/mermaid/flowchart.rs (~3,200+ lines).
Requirements:
- Split into logical modules (e.g., nodes, edges, layout, rendering)
- Preserve behavior; no functional changes
- Improve maintainability for future Mermaid enhancements
- Rendering cache: egui is immediate-mode — recomputing layout every frame is expensive. Cache the rendered flowchart as a texture; only recompute when diagram content changes. Avoid full layout+draw on each frame.
Proposed structure (example):
flowchart/nodes.rs— node shapes, labelsflowchart/edges.rs— edge routing, arrow typesflowchart/layout.rs— positioning, rank assignmentflowchart/render.rs— egui drawingflowchart/mod.rs— public API, glue
Test: All existing flowchart tests pass; manual Mermaid flowchart rendering unchanged.
Feature: Native-feel window controls for macOS; further icon polish.
Requirements:
- macOS: traffic-light style window controls (close, minimize, maximize) in window frame
- Consistent icon quality across light/dark themes
- Follow platform HIG where applicable
Implementation notes:
src/ui/window.rs— window decorationeframe/eguiwindow options for native vs custom traffic lights
Test: macOS build shows native-style window controls; icons look correct in both themes.
Security note: Code execution is opt-in and disabled by default.
Feature: Add ▶ Run button to fenced code blocks.
Requirements:
- Render small "Run" button on eligible code blocks (shell, bash, python)
- Click → execute via
std::process::Command - Output displayed inline or in collapsible section below block
- Shell / Bash: Execute via system shell. Windows:
sh/bashfail unless WSL or Git Bash in PATH — default topowershellorcmd, or detect ifbash.exeexists. Unix: useshorbash. - Python: Detect
python/python3and run with system interpreter - CWD (Current Working Directory): Run script in the file's directory (user expectation for relative paths). Fallback to app root only if file has no path (e.g. unsaved).
- Timeout: Kill long-running scripts after configurable timeout (default: 30s)
- Security warning: First-run dialog explaining execution risks; user must acknowledge before first run
Implementation notes:
- New module e.g.
src/code_execution/or undersrc/markdown/ - Settings: enable/disable, timeout, interpreter paths
- Use
std::process::Command; timeout viastd::thread::spawn+ kill - Store "has seen warning" in settings or local state
Test:
- Default: Run button hidden or disabled until opt-in
- Enable → Run button appears on
bash andpython blocks - Run simple script → output shown; CWD is file's directory (relative paths work)
- Run infinite loop → killed after 30s
- First run → security dialog shown once
- Windows: script runs via powershell/cmd (or detected bash) without WSL
Feature: Support GitHub-style admonition blocks.
Syntax:
> [!NOTE]— Note> [!TIP]— Tip> [!WARNING]— Warning> [!CAUTION]— Caution> [!IMPORTANT]— Important
Requirements:
- Parse
> [!TYPE]and optional> [!TYPE] Custom Title - Styled rendering: color-coded blocks, icons
- Collapsible:
> [!NOTE]-for collapsed-by-default
Implementation notes:
- Extend blockquote parsing in
src/markdown/ - Map type to color + icon; render in
markdown/widgets.rsor similar - Collapsed state: store in AST or view state; toggle on click
Test:
> [!NOTE]\n> Content→ blue note block with icon> [!WARNING] Custom Title\n> Content→ orange block, "Custom Title"> [!NOTE]-→ collapsed by default; click to expand
- Bidirectional scroll sync — Editor-Preview scroll sync in Split view (requires viewport-based line tracking)
- IME candidate box positioning (#15) — Chinese/Japanese IME candidate window offset
- Click-to-edit cursor drift — Cursor offset on mixed-format lines in rendered view
Suggested order for task breakdown:
- Bug fixes (P0) — Unblock users immediately
- Check for Updates (P3) — Small, self-contained, high visibility
- Large file detection (P4) — Quick win, low risk
- Callouts (P7) — Pure parser/rendering change; lower risk, warms up on parser codebase before linking logic. Do before Wikilinks.
- Wikilinks (P1) — Foundation for backlinks; parser + interaction
- Backlinks panel (P1) — Depends on wikilinks
- Flowchart refactoring (P5) — Improves maintainability
- Window controls (P5) — Platform polish
- Lazy CSV (P4) — Larger refactor
- Vim mode (P2) — Larger feature, editor integration
- Executable code blocks (P6) — New subsystem, security-sensitive
| Component | Location | Notes |
|---|---|---|
| Markdown parser | src/markdown/parser.rs |
Extend for wikilinks, callouts |
| Rendering | src/markdown/widgets.rs, editor.rs |
Callouts, run button, link handling |
| Editor | src/editor/ferrite/ |
Vim mode, large file behavior |
| Settings | src/config/settings.rs |
New options: Vim, code execution, updates |
| UI panels | src/ui/ |
Backlinks, settings button |
| Mermaid | src/markdown/mermaid/ |
Flowchart refactor |
| Risk | Mitigation |
|---|---|
| Code execution security | Opt-in, first-run warning, timeout, no network/filesystem by default |
| Vim mode scope creep | Define minimal MVP (hjkl, i, Esc, dd, yy, p, v, /) |
| Flowchart regressions | Preserve all tests; manual Mermaid checklist |
| Wikilinks ambiguity | Tie-breaker rule (same-folder-first, shortest path); prompt if ambiguous |
| Vim key conflicts | Vim consumes keys when active; egui focus/priority handling |
| Code exec on Windows | Default to powershell/cmd; detect bash if present |
- P0: CJK renders after restart with explicit preference
- P1: Wikilinks parse, render, navigate; backlinks panel works
- P2: Vim mode toggles, basic commands work
- P3: Check for Updates works (current + outdated cases)
- P4: Large file toast; lazy CSV for big files
- P5: Flowchart tests pass; window controls on macOS
- P6: Code execution opt-in, timeout, security dialog
- P7: All callout types render; collapsible works
- No regressions in editor, terminal, productivity hub
- Cross-platform smoke test (Windows, macOS, Linux if available)
Bug Fixes:
- Fixed CJK font rendering in restored tabs when using explicit font preference (#76)
New Features:
- Wikilinks (
[[link]],[[link|text]]) with click-to-navigate - Backlinks panel showing documents that link to the current file
- Optional Vim mode (Normal/Insert/Visual)
- Check for Updates button in Settings (manual only)
- Large file detection (>10MB) with warning toast
- Lazy CSV parsing for massive spreadsheets
- GitHub-style callouts (
> [!NOTE],> [!TIP], etc.) with optional collapse - Executable code blocks (opt-in): Run button for shell/Python with timeout
- Native window controls on macOS
Improvements:
- Flowchart module refactored for maintainability
- Icon and window polish
Document Version: 1.1
Created: February 7, 2026
Updated: February 7, 2026 — Incorporated external review (resolution rules, Vim status bar, Windows exec, CWD, flowchart cache, dependency order)
Status: Draft — Ready for Review
Next Step: Review with team; then run task-master parse-prd to generate tasks.