This project provides a specialized web-based G-code generator for the openBrushograph, designed to render the indigenous Batak script (Surat Batak) of Sumatra, Indonesia. It features a custom "Skeleton Assembler" engine that generates single-stroke paths optimized for pen/brush plotting, bypassing standard outline fonts.
Test it here: https://openbrushograph.github.io/extensions/batak-assembler.html
The openBrushograph is an open-source "mechatronic brush" painting machine. Originally conceptualized by Dominik Mahnič as "Brušografia," it explores the intersection of classical artistry and robotic technology.
This project is part of the larger openBrushograph ecosystem, an open hardware and software initiative to democratize robotic painting.
- Main Project Repository: https://github.com/openBrushograph
- Documentation & Wiki: https://wiki.sgmk-ssam.ch/wiki/Brushograph
- Project Website: https://openbrushograph.github.io/
License: This software is released under the MIT License, permitting free modification, distribution, and use in both personal and commercial projects. Hardware designs are typically released under Creative Commons or CERN OHL (check specific hardware repositories for details).
Technically, it is a compact CNC plotter (often based on "Arduino mini CNC" mechanics) adapted to hold a brush or pen. Modern versions run on FluidNC (ESP32), allowing for wireless web-based control, which this project leverages for a seamless "Type-to-Print" workflow.
Surat Batak is a traditional writing system used by the Batak peoples of North Sumatra, Indonesia. It is an Abugida: each distinct consonant character (e.g., Ka, Ba) carries an inherent vowel sound (usually 'a').
- Diacritics: Vowels are changed (to 'i', 'u', 'e', 'o') or muted (using the Pangolat) by attaching small marks around the base character.
- Cultural Themes: This tool includes UI themes inspired by Gorga (traditional Batak wood carving patterns) and Ulos (hand-woven textile motifs).
The UI scale is responsive and features dark mode for comfortable machine operation.

The "Test: All Glyphs" button generates a complete grid of all available Batak characters (minus placeholder boxes) to verify font integrity and pen width.

For DIY machines with loose belts or lead screws, use the Backlash Compensation settings.
Left: Default settings (0 backlash). Right: Settings adjusted for a machine with significant play.
Example: "tuak" The preview visualizes the compensation (note the 'ghosting' or double-strokes where the machine takes up slack).
With Backlash (2.0mm)
Note the slight erratic lines (pink) which represent the machine moving to 'take up slack' before the actual drawing stroke begins.
- Skeleton Output: Generates efficient, single-stroke G-code suitable for fountain pens and brushes.
- FluidNC Integration: Runs directly in the browser and can "Upload & Run" files to the machine wirelessly.
- Ink Dipping: (Optional) Configurable intervals to pause printing and travel to ink pots (Pink, Green, Blue presets) for refilling.
- Diagnostic Tools: Includes a "Test: All Glyphs" chart to print the entire character set for calibration.
Ensure your Brushograph is powered on and the FluidNC controller is accessible via Wi-Fi.
- Default Hostname:
fluidnc.local(or the IP address shown in your router). - Web Interface: Verify you can access the standard FluidNC dashboard in your browser.
You can run this tool in two ways:
- Local Mode (Testing): Open the
.htmlfile directly in your browser.- Enter the IP address of your machine in the "Controller Host" field (e.g.,
http://192.168.0.x). - Note: Due to browser security (CORS), status feedback might be limited in local mode ("Blind Mode"). The tool will send commands, but may not confirm receipt.
- Enter the IP address of your machine in the "Controller Host" field (e.g.,
- Embedded Mode (Production): Upload the
batak-assembler.htmlfile to the FluidNC Flash/SD card.- Access it directly from the controller:
http://fluidnc.local/batak-assembler.html. - In this mode, connection is automatic (same-origin).
- Access it directly from the controller:
- Type & Transliterate: Enter Latin text (e.g., "Horas") in the input box.
- Generate: Click "Generate G-code" to visualize the path.
- Upload & Run:
- Upload Wrapped: Sends the file to the SD card.
- Run: Instructs the machine to execute the file immediately. (Safety Delay: The tool waits 2 seconds between upload and run to ensure the file is saved).
The assembler is designed for real-world plotting with fountain pens or brushes, which run out of ink.
- Distance Tracking: The tool calculates the cumulative travel distance of the pen.
- Auto-Dip: When the
Dip Interval(e.g., 500mm) is reached, the machine pauses, moves to the configurationDip Location(Ink Pot), performs a refill sequence, and resumes printing. - Color Presets: Three "Quick-Set" buttons (Pink, Green, Blue) allow for rapid switching between ink stations without manual coordinate entry.
- Custom Sequences: Advanced users can write their own G-code macros for specific dipping/wiping motions (e.g., "shake the brush" or "wipe on edge").
Summary of the development philosophy:
Standard digital fonts are "outlines" — defining the edges of a shape. For a pen plotter, drawing outlines looks artificial (like a hollow letter). This project uses Skeletonization (centerline extraction) to produce single-stroke paths that mimic the movement of a human hand writing with a stylus.
Unlike a word processor that renders pixels, this tool acts as an Assembler. It treats every Batak glyph as a physical object with a defined width and anchor point. It constructs words by placing these objects side-by-side (syndetically) and calculating the necessary machine movements to connect them.
Implementing non-Latin scripts requires respecting their internal logic. Batak is an Abugida (syllable-based). The core challenge was translating linear keyboard input (Latin) into this structural format:
- Vowel Killing: Automatically applying the Pangolat (killer) when a syllable ends in a consonant.
- Reordering: Visually moving vowels (like U) to different positions relying on "Closed Syllable" logic, ensuring the machine draws them in a linguistically correct but visually pleasing order.
The Machine as "Par-Tuak" Central to the project's identity is the concept of Tuak, the traditional Batak palm wine.
- The Ritual: Just as Tuak is poured and served in social gatherings, the machine enacts a ritual of dipping and serving ink.
- The "Alcoholic" Machine: The Ink Management system (Distance Tracking & Dipping) was humorously designed around the machine's "thirst." If the dip interval is too short, the machine spends more time drinking (dipping) than working.
- Par-Tuak: The machine is not just a printer; it is a Par-Tuak (the wine server), carrying fluids from the reservoir to the paper, mediating between the digital command and the organic flow of liquid. This transforms the "Backlash Compensation" and "Ink Refill" from technical bugs into character traits of a machine that is alive, thirsty, and participating in the culture it writes.
This project was built using an Agentic Workflow focusing on:
- Glyph Extraction: Python-based skeletonization of Batak fonts.
- Linguistic Engine: Custom Javascript transliteration for Batak rules (Transliteration, Closed Syllables).
- Embedded UI: A responsive, single-file HTML/JS app designed for the FluidNC environment.
For detailed technical workflows and skills involved, refer to the knowledge base:
agent_knowledge/fluidnc_extension_workflow.mdagent_knowledge/fluidnc_script_assembly.md

