Font Design MCP
Font Design MCP
Draw, inspect, refine, and build fonts through MCP.
A local MCP server for AI-assisted type design, from vector outlines to TTF and WOFF2.
English · Français
Get started · Connect a client · Documentation · Report an issue
Get started
Clone the repository and install the dependencies with the commands below.
Run the diagnostic and demo to generate your first font specimen.
Connect your MCP client to start designing with an agent.
Requirements: Python 3.11–3.13, uv, and a GitHub account with access to this repository. Commands work in PowerShell and POSIX shells. Install from source; this version is not published to PyPI.
git clone https://github.com/Kydaix/font-design-mcp.git
cd font-design-mcp
uv sync --frozen --python 3.11
uv run --frozen font-design-mcp doctor
uv run --frozen python examples/demo.py --workspace ./workspacedoctor checks the installed dependencies and rasterizes a PNG. Font operations run locally after installation;
the server needs no model API key or proprietary editor. The client agent may use a remote model.
The demo launches a real STDIO server through the official MCP Python SDK. It draws A, V, O, Q, acute, and Á,
sets AV kerning to −80 units, moves A's apex, compares revisions, validates, and builds both export formats.
Each run creates a new project and prints the path to specimen.html. Open it directly in a browser.
Demo output | Contents |
| Read-only previews and links to the generated fonts; no web server needed |
| The MCP calls and their structured results |
| Project, revision, source, build, and validation references |
| UFO snapshots, PNGs, TTF/WOFF2, parameters, and hashes |
Generated workspaces stay local and are ignored by Git.
Miette: a rounded typeface example
Miette Regular is an original, soft rounded font with 84 letters: uppercase and lowercase Latin, French accents, and æ/œ/Æ/Œ. Basic punctuation and spaces bring the total to 107 encoded characters. Its drawings, accent components, optical kerning, and complete MCP build recipe are included.

