Convert Markdown to PDF with full support for images, SVG, HTML, LaTeX math, and syntax highlighting
Project description
📄 MD → PDF
Convert Markdown to polished PDFs — CLI, desktop GUI, or Python API.
Powered by Playwright (Chromium headless) for PDF generation and pywebview for the optional desktop GUI.
⚠️ Important Note (Linux users)
The CLI works out-of-the-box using Playwright (no system GUI dependencies required).
However, the desktop GUI requires a system GUI backend (Qt or GTK) on Linux.
If the GUI fails to start, you likely need to install additional system libraries.
✨ Features
| Category | What's supported |
|---|---|
| Text | Headings, bold, italic, strikethrough, highlight, superscript, subscript |
| Code | Fenced blocks with syntax highlighting (Monokai), inline code, line numbers |
| Images | Local files auto-embedded as base64 · SVG inline rendering |
| Math | LaTeX via Arithmatex ($...$ / $$...$$) |
| Tables | GitHub-style with alternating rows |
| Lists | Ordered · unordered · task lists with checkboxes |
| Callouts | Blockquotes · admonitions (info / warning / danger / tip) · <details> |
| Diagrams | Mermaid (rendered by Chromium at export time) |
| Structure | Table of contents · footnotes · definition lists · abbreviations · \newpage |
| Extras | Emoji · keyboard keys (<kbd>) · magic links · smart symbols |
📦 Installation
Recommended (isolated environment)
python -m venv .venv
source .venv/bin/activate
pip install -e .
Alternative (recommended for CLI tools)
pipx install .
🌐 Install browser (required)
This project uses Playwright to download Chromium:
md-to-pdf --install-browser
Browser binaries are cached by Playwright in:
- Linux/macOS:
~/.cache/ms-playwright - Windows:
%LOCALAPPDATA%\ms-playwright
🐧 Linux system dependencies
Playwright requires system libraries for Chromium:
sudo apt update && sudo apt install -y \
libatk1.0-0 libatk-bridge2.0-0 libcups2 libdbus-1-3 libexpat1 libgbm1 \
libpango-1.0-0 libpangocairo-1.0-0 libx11-6 libx11-xcb1 libxcb1 \
libxcomposite1 libxcursor1 libxdamage1 libxext6 libxfixes3 libxi6 \
libxinerama1 libxrandr2 libxrender1 libxss1 libxtst6 libxkbcommon0
Then:
pip install -e .
md-to-pdf --install-browser
🖥️ GUI dependencies (Linux only)
The GUI uses pywebview, which requires a native backend.
Option A — Qt (recommended)
pip install pyqt6 PyQt6-WebEngine qtpy
sudo apt install libxcb-cursor0
Option B — GTK (alternative)
sudo apt install python3-gi gir1.2-gtk-3.0
pip install PyGObject
🔧 If GUI fails to start
Force Qt backend:
PYWEBVIEW_GUI=qt md-to-pdf
🚀 Usage
GUI mode
md-to-pdf
or
md-to-pdf --gui
Drop a .md file onto the window (or click Open), adjust settings in the sidebar,
and click Convert to PDF. Output directory, page size, and custom CSS are remembered
between sessions.
CLI mode
md-to-pdf document.md # output: document.pdf (same dir)
md-to-pdf document.md -o ~/exports/out.pdf
md-to-pdf document.md --page-size Letter
md-to-pdf document.md --css custom.css --title "My Report"
CLI Options
| Flag | Default | Description |
|---|---|---|
-o, --output |
<input>.pdf |
Output path |
--page-size |
A4 |
A4 · A3 · A5 · Letter · Legal |
--css |
built-in | Path to a CSS file to override styles |
--title |
filename stem | PDF document title |
--gui |
— | Launch the desktop GUI |
--install-browser |
— | Download Chromium (run once after install) |
-v, --verbose |
— | Verbose logging |
🐍 Python API
from pathlib import Path
from md_to_pdf.renderer import md_to_pdf
from md_to_pdf.css import load_default_css
md_to_pdf(
Path("document.md"),
Path("output.pdf"),
css_content=load_default_css(),
title="My Document",
page_size="A4",
)
🧱 Project Structure
md_to_pdf/
├── __main__.py — CLI entry point + GUI dispatch
├── converter.py — Markdown → HTML (python-markdown + pymdownx)
├── renderer.py — HTML → PDF via Playwright (Chromium headless)
├── css.py — Default print stylesheet (GitHub-inspired)
├── settings.py — Persistent GUI preferences (JSON, per-OS config dir)
└── gui.py — Desktop GUI (pywebview)
tests/
├── fixtures/ — Sample .md files for testing
├── test_converter.py
├── test_renderer.py
└── test_settings.py
🛠️ Development
pip install -e ".[dev]"
pytest
ruff check .
📌 Notes
- CLI mode uses Playwright only
- GUI mode requires Qt or GTK on Linux
- Windows/macOS generally work without extra system packages
- Qt is preferred if multiple GUI backends are installed
- If GUI fails, force backend with PYWEBVIEW_GUI=qt
License
MIT
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file md_to_pdf_costamagnus-1.0.0.tar.gz.
File metadata
- Download URL: md_to_pdf_costamagnus-1.0.0.tar.gz
- Upload date:
- Size: 22.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
794a02682001d46606095a96fea3db690c589ed0400430967b23b2566a55d9b0
|
|
| MD5 |
bed3185823ea6b1a8b3377d33f5d7c3d
|
|
| BLAKE2b-256 |
cd7dbab7b7844fca9dd836b9a36dd9e5f3da2b39a9c20d8b5d19aa1905a293c5
|
Provenance
The following attestation bundles were made for md_to_pdf_costamagnus-1.0.0.tar.gz:
Publisher:
publish.yml on matiascostamagna/md-to-pdf
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
md_to_pdf_costamagnus-1.0.0.tar.gz -
Subject digest:
794a02682001d46606095a96fea3db690c589ed0400430967b23b2566a55d9b0 - Sigstore transparency entry: 1397579273
- Sigstore integration time:
-
Permalink:
matiascostamagna/md-to-pdf@c55fb1d2263ec1f367147c442a290884ebebb67c -
Branch / Tag:
refs/heads/main - Owner: https://github.com/matiascostamagna
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@c55fb1d2263ec1f367147c442a290884ebebb67c -
Trigger Event:
workflow_dispatch
-
Statement type:
File details
Details for the file md_to_pdf_costamagnus-1.0.0-py3-none-any.whl.
File metadata
- Download URL: md_to_pdf_costamagnus-1.0.0-py3-none-any.whl
- Upload date:
- Size: 20.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b2da9dbcb7b058949465bb42374022e52ae4e5ca206ff3c5b028225540be2e4e
|
|
| MD5 |
dfed1641d0b8b618e9e4a50cbc71ea52
|
|
| BLAKE2b-256 |
21152f19a70210375069866f3b85a2c95e2ee9bd7813be0422913d791c474b90
|
Provenance
The following attestation bundles were made for md_to_pdf_costamagnus-1.0.0-py3-none-any.whl:
Publisher:
publish.yml on matiascostamagna/md-to-pdf
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
md_to_pdf_costamagnus-1.0.0-py3-none-any.whl -
Subject digest:
b2da9dbcb7b058949465bb42374022e52ae4e5ca206ff3c5b028225540be2e4e - Sigstore transparency entry: 1397579280
- Sigstore integration time:
-
Permalink:
matiascostamagna/md-to-pdf@c55fb1d2263ec1f367147c442a290884ebebb67c -
Branch / Tag:
refs/heads/main - Owner: https://github.com/matiascostamagna
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@c55fb1d2263ec1f367147c442a290884ebebb67c -
Trigger Event:
workflow_dispatch
-
Statement type: