Business Rules: Unit 1 — Core Editor Engine

BR-01: Paragraph-Level Delayed Rendering

Rule Description
BR-01.1 When the cursor is inside a structural block, that block MUST display raw Markdown syntax with syntax highlighting
BR-01.2 When the cursor leaves a block, that block MUST render as styled output (formatted text, no visible syntax characters)
BR-01.3 Block activation MUST follow ActivationScope rules (see domain-entities.md)
BR-01.4 Only ONE block activation group may be active at a time
BR-01.5 Switching active blocks MUST re-render both the deactivated and newly activated blocks

BR-02: GFM Element Rendering Rules

BR-02.1: Headings (h1–h6)

BR-02.2: Bold

BR-02.3: Italic

BR-02.4: Strikethrough

BR-02.5: Inline Code

BR-02.7: Images

BR-02.8: Fenced Code Blocks

BR-02.9: Unordered Lists

BR-02.10: Ordered Lists

BR-02.11: Task Lists

BR-02.12: Tables

BR-02.13: Blockquotes

BR-02.14: Horizontal Rules


BR-03: IME Composition Handling

Rule Description
BR-03.1 During IME composition (marked text), the parsing pipeline MUST pause — no re-parse or active block switch
BR-03.2 During IME composition, the active block MUST remain in raw syntax mode (no rendering switch)
BR-03.3 When IME composition commits (marked text finalizes), immediately resume the parse pipeline
BR-03.4 IME composition state is detected via NSTextInputClient.hasMarkedText()

BR-04: Unsupported Extension Fallback

Rule Description
BR-04.1 LaTeX math ($...$, $$...$$) MUST be rendered as a fenced code block with language math
BR-04.2 Mermaid diagrams ( ``mermaid `) are already fenced code blocks — render with language label “mermaid”, no special rendering
BR-04.3 Any fenced code block with an unrecognized language MUST render as plain monospace with the language label displayed
BR-04.4 YAML frontmatter (--- delimited at document start) MUST be rendered as a code block with language yaml

BR-05: Parse Pipeline Rules

Rule Description
BR-05.1 Full document re-parse on every text change (after debounce)
BR-05.2 Parse MUST run off main thread (background actor)
BR-05.3 Parse results tagged with documentRevision; stale results (revision < current) MUST be discarded
BR-05.4 Debounce: 50ms after last keystroke before triggering parse
BR-05.5 Diff new parse result against current model; only re-render changed blocks
BR-05.6 RenderCache MUST be invalidated when appearance (light/dark) changes or font settings change

BR-06: Keyboard Shortcuts

Shortcut Action Implementation
Cmd+B Toggle bold on selection Wrap/unwrap with **
Cmd+I Toggle italic on selection Wrap/unwrap with *
Cmd+K Insert/edit link Wrap with [](), place cursor in URL
Cmd+1 through Cmd+6 Set heading level Replace/add # prefix on current line
Cmd+Shift+K Toggle inline code Wrap/unwrap with `

Toggle logic: If selection is already wrapped with the formatting delimiter, remove the delimiters. If not, add them.


BR-07: Syntax Highlighting (Active Block)

When a block is active (showing raw syntax), apply subtle coloring to syntax characters:

Element Color (Light) Color (Dark)
# heading prefix Gray (secondary label) Gray (secondary label)
** / __ bold delimiters Gray (secondary label) Gray (secondary label)
* / _ italic delimiters Gray (secondary label) Gray (secondary label)
` code delimiters Gray (secondary label) Gray (secondary label)
[ ] ( ) link syntax Blue (link color) Blue (link color)
> blockquote prefix Green (accent) Green (accent)
- / * list prefix Gray (secondary label) Gray (secondary label)
` ``` ` code fence Orange (accent) Orange (accent)
| table pipe Gray (secondary label) Gray (secondary label)

Use NSColor.secondaryLabelColor, NSColor.linkColor, and system accent colors for automatic light/dark adaptation.