Download TTF · Download WOFF2 · Specimen and reproduction
Open examples/miette/specimen.html locally to type your own text, adjust its size, and compare kerning.
This first Regular style focuses on French letters; digits and additional styles are not included.
Connect a client
The MCP client launches the server process. Set an absolute interpreter path and an absolute workspace path in the client's configuration:
{
"mcpServers": {
"font-design": {
"command": "/absolute/path/font-design-mcp/.venv/bin/python",
"args": ["-m", "font_design_mcp", "serve", "--workspace", "/absolute/path/font-workspace"]
}
}
}On Windows, use C:/path/font-design-mcp/.venv/Scripts/python.exe for command and a Windows absolute path
for the workspace. The user sets this directory at launch; a tool call cannot expand it.
Add a block like this to your Codex configuration, adapting both paths:
[mcp_servers.font_design]
command = "/absolute/path/font-design-mcp/.venv/bin/python"
args = ["-m", "font_design_mcp", "serve", "--workspace", "/absolute/path/font-workspace"]
startup_timeout_sec = 20
tool_timeout_sec = 180The format follows the official Codex MCP documentation. The Windows example needs its installation-specific paths adjusted. The SDK client is tested end to end. Miette also exercised a live Codex MCP connection on Windows, including project creation, inspection, image previews, and font exports.
Windows / PowerShell:
.\.venv\Scripts\font-design-mcp.exe serve --workspace "$PWD\workspace"macOS / Linux:
.venv/bin/font-design-mcp serve --workspace "$PWD/workspace"The process waits for MCP messages on stdin. Stdout is reserved for JSON-RPC, so there is no startup banner. Logs go to stderr or captured compiler logs. Using the installed executable avoids dependency resolution at server startup. Normally, let the client start the process itself.
Image visibility depends on the client. Render tools return actual MCP image blocks, plus persistent paths, dimensions, hashes, and revisions. The client must forward those images to a model that can use them.
Design a font
The client agent makes the creative decisions; the server applies validated operations and keeps a revision history.
Step | What you can do |
Draw | Start with a brief and a few structural glyphs. Create lines, cubic and quadratic curves, counters, components, and anchors. |
Preview and refine | Inspect PNG previews with guides and handles. Move points by stable ID and compare revisions at the same sizes. |
Space and kern | Stabilize proportions, set side bearings, then adjust kerning. Test words with kerning on and off before extending the alphabet. |
Validate and export | Check geometry, coverage, and compilation. Build TTF and WOFF2 from a frozen revision. |
Record hypotheses and observed corrections in the project's decision journal.
Every call names its project. Source edits require expected_revision; stale requests fail instead of
overwriting another edit. Points and handles have stable IDs, so a correction can be as small as:
{
"op": "move_point",
"point_id": "Aouter_1",
"x": 340,
"y": 720
}Pass this operation in glyph_edit.operations with the project ID, glyph ID, and current expected revision.
A successful edit returns the new revision and changed IDs. compare_revision on either render tool shows
two revisions under the same viewing conditions.
Technical validation and the agent's judgement are distinct from human approval. The server does not assign an artistic score or accept an agent-supplied claim of authenticated human approval.
Available tools
The official MCP SDK publishes input and output schemas through tools/list. Responses include structured
data, readable summaries, revisions, warnings, and identifiable errors.
Tool | Purpose |
| Create a project with metadata, metrics, and an optional brief |
| Reopen a server-created project and verify its integrity |
| Read metadata, metrics, kerning, and a paginated glyph inventory |
| Update the brief, supported metadata, vertical metrics, or decision journal |
| Inspect contours, IDs, components, anchors, advance, bounds, and bearings |
| Apply a typed, atomic vector-editing batch to a glyph |
| Set advances, side bearings, kerning pairs, and kerning groups |
| Render a glyph with optional guides, handles, and revision comparison |
| Compile, shape, and render text at multiple sizes |
| Check geometry, Unicode coverage, compilation, and OpenType tables |
| Export TTF and/or WOFF2 from a frozen revision |
| Browse committed revisions and change summaries |
| Restore an earlier state by creating a new revision |
Exact JSON schemas · Detailed tool reference, in French
Save and restore your work
UFO 3 is the authoritative typography source. Fonts and images are derived artifacts tied to a revision:
workspace/<project_id>/
├── HEAD.json
├── revisions/<revision>/
│ ├── source.ufo/
│ └── manifest.json
└── artifacts/<artifact_id>/
├── font.ttf / font.woff2 / image.png
└── artifact.jsonEdits validate the whole project, write a complete new UFO snapshot, then atomically update the revision pointer under an OS lock. Invalid batches leave the committed state intact. Hashes detect external changes; restoration preserves existing history. Back up the entire project directory, preferably with the server stopped.
Use a private local workspace and edit snapshots through the tools. The server checks paths and UFO references, rejects symlinks/junctions and unsafe XML, and exposes no arbitrary code, shell, download, or package-installation tool. Inputs, images, geometry, compiler time, and logs are bounded. These checks are not an OS sandbox against a hostile process with the same user privileges, and snapshots are not a substitute for an external backup. Disk usage has no automatic global quota or history purge.
Coordinates use font units, baseline y=0, with Y pointing up. Advance, visible width, and side bearings are
different measurements. UPM is fixed at creation. Closed contours use non-zero filling; counters need the
opposite winding. See the architecture and recovery notes, in French for details.
Supported formats and limits
Current scope: static fonts with one master, freeform closed contours, components, anchors, and kerning. Text is shaped with HarfBuzz from a compiled TTF and rasterized with FreeType/Pillow, without system-font fallback.
Not supported in this version: OTF, variable fonts, multiple masters, arbitrary UFO/SVG import, image tracing, editor adapters, collaborative networking, and a full graphical editor. No hinting or arbitrary OpenType feature code is exposed. Text previews are single-line specimens, not paragraph layout.
Precomposed Á built from components is tested. General combining-mark positioning (mark/mkmk) and
complex-script coverage are not advertised. Source previews can differ slightly from compiled contours
after curve conversion, and unhinted FreeType output need not match native OS rendering.
Build from source
After completing Get started, build the source archive and wheel:
uv buildOutput: dist/. Dependency versions are pinned in pyproject.toml and uv.lock;
requirements.lock provides a hashed export for pip installations.
Checks
uv run --frozen pytest -q
uv run --frozen ruff check src tests scripts examples
uv run --frozen python tests/test_acceptance.pyThe standalone acceptance client retains its captures and JSON-RPC transcript under test-output/acceptance-*.
It checks actual compiled kerning, edit isolation, revision conflicts, failed atomic batches, unsafe paths,
compiler failure, restart, and interrupted writes.
Verification | Evidence |
Windows 11 x64, Python 3.11 | 21 local tests passed, including real STDIO calls, builds, rendering, recovery, and embedding defaults |
Windows, macOS, Linux runners | CI results, covering Python 3.11 and 3.13 |
Installed wheel | Entry point and full MCP demo tested in a separate environment |
The CI result covers its runner environments, not every OS version or CPU architecture. The original delivery report, in French records the local tests before CI was first run.
Documentation
English is the default README language; a French README is also maintained. The detailed guides currently remain in French, except the dependency inventory and machine-readable schemas.
Reference | Contents |
Input conventions, vector operations, spacing, results, and error codes | |
Schemas exported from a live | |
Domain, persistence, rendering, compilation, limits, and recovery | |
Original acceptance evidence, captures, and remaining visual review | |
Locked dependencies and native-library notices | |
Development environment, technical choices, and official sources |
Credits and license
Built with the official MCP Python SDK, UFO sources, HarfBuzz, and FreeType/Pillow. See dependency licenses for third-party notices.
The server code and original examples are MIT licensed. This does not automatically license fonts you create with the server. Font license metadata is empty by default and remains under the creator's control. No third-party font outlines or font files are included.
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/Kydaix/Font-Design-MCP'
If you have feedback or need assistance with the MCP directory API, please join our Discord server