Markdown Inline Editor

Typora-like Markdown editing in VS Code. Write in a clean, WYSIWYG-style view with context-aware syntax shadowing, GFM pipe tables, inline Mermaid and LaTeX math rendering, hover previews, and clickable task lists.
Your files stay 100% standard Markdown. This extension uses editor decorations — it never rewrites your document.
Why people install it
- No preview pane needed: headings, emphasis, links, images, lists, code, GFM tables, math, and Mermaid render inline where you write.
- Rendered -> Ghost -> Raw syntax shadowing: Markdown markers stay out of the way until you need them, then fade in on the active line or fully reveal for precise edits.
- GFM tables: pipe characters and cell text are drawn as an aligned grid; place the cursor anywhere in the table to reveal raw
| syntax for editing.
- Inline Mermaid and LaTeX math: render
```mermaid diagrams, $...$, $$...$$, and ```math blocks directly in the editor.
- Interactive Markdown: click task list checkboxes to toggle them, hover links to see targets, and hover images to preview them.
- Safe for real workflows: files remain plain Markdown, and diffs stay raw by default for Git, merge editor, and Copilot inline review contexts.
- Theme-aware, configurable, and fast: matches your VS Code theme, lets you tune colors/opacity/behavior, and uses a shared parse cache to avoid lag during normal editing.
Demo
Tip: move the cursor onto a line to see faint “ghost” markers; click/select to reveal raw Markdown for precise edits.
Get started
- Install:
- Open a Markdown file (
.md) to activate the extension. (It also supports editors with markdown/md/mdx language IDs once active.)
- Start typing – formatting appears inline while syntax is hidden (Rendered state).
- Move the cursor onto a line – syntax fades in for edit cues (Ghost state).
- Click/select inside formatted text – raw Markdown becomes fully visible (Raw state).
- Toggle anytime – Command Palette → Toggle Markdown Decorations (command id:
mdInline.toggleDecorations) or use the editor title bar eye icon.
Requirement: VS Code 1.88+ (Cursor is supported too).
If decorations aren’t showing, see the FAQ.
Why inline (instead of a preview pane)?
VS Code’s Markdown preview is great for reading. Markdown Inline Editor is for writing: it keeps you in the editor, reduces syntax noise, and reveals raw Markdown only where you’re editing.
Feature videos
Commands
- Toggle Markdown Decorations (
mdInline.toggleDecorations): Enable/disable inline Markdown rendering.
Recommended extensions (optional)
3-state syntax shadowing
The extension uses an intelligent 3-state syntax shadowing system that adapts syntax visibility based on your editing context:
Rendered State (Default)
- Syntax markers are hidden – see only formatted content
- Clean, distraction-free reading experience
- Example:
**bold** appears as bold with no visible markers
Ghost State (Cursor on line)
- Syntax markers appear faintly (30% opacity by default, configurable)
- Provides edit cues without cluttering the view
- Only applies to constructs on the active line, not the entire document
- Example: Cursor on a line with
**bold** shows faint ** markers
Raw State (Cursor/selection inside construct)
- Syntax markers are fully visible for direct editing
- Precise scope detection – only the specific construct you're editing shows raw
- Example: Cursor inside
**bold** reveals the full **bold** syntax
Special behavior for structural markers:
- Blockquotes, lists, and checkboxes stay fully rendered on active lines unless you directly click on the marker
- Headings show raw
# markers and remove styling when cursor is on the heading line
- Ordered list numbers always remain visible
- Tables switch the entire table to raw Markdown (all rows) when your cursor or selection is on any line inside the table
Configure ghost opacity: markdownInlineEditor.decorations.ghostFaintOpacity (default: 0.3)
Configure emoji shortcodes: markdownInlineEditor.emojis.enabled (default: true)
Supported Features
The extension supports the following Markdown (and common GitHub-flavored) features with inline rendering and syntax hiding. Formatting appears inline while syntax markers stay hidden—click any text to reveal and edit raw Markdown.
Text Formatting
Structure
Lists
- [x] Unordered Lists (
-, *, +) • Details
- [x] Task Lists (
- [ ] / - [x]) • Details
Code
Configuration
Customize (optional)
Everything works out of the box. If you want to tune the experience, open Settings and search for “Markdown Inline Editor” (all keys start with markdownInlineEditor.).
- Ghost markers visibility (
decorations.ghostFaintOpacity, default 0.3)
- Lower it for a cleaner look, raise it for stronger edit cues.
- Diff view behavior (
defaultBehaviors.diffView.applyDecorations, default false)
- Keep
false to review raw Markdown in diffs; set true if you want the same inline rendering in diffs too.
- Single-click links (
links.singleClickOpen, default false)
- Opens links/images without Ctrl/Cmd-click, but may interfere with text selection.
- Mentions & issue refs (
mentions.enabled, default true; mentions.linksEnabled, unset = infer from git remote)
- Style GitHub-style
@user / #123; optional clickable targets when forge context is available. See Mentions & references.
- Emoji shortcodes (
emojis.enabled, default true)
- Disable if you prefer seeing
:shortcode: text.
- Syntax colors (
colors.heading1 … colors.checkbox, 15 options including inlineCodeBackground)
- Optional hex overrides (e.g.
#e06c75) for headings, links, list markers, inline code, inline code background, emphasis, blockquote, image, horizontal rule, checkbox. Unset or invalid values use theme-derived defaults (for headings, unset keeps the editor’s markdown heading syntax colors rather than forcing a single foreground). See Customizable Syntax Colors.
Example settings.json
{
"markdownInlineEditor.decorations.ghostFaintOpacity": 0.25,
"markdownInlineEditor.defaultBehaviors.diffView.applyDecorations": false,
"markdownInlineEditor.links.singleClickOpen": false,
"markdownInlineEditor.emojis.enabled": true
}
Roadmap
Want to help? Pick an item below and open a PR (or add feedback in the linked issue/spec).
Work in progress
- [ ] Default feature activation – configure which features are decorated by default • Spec
Medium priority
Low priority
Getting Started (Developers)
Quick Setup (TLDR)
git clone https://github.com/SeardnaSchmid/markdown-inline-editor-vscode.git
cd markdown-inline-editor-vscode
npm install
npm run compile
npm test
Press F5 to launch the Extension Development Host and test your changes.
Dependencies
Key Technologies:
- TypeScript 5.9+ – Type-safe development
- VS Code API 1.88.0+ – Editor integration and decoration system
- remark – Markdown parser for precise AST-based parsing
- unified – AST processing framework
- remark-gfm – GitHub Flavored Markdown support
- Jest – Testing framework
Runtime Requirements:
- Node.js 20 or higher
- VS Code 1.88.0+ (or Cursor IDE)
Production Dependencies:
remark-gfm, remark-parse, unified, unist-util-visit
Development Dependencies:
- TypeScript, Jest, ESLint, VS Code extension tools
Architecture
src/
├── extension.ts # Extension entry point and activation
├── config.ts # Centralized configuration access
├── diff-context.ts # Unified diff view detection and policy
├── link-targets.ts # Unified link/image URL resolution
├── markdown-parse-cache.ts # Shared parsing and caching service
├── parser.ts # Markdown AST parsing (remark-based)
├── parser-remark.ts # Remark dependency helper
├── decorations.ts # VS Code decoration type definitions
├── decorator.ts # Decoration orchestration
├── decorator/
│ ├── decoration-type-registry.ts # Decoration type lifecycle
│ ├── visibility-model.ts # 3-state filtering logic
│ ├── checkbox-toggle.ts # Checkbox click handling
│ └── decoration-categories.ts # Decoration type categorization
├── link-provider.ts # Clickable link provider
├── link-hover-provider.ts # Hover provider for link URLs
├── image-hover-provider.ts # Hover provider for image previews
├── link-click-handler.ts # Single-click navigation handler
├── position-mapping.ts # Position mapping utilities (CRLF handling)
└── */__tests__/ # Comprehensive test suites
├── parser/__tests__/ # Parser tests
├── markdown-parse-cache/__tests__/ # Parse cache tests
├── diff-context/__tests__/ # Diff context tests
├── link-targets/__tests__/ # Link target resolution tests
├── link-provider/__tests__/ # Link provider tests
├── image-hover-provider/__tests__/ # Image hover tests
├── link-hover-provider/__tests__/ # Link hover tests
└── link-click-handler/__tests__/ # Click handler tests
How it works:
- Parser (
parser.ts) – Uses remark to parse Markdown into an AST and extract scopes
- Shared Cache (
markdown-parse-cache.ts) – Single parse cache instance shared across all components
- Decorator (
decorator.ts) – Orchestrates decoration management with 3-state syntax shadowing
- Scope-based detection – Precisely identifies markdown constructs for context-aware syntax visibility
- 3-state model – Rendered (hidden), Ghost (faint), Raw (visible) states adapt to editing context
- Hover providers – Show image previews and link URLs on hover (use shared cache)
- Click handler – Optional single-click navigation for links and images (uses shared cache)
Testing
The project maintains comprehensive test coverage with 560+ passing tests across 40+ test suites:
- Parser tests (
parser/__tests__/) – Core markdown parsing logic (including GFM tables, math, Mermaid regions)
- Parse cache tests (
markdown-parse-cache/__tests__/) – Shared caching and LRU eviction
- Diff context tests (
diff-context/__tests__/) – Diff view detection and policy
- Link target tests (
link-targets/__tests__/) – Link/image URL resolution
- Image hover provider tests (
image-hover-provider/__tests__/) – Image preview hover functionality
- Link hover provider tests (
link-hover-provider/__tests__/) – Link URL hover functionality
- Link click handler tests (
link-click-handler/__tests__/) – Single-click navigation behavior
- Link provider tests (
link-provider/__tests__/) – Clickable link provider functionality
Run tests with npm test or npm run test:watch for development.
Installing
npm install
Key Commands
| Command |
Description |
npm run compile |
Compile TypeScript to JavaScript |
npm run bundle |
Bundle with esbuild |
npm test |
Run all tests |
npm run test:watch |
Run tests in watch mode |
npm run test:coverage |
Generate coverage report |
npm run lint |
Run ESLint |
npm run validate |
Run docs lint + tests + build |
npm run package |
Create .vsix package |
npm run clean |
Clean build artifacts |
npm run build |
Full build (compile + bundle + package) |
npm run release |
Automated release workflow |
Executing
Option 1: VS Code Launch Configuration
Create .vscode/launch.json with the extension host configuration, then press F5 to launch the Extension Development Host.
Option 2: Manual Build & Test
npm run compile
npm run package
code --install-extension dist/extension.vsix
Contributing
Contributions are welcome! This project follows Conventional Commits and maintains high code quality standards.
Quick Start
git checkout -b feat/my-feature
# Make changes, write tests
npm test && npm run lint
git commit -m "feat(parser): add support for definition lists"
Contribution Guidelines (TLDR)
- Read first:
CONTRIBUTING.md for detailed workflow
- Code style: TypeScript strict mode, JSDoc comments, comprehensive tests
- Commit format:
<type>(<scope>): <description>
- Types:
feat, fix, docs, style, refactor, perf, test, chore
- Testing: All changes must include tests
- Performance: No regressions – maintain efficient code execution
See CONTRIBUTING.md for full contribution guidelines and AGENTS.md for agent roles and architecture details.
Known Limitations & Reporting Bugs
Known Limitations
Reporting Bugs
If you encounter an issue not covered in the FAQ, please open an issue with:
- VS Code version
- Extension version
- Steps to reproduce
- Expected vs. actual behavior
- Screenshots/GIFs if applicable
For common issues and solutions, see the FAQ.
License
MIT License – See LICENSE.txt
Acknowledgments
Special thanks to these projects, which inspired or enabled this extension:
Contributors