SNIPPET
praxstackMarkdown Viewer App
Production-ready markdown viewer with real-time preview, syntax highlighting, Mermaid diagrams, and 10 professional themes
2 Stars
GitHubCSSAny theme
# ๐ Markdown Viewer Pro
**A professional markdown viewer with modular architecture, comprehensive testing, and scalable design patterns.**
[](./tests)
[]()
[]()
[]()
[](https://github.com/sponsors/PrakharMNNIT)
[](https://ko-fi.com/praxlannister)
[](https://razorpay.me/@prakharshekharparthasarthi)
---
## โจ Features
### Core Functionality
- ๐ **Real-time Markdown Preview** - Instant rendering as you type
- ๐จ **12 Beautiful Themes** - 6 themes ร 2 variants (light/dark) including Nebula theme
- ๐ฏ **Syntax Highlighting** - 20+ programming languages supported via PrismJS
- ๐ **Mermaid Diagrams** - Flowcharts, sequences, class diagrams, and more
- โ **LaTeX Math Support** - Full KaTeX rendering with `$...$`, `$$...$$`, `\(...\)`, and `\[...\]` delimiters
- ๐จ **Custom Theme Builder** - Create and save your own color schemes
- ๐ค **Export Options** - HTML and PDF with theme preservation
- ๐๏ธ **View Modes** - Editor-only, split-view, or preview-only
- ๐ **Zoom Controls** - Scale preview from 50% to 200%
- ๐พ **Auto-save** - Content automatically saved to localStorage
### ๐ Folder Browser (NEW)
- ๐ **Open Folder** - Browse and open local folders with markdown files
- ๐๏ธ **File Tree** - Navigate through nested directories
- ๐ **Quick File Access** - Click to open any markdown file
- โ **Create Files** - Create new markdown files with templates (empty, basic, readme, notes, blog)
- ๐ **Folder Refresh** - Refresh folder contents without reopening
- ๐ **Resizable Sidebar** - Drag to resize, auto-collapse at edge
- โก๏ธ **Expand Button** - Quick sidebar expand with premium animations
- ๐พ **State Persistence** - Sidebar width and collapsed state saved
### ๐ง Zen Mode (NEW)
- ๐ฅ๏ธ **Full Screen Preview** - 100% width and height distraction-free reading
- ๐ซ **Hidden UI** - Toolbar, sidebar, and footer hidden
- โจ๏ธ **ESC to Exit** - Press Escape or click exit button to return
- ๐ **Centered Content** - Max-width 900px for optimal readability
### โ๏ธ Split View Resizer (NEW)
- ๐ **Draggable Divider** - Resize editor and preview panels
- ๐ **Custom Ratio** - Set 20% to 80% split ratio
- ๐พ **Ratio Persistence** - Split position saved across sessions
- ๐จ **Visual Feedback** - Animated handles on hover/drag
### ๐ TOC Anchor Navigation (NEW)
- ๐ **Click-to-Navigate** - Click TOC links to smooth scroll to headings
- ๐ฏ **Smart Targeting** - 4-priority resolution (exact โ normalized โ GitHub โ fuzzy)
- ๐ **Browser History** - Back/forward navigation support
- โฟ **Accessibility** - Focus management and keyboard navigation
- ๐ค **Special Characters** - C++ โ cpp, C# โ csharp handling
- ๐ **Deep Linking** - Direct URL hash support
### Professional Architecture
- ๐๏ธ **Modular Design** - 9 organized modules with clear separation of concerns
- ๐งช **Comprehensive Testing** - 155+ tests with >85% coverage
- ๐ง **Modern Tooling** - Vite, Vitest, ESLint, Prettier
- ๐ **Design Patterns** - Service layer, observer, dependency injection
- ๐ฏ **Zero Technical Debt** - Clean, maintainable, production-ready code
- ๐ค **AI Code Review** - Automated quality checks with every commit
- ๐ **Safari Compatible** - Enterprise-grade CSS loading for all browsers
- ๐ฑ **Mobile Responsive** - Optimized for iPhone/iPad/Android
---
## ๐ Project Structure
```
markdown-viewer-app/
โโโ index.html # Main HTML file
โโโ style.css # Base styles
โโโ script.js # Main application entry (~2300 lines)
โโโ animations.css # Premium animations
โโโ variables.css # CSS custom properties
โโโ package.json # Dependencies and scripts
โโโ vite.config.js # Vite configuration
โโโ vitest.config.js # Vitest configuration
โโโ .eslintrc.js # ESLint rules
โโโ .prettierrc # Prettier configuration
โ
โโโ src/js/ # Source modules
โ โโโ config/ # Configuration files
โ โ โโโ constants.js # App constants (12 groups)
โ โ โโโ errorMessages.js # Centralized error messages
โ โ โโโ featureFlags.js # Feature flag system
โ โ
โ โโโ utils/ # Utility functions
โ โ โโโ htmlHelpers.js # HTML manipulation (4 functions)
โ โ โโโ colorHelpers.js # CSS variable helpers (6 functions)
โ โ โโโ validators.js # Input validation (5 functions)
โ โ
โ โโโ services/ # Business logic services
โ โ โโโ FolderBrowserService.js # File system access (NEW)
โ โ โโโ HTMLService.js # HTML export
โ โ โโโ MermaidService.js # Mermaid diagram rendering
โ โ โโโ PDFService.js # PDF export with preview
โ โ โโโ PrismService.js # Syntax highlighting
โ โ
โ โโโ core/ # Core application modules
โ โโโ StorageManager.js # LocalStorage abstraction (11 methods)
โ โโโ ThemeManager.js # Theme management (11 methods)
โ
โโโ tests/ # Test suite (155+ tests)
โ โโโ setup.js # Test configuration
โ โโโ baseline/ # Baseline functionality tests (98)
โ โ โโโ current-functionality.test.js
โ โโโ unit/ # Unit tests (57+)
โ โโโ config/ # Config tests
โ โ โโโ errorMessages.test.js
โ โโโ services/ # Service tests
โ โ โโโ FolderBrowserService.test.js
โ โ โโโ MermaidService.test.js
โ โ โโโ PrismService.test.js
โ โโโ core/ # Core module tests
โ โ โโโ StorageManager.test.js
โ โ โโโ ThemeManager.test.js
โ โโโ utils/ # Utility tests
โ โโโ colorHelpers.test.js
โ โโโ validators.test.js
โ
โโโ themes/ # Theme files (15 files)
โ โโโ default-light.css # Professional light theme
โ โโโ default-dark.css # GitHub-inspired dark theme
โ โโโ ocean-light.css # Fresh cyan theme
โ โโโ ocean-dark.css # Deep navy theme
โ โโโ neon-light.css # Vibrant purple theme
โ โโโ neon-dark.css # Cyberpunk theme
โ โโโ forest-light.css # Natural green theme
โ โโโ forest-dark.css # Deep forest theme
โ โโโ sunset-light.css # Warm orange theme
โ โโโ sunset-dark.css # Sunset theme
โ โโโ obsidian-light.css # Clean minimal theme
โ โโโ obsidian-dark.css # Dark minimal theme
โ โโโ nebula-light.css # Cosmic purple theme (NEW)
โ โโโ nebula-dark.css # Deep space theme (NEW)
โ โโโ nebula-elements.css # Shared Nebula elements
โ
โโโ docs/ # Documentation
โโโ 01-requirements/ # Feature specifications
โโโ 02-architecture/ # Architecture docs
โโโ 05-implementation/ # Implementation guides
โโโ 08-deployment/ # Deployment guides
โโโ 09-temp/ # Temporary docs
```
---
## ๐ Quick Start
### Prerequisites
- Node.js 18+ and npm
- Modern browser (Chrome 86+, Firefox 90+, Safari 14+, Edge 86+)
### Installation
```bash
# Clone the repository
git clone https://github.com/PrakharMNNIT/markdown-viewer-app.git
cd markdown-viewer-app
# Install dependencies
npm install
# Start development server
npm run dev
```
### Usage
1. Open your browser to `http://localhost:5173`
2. Start typing markdown in the left panel
3. See live preview on the right
4. **Open Folder** - Click to browse local markdown files
5. **Zen Mode** - Click for distraction-free reading
6. Switch themes from the dropdown
7. Customize colors with the theme builder
8. Export to HTML or PDF
### Keyboard Shortcuts
| Shortcut | Action |
| -------------- | ------------- |
| `Ctrl/Cmd + +` | Zoom in |
| `Ctrl/Cmd + -` | Zoom out |
| `Ctrl/Cmd + 0` | Reset zoom |
| `Escape` | Exit Zen Mode |
---
## ๐ ๏ธ Development
### Available Scripts
```bash
# Development
npm run dev # Start Vite dev server with hot reload
npm run build # Build production bundle
npm run preview # Preview production build
# Testing
npm test # Run all tests (155+ tests)
npm run test:ui # Open Vitest UI dashboard
npm run test:coverage # Generate coverage report
# Code Quality
npm run lint # Check code with ESLint
npm run format # Format code with Prettier
npm run review # Run AI code review
```
### Development Workflow
1. **Make changes** to source files
2. **Run tests**: `npm test` (ensure all pass)
3. **Check quality**: `npm run lint`
4. **AI review**: `npm run review` (analyze AI_REVIEW.md)
5. **Commit**: Use conventional commit format
---
## ๐๏ธ Architecture
### Design Patterns
- **Service Layer Pattern** - Isolated business logic (MermaidService, PrismService, FolderBrowserService)
- **Observer Pattern** - Theme change notifications to dependent services
- **Dependency Injection** - ThemeManager receives StorageManager instance
- **Facade Pattern** - Clean API abstractions for complex operations
- **Strategy Pattern** - Pluggable theme loading strategies
- **Singleton Pattern** - Anchor navigation heading slug map
### Module Organization
#### **config/** - Configuration and Constants
- `constants.js`: 12 constant groups (ZOOM, STORAGE_KEYS, THEMES, etc.)
- `errorMessages.js`: Centralized error message definitions
- `featureFlags.js`: Feature toggle system for safe rollouts
#### **utils/** - Reusable Utilities
- `htmlHelpers.js`: DOM manipulation, blob URLs, file downloads
- `colorHelpers.js`: CSS variable getters/setters
- `validators.js`: Input validation and constraints
#### **services/** - Business Logic
- `FolderBrowserService.js`: File System Access API integration
- `HTMLService.js`: HTML export with theme embedding
- `MermaidService.js`: Theme-aware diagram rendering (5 methods)
- `PDFService.js`: PDF generation with html2pdf.js
- `PrismService.js`: Syntax highlighting with error recovery (5 methods)
#### **core/** - Core Modules
- `StorageManager.js`: LocalStorage abstraction with error handling (11 methods)
- `ThemeManager.js`: Theme loading, switching, and persistence (11 methods)
### Integration Points
```javascript
// Main application entry (script.js)
import { StorageManager } from './src/js/core/StorageManager.js';
import { ThemeManager } from './src/js/core/ThemeManager.js';
import { MermaidService } from './src/js/services/MermaidService.js';
import { PrismService } from './src/js/services/PrismService.js';
import { FolderBrowserService } from './src/js/services/FolderBrowserService.js';
import { PDFService } from './src/js/services/PDFService.js';
import { HTMLService } from './src/js/services/HTMLService.js';
// Initialize with dependency injection
const storageManager = new StorageManager();
const themeManager = new ThemeManager(storageManager);
const mermaidService = new MermaidService();
const prismService = new PrismService();
const folderBrowserService = new FolderBrowserService(storageManager);
const pdfService = new PDFService();
const htmlService = new HTMLService();
// Configure observer pattern
themeManager.setThemeChangeListener(() => {
mermaidService.reinitialize();
});
```
---
## ๐งช Testing
### Test Coverage
- **Total Tests**: 155+ (all passing โ
)
- **Baseline Tests**: 98 (functional integrity)
- **Unit Tests**: 57+ (module-specific)
- Services: 23+ tests
- Core: 34 tests
- Utils: 20+ tests
- Config: 5+ tests
- **Coverage**: >85% across all modules
### Test Structure
```bash
tests/
โโโ baseline/
โ โโโ current-functionality.test.js # 98 integration tests
โโโ unit/
โโโ config/
โ โโโ errorMessages.test.js
โโโ services/
โ โโโ FolderBrowserService.test.js
โ โโโ MermaidService.test.js
โ โโโ PrismService.test.js
โโโ core/
โ โโโ StorageManager.test.js
โ โโโ ThemeManager.test.js
โโโ utils/
โโโ colorHelpers.test.js
โโโ validators.test.js
```
### Running Tests
```bash
# Run all tests
npm test
# Run with coverage
npm run test:coverage
# Open interactive UI
npm run test:ui
# Watch mode
npm test -- --watch
```
---
## ๐จ Themes
### Available Themes
| Theme | Light | Dark | Best For |
| ---------------- | ----- | ---- | ------------------------------------- |
| **Default** | โ
| โ
| Professional documents, general use |
| **Ocean** | โ
| โ
| Technical content, calming atmosphere |
| **Neon** | โ
| โ
| Creative work, presentations |
| **Forest** | โ
| โ
| Environmental content, natural topics |
| **Sunset** | โ
| โ
| Warm content, personal writing |
| **Obsidian** | โ
| โ
| Clean minimal design, focus mode |
| **Nebula** (NEW) | โ
| โ
| Cosmic themes, sci-fi content |
### Creating Custom Themes
#### Method 1: Visual Customizer
1. Click "๐จ Customize Colors"
2. Adjust colors with color pickers
3. Click "Save Custom Theme"
#### Method 2: CSS File
1. Copy existing theme file
2. Modify color values
3. Add to dropdown in `index.html`
```css
:root {
/* Backgrounds */
--bg-primary: #ffffff;
--bg-secondary: #f8f9fa;
/* Text */
--text-primary: #212529;
/* Headers */
--h1-color: #2563eb;
--h2-color: #7c3aed;
/* Elements */
--link-color: #2563eb;
--code-bg: #f1f5f9;
--blockquote-border: #7c3aed;
}
```
---
## ๐ฑ Browser Compatibility
| Browser | Version | Status |
| ---------- | ------- | ------------------------------------ |
| Chrome | 86+ | โ
Full support |
| Firefox | 90+ | โ
Full support (no folder browser) |
| Safari | 14+ | โ
Full support (enterprise CSS fix) |
| Edge | 86+ | โ
Full support |
| Safari iOS | 14+ | โ
Mobile optimized |
**Note**: Folder Browser feature requires File System Access API (Chrome/Edge 86+)
---
## ๐ API Reference
### FolderBrowserService (NEW)
```javascript
const folderService = new FolderBrowserService(storageManager);
// Check support
if (folderService.isSupported()) {
// Open folder dialog
const result = await folderService.openFolder();
// result: { success, files, folderName, totalFiles }
// Read file
const fileResult = await folderService.readFile(fileHandle);
// fileResult: { success, content, name, size }
// Create new file
const createResult = await folderService.createFile(dirHandle, filename, content);
// createResult: { success, filename, fileHandle }
// Refresh folder
const refreshResult = await folderService.refreshFolder();
}
```
### StorageManager
```javascript
const storage = new StorageManager();
// Basic operations
storage.set('key', 'value'); // Store string
const value = storage.get('key'); // Retrieve string
storage.remove('key'); // Remove item
storage.has('key'); // Check existence
// JSON operations
storage.setJSON('data', { a: 1 }); // Store object
const obj = storage.getJSON('data'); // Retrieve object
// Utility methods
storage.getAllKeys(); // Get all keys
storage.getSize(); // Storage size in bytes
storage.clear(); // Clear all (USE WITH CAUTION)
storage.isAvailable(); // Check localStorage availability
```
### ThemeManager
```javascript
const themeManager = new ThemeManager(storageManager);
// Theme operations
await themeManager.loadTheme('ocean-dark'); // Load theme
themeManager.saveCustomTheme({ '--h1': '#f00' }); // Save custom
const current = themeManager.getCurrentTheme(); // Get current name
const colors = themeManager.getCurrentColors(); // Get all colors
// Observer pattern
themeManager.setThemeChangeListener(themeName => {
console.log('Theme changed to:', themeName);
});
// Utility methods
const themes = themeManager.getAvailableThemes(); // List all themes
const exists = themeManager.themeExists('neon-dark'); // Check existence
```
### MermaidService
```javascript
const mermaidService = new MermaidService();
// Initialize with current theme
mermaidService.initialize();
// Render diagram
const svg = await mermaidService.render(
'diagram-1',
`
graph TD
A[Start] --> B[Process]
B --> C[End]
`
);
// Check readiness and reinitialize
if (mermaidService.isReady()) {
mermaidService.reinitialize(); // Call after theme change
}
```
### PDFService (NEW)
```javascript
const pdfService = new PDFService();
// Generate PDF with options
const blob = await pdfService.generatePDF(previewElement, {
pageSize: 'A4',
orientation: 'portrait',
margins: [10, 10, 10, 10],
fontSize: 12,
});
// Preview PDF in iframe
const url = await pdfService.previewPDF(previewElement, config);
// Download PDF
pdfService.downloadPDF();
```
---
## ๐ค Contributing
### Code Standards
- **ES6+ JavaScript** with module imports
- **JSDoc comments** for all public methods
- **Conventional Commits** for commit messages
- **Zero warnings** from ESLint
- **Prettier formatting** enforced
- **100% test pass rate** required
### Commit Message Format
```
<emoji> <type>(<scope>): <description>
[optional body]
[optional footer]
```
**Types**: `feat`, `fix`, `docs`, `style`, `refactor`, `perf`, `test`, `build`, `ci`, `chore`
**Emojis**:
- โจ `feat` - New feature
- ๐ `fix` - Bug fix
- ๐ `docs` - Documentation
- โป๏ธ `refactor` - Code refactoring
- โ
`test` - Tests
- ๐ง `chore` - Maintenance
**Example**:
```
โจ feat(browser): add file creation with templates
- Implement createFile method in FolderBrowserService
- Add 5 templates (empty, basic, readme, notes, blog)
- Add create file modal with form validation
- Add unit tests for new functionality
Closes #45
```
### Pull Request Process
1. Fork the repository
2. Create feature branch (`git checkout -b feature/amazing-feature`)
3. Make changes with tests
4. Run `npm test` (all must pass)
5. Run `npm run lint` (zero warnings)
6. Run `npm run review` (address AI feedback)
7. Commit with conventional format
8. Push to branch
9. Open Pull Request
---
## ๐ Troubleshooting
### Common Issues
**Tests failing?**
```bash
npm test -- --reporter=verbose # Detailed output
```
**Linting errors?**
```bash
npm run lint -- --fix # Auto-fix issues
```
**Build errors?**
```bash
rm -rf node_modules package-lock.json
npm install
npm run build
```
**Theme not loading?**
- Check browser console for errors
- Verify theme file exists in `themes/`
- Clear browser cache
**Mermaid diagrams not rendering?**
- Check internet connection (CDN required)
- Verify diagram syntax
- Check browser console for errors
**Folder Browser not working?**
- Requires Chrome 86+ or Edge 86+
- Firefox/Safari don't support File System Access API
- Check for permission prompts
**PDF export fails on Safari?**
- This is fixed in the latest version
- Uses fallback colors for Safari compatibility
---
## ๐ Performance
- **Bundle Size**: <500KB (gzipped) - includes Mermaid, KaTeX, Prism
- **First Paint**: <500ms
- **Time to Interactive**: <1s
- **Lighthouse Score**: 95+
---
## ๐ Security
- No dependencies with known vulnerabilities
- Input sanitization via DOMPurify
- XSS prevention with proper encoding
- CSP headers recommended for production
- Regular security audits with `npm audit`
- File system access scoped to selected folders only
---
## ๐ License
MIT License - See LICENSE file for details
---
## ๐ Acknowledgments
- [Marked.js](https://marked.js.org/) - Markdown parsing
- [Prism.js](https://prismjs.com/) - Syntax highlighting
- [Mermaid.js](https://mermaid-js.github.io/) - Diagram rendering
- [KaTeX](https://katex.org/) - LaTeX math rendering
- [html2pdf.js](https://github.com/eKoopmans/html2pdf.js) - PDF generation
- [DOMPurify](https://github.com/cure53/DOMPurify) - HTML sanitization
- [Vite](https://vitejs.dev/) - Build tooling
- [Vitest](https://vitest.dev/) - Testing framework
---
## ๐ Support
- ๐ [Documentation](./docs/README.md)
- ๐๏ธ [Architecture Guide](./docs/02-architecture/architecture.md)
- ๐ [Issue Tracker](https://github.com/PrakharMNNIT/markdown-viewer-app/issues)
- ๐ฌ [Discussions](https://github.com/PrakharMNNIT/markdown-viewer-app/discussions)
---
---
## ๐ Support This Project
If you find Markdown Viewer Pro useful, consider supporting its development:
[](https://github.com/sponsors/PrakharMNNIT)
[](https://ko-fi.com/praxlannister)
[](https://razorpay.me/@prakharshekharparthasarthi)
### Support Tiers
| Tier | Amount (USD) | Amount (INR) | Perks |
| ----------- | ------------ | ------------ | --------------------- |
| โ Coffee | $1 | โน50 | My gratitude! |
| ๐ Pizza | $5 | โน250 | Name in SUPPORTERS.md |
| ๐ Patron | $20 | โน1000 | Name in README |
| ๐ Champion | $50+ | โน2500+ | Logo in README |
Your support helps maintain and improve this project. Every contribution is appreciated! ๐
---
**Built with โค๏ธ using modern JavaScript, comprehensive testing, and scalable architecture.**
**Status**: Production-ready โ
| Tests: 155+/155+ passing โ
| Technical Debt: Zero โ
How to Install
- Download the CSS file below
- Move it to your vault's
.obsidian/snippets/folder - Open Obsidian โ Settings โ Appearance โ CSS Snippets โ Enable it
Stats
Stars
2
Forks
0
Last updated 1mo ago