# Make PDF

> Turn a Markdown report into a clean, branded A4 PDF the president can read or print. Use whenever the user asks for a report/summary/proposal "as a PDF" or "to read properly". Works fully offline on Windows using pandoc + headless Chrome/Edge — no LaTeX or extra installs needed.

- Skill: `faaz17/make-pdf` (Agent Skill, multi-file: 2 files)
- Install (CLI): `npx skillmds@latest add faaz17/make-pdf`
- Raw SKILL.md: https://api.skillmd.com/api/skills/faaz17/make-pdf/raw
- Safety review: pending
- Works with: Claude Code, Claude.ai, OpenAI Codex
- Category: Docs & Writing
- Author: Faaz17 (https://skillmd.com/u/faaz17)
- Updated: 2026-09-17
- Page: https://skillmd.com/skills/faaz17/make-pdf

---


# Make a PDF

Renders Markdown → styled HTML (pandoc) → PDF (headless Chrome). Produces
society-branded A4 output with a title page, table of contents, and per-section
page breaks. No internet, no LaTeX required.

## The two-step pipeline

Run from the society root (`Scoiety Folders/`). Give your report YAML metadata at
the top so the title page renders:

```markdown
---
title: "Report Title"
subtitle: "A subtitle in small-caps"
author: "For <Person Name>, President 2026/27"
date: "1 July 2026"
---
# First Heading
...
```

**Step 1 — Markdown → standalone HTML (CSS embedded):**

```bash
pandoc "MyReport.md" -o "MyReport.html" -s --toc --toc-depth=1 \
  -c ".claude/skills/make-pdf/report.css" --embed-resources --standalone
```

**Step 2 — HTML → PDF via headless Chrome:**

```bash
CHROME="/c/Program Files/Google/Chrome/Application/chrome.exe"   # or Edge (see below)
UDD="$TMPDIR/ea_chrome_pdf_$$"
"$CHROME" --headless=new --disable-gpu --no-first-run --no-pdf-header-footer \
  --user-data-dir="$UDD" --virtual-time-budget=15000 \
  --print-to-pdf="<project>/MyReport.pdf" \
  "file:///<project>/MyReport.html"
rm -rf "$UDD"
```

Edge works identically — swap the executable:
`/c/Program Files (x86)/Microsoft/Edge/Application/msedge.exe`.

## Gotchas (learned the hard way)

- **`--print-to-pdf` MUST be an absolute path.** A relative path resolves against
  Chrome's own directory and fails with "Access is denied." Use the full
  `C:/Users/.../file.pdf` form (forward slashes are fine on Windows).
- **The input is a `file://` URL** with spaces percent-encoded (`%20`).
- **Use a throwaway `--user-data-dir`** so it never collides with an open browser
  window (otherwise headless may attach to the running profile and skip printing).
- `--no-pdf-header-footer` removes Chrome's default URL/date header/footer; page
  margins come from `@page` in `report.css`.
- `--toc-depth=1` lists only top-level sections; raise it for finer contents.

## Verify

```bash
python -c "import re;d=open('MyReport.pdf','rb').read();print('pages~',len(re.findall(rb'/Type\s*/Page[^s]',d)),d[:8])"
```

Expect `%PDF-1.4` and a sensible page count. Clean up the intermediate `.html`
afterwards; keep the `.md` (editable source) and `.pdf` (deliverable).

## Styling

`report.css` carries the society palette (ink `#14202B`, brass `#A6803C`, ECT-blue
`#11487E`). Edit it to restyle every report at once. It targets pandoc's default
HTML structure: `header#title-block-header`, `nav#TOC`, and `h1`/`h2`/`h3`.

