Text to Handwriting AI
Turn typed text into realistic handwritten pages, or build a complete handwritten assignment, with a filled-in front page and AI-drafted answers.
Maintained by CodewithWitcher. Contributions are welcome. See CONTRIBUTING.md.
Use it
| Option | How | Best for |
|---|---|---|
| Online | Open https://codewithwitcher.github.io/Text-To-Handwritten-With-AI/ | Trying it out, nothing to install |
| One command (Python) | pipx run text-to-handwriting-ai or uvx text-to-handwriting-ai (Python 3.8+) |
Every AI provider, fully on your machine |
| One command (Node) | npx text-to-handwriting-ai (Node.js 18+) |
Same, if you have Node instead of Python |
| From source | Clone the repo, then npm start or python3 server.py |
Contributing |
Your data stays in your browser in every option. The online version calls AI providers straight from your browser. Claude and DeepSeek allow that, but some providers block it (CORS). If a provider fails online, use the one-command option: it runs a small local relay that works with all of them.
Two modes
Use the switch at the top of the page.
Classic
The original quick converter. Type or paste text, choose a font, ink and paper, then generate images or a PDF.
Advanced (AI)
A guided, four-step flow:
-
Template & handwriting. Pick an assessment template (Q&A, short answers, detailed answers, essay, lab report, case study, or your own). Choose a font or upload your own
.ttf, then set ink colours for answers and headings, heading style, ruled lines, margin, and natural variation (small per-word tilt so it doesn't look like a font). A live preview updates as you change things. -
Front page (optional). Upload your university or college front page (image or PDF). Auto-detect uses OCR to find blanks such as "Name:", "Roll No.:" and "Subject:", then writes your details in your handwriting. Smart detect (AI) lets the AI decide which blank is which. Drag any value to fine-tune it, and save the layout to reuse next time.
-
Questions & answers. Choose one of three sources:
- Upload the question paper (PDF). The AI lists every question with its marks. Scanned PDFs are read with OCR, or directly by Claude.
- Paste the questions.
- Write or paste your own content. No AI is needed. Use simple formatting for headings and lists.
Then generate the answers one by one with AI. Answer length follows the marks and the template. You can edit, regenerate or reorder anything. No API key? Click Copy prompt, paste it into ChatGPT, Claude.ai or DeepSeek, paste the reply back, and click Import answers.
-
Preview & download. Text flows across A4 pages: words are never cut, and headings are never left alone at the bottom of a page. Edit the final text if you like, then download one PDF (front page first) or the individual page images.
My Profile stores your name, roll number, course, subject and other details in this browser. To fill it from a file, click Download profile template, fill in the JSON in any text editor, then Import profile. AI Settings supports Claude, DeepSeek, OpenAI, Google Gemini, OpenRouter, Groq, Ollama (local, no key) and any OpenAI-compatible endpoint.
Run locally
One command, no clone. Use whichever you have:
pipx run text-to-handwriting-ai # Python (pipx)
uvx text-to-handwriting-ai # Python (uv)
npx text-to-handwriting-ai # Node.js
Each one opens http://127.0.0.1:8080 in your browser. Options: --port 9000, --no-open, --host 0.0.0.0 (to reach it from other devices on your network).
To keep it installed instead: pip install text-to-handwriting-ai, then run text-to-handwriting-ai.
From a clone (no dependencies needed to run):
npm start # Node 18+
python3 server.py # or Python 3.8+, same behaviour
Both serve the app and relay AI requests to the provider you choose, so browsers don't block them (CORS). If the port is busy, the next free one is used.
macOS: port 5000 is taken by AirPlay Receiver, which is why the default is 8080.
Privacy
- Everything you enter (profile, templates, fonts, front pages, drafts, API keys) is stored only in this browser (localStorage and IndexedDB).
- API keys are sent only to the provider you select. When the local server relays a request, it doesn't store or log keys or content.
- Only academic context (course, subject, semester) is included in AI prompts. Your name and ID numbers are never sent.
- My Profile → Delete all saved data wipes everything. Data exports never include API keys.
Content formatting
Own content and the final text step use this formatting:
| Write | Result |
|---|---|
# Title |
Centered title |
## Heading |
Question / section heading |
### Sub-heading |
Sub-heading |
- item / 1. item |
Bullet / numbered list |
**text** |
Underlined emphasis |
| blank line | New paragraph |
--- |
New page |
Project structure
index.html Page shell: Classic markup + Advanced markup
bin/cli.mjs `npx text-to-handwriting-ai` launcher (Node, no deps)
text_to_handwriting_ai/ Same server + AI relay in Python (stdlib only); the pip package
server.py Runs the Python server from a clone
pyproject.toml pip package definition (bundles the site files at build time)
js/app.mjs Classic mode (original behaviour)
js/mode-switch.mjs Classic / Advanced switch (lazy-loads Advanced)
js/config.mjs Repository / author links
js/advanced/
main.mjs Advanced mode controller (tabs, steps)
llm.mjs AI providers (Claude SDK + OpenAI-compatible)
questions.mjs Question extraction (AI and rule-based)
templates.mjs Templates, prompts, document composition
renderer.mjs Pagination + handwriting page rendering
frontpage.mjs Front page detection / editor
pdf-input.mjs PDF text extraction + OCR
profile.mjs, store.mjs, output.mjs, ui.mjs, loaders.mjs
css/advanced.css Advanced mode styles
Libraries
- html2canvas: renders pages to images
- jsPDF: builds the PDF
- pdf.js: reads uploaded PDFs
- Tesseract.js: OCR for front pages and scanned papers
- Anthropic TypeScript SDK: Claude integration
- Cypress: end-to-end tests (
npm test, with the server running)
Contributing
Bug reports, front-page layouts that don't detect well, new templates and fixes are all welcome. Read CONTRIBUTING.md to get set up, and follow our Code of Conduct. To report a security problem, see SECURITY.md.
Responsible use
Use this for notes, practice, accessibility (for example, if handwriting is hard for you) and mock-ups. Check your institution's rules before submitting AI-assisted or generated work.
License
MIT. See LICENSE. Based on the MIT-licensed text-to-handwriting project.
Metadata
Release files for text-to-handwriting-ai 2.0.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | Actions |
|---|---|---|---|---|
| text_to_handwriting_ai-2.0.0.tar.gz | 406.0 kB | With provenance | Details for text_to_handwriting_ai-2.0.0.tar.gz |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| text_to_handwriting_ai-2.0.0-py3-none-any.whl | Python 3 | none | any | Details for text_to_handwriting_ai-2.0.0-py3-none-any.whl |
Total release size: 825.1 kB
Release files / text_to_handwriting_ai-2.0.0.tar.gz
| Download URL | text_to_handwriting_ai-2.0.0.tar.gz |
|---|---|
| Size | 406.0 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
11585a4cf81bececa3cdab5b5bf2ed225a653a7f3a2a8f44d29e3bcb409448a3
|
|
BLAKE2b-256 checksum How to use checksums |
579d609e0b8087c6ef4d10b9e8686c2abf62a74c8fcc6e46b954053920db8287
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 10, 2026.
Transparency logRelease files / text_to_handwriting_ai-2.0.0-py3-none-any.whl
| Download URL | text_to_handwriting_ai-2.0.0-py3-none-any.whl |
|---|---|
| Size | 419.1 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
02f31b332cfe81502407681ebedd25228ad2c31f89274402acb366215ba4753a
|
|
BLAKE2b-256 checksum How to use checksums |
790d390bf4f1ac5620093b50d9ba501bac136f36a7be0c8c3040aa7a2af097eb
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 10, 2026.
Transparency logSecurity for text-to-handwriting-ai 2.0.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
Full provenance
All 2 files in this release have been uploaded with provenance metadata.
Attestation for text_to_handwriting_ai-2.0.0.tar.gz
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 10, 2026.
Transparency logA note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.