Custom Templates
While Glyph provides professional templates out of the box, you can create custom templates for complete control over your document design.
Template Structure
Section titled “Template Structure”A Glyph template consists of three files:
my-template/ template.html # HTML structure with Mustache placeholders styles.css # Template-specific styles schema.json # Data validation schemaCreating a Template
Section titled “Creating a Template”1. HTML Template
Section titled “1. HTML Template”Use Mustache syntax for data binding:
<!DOCTYPE html><html lang="en"><head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>{{meta.documentTitle}}</title> <style> /* Inline critical styles or link external CSS */ </style></head><body> <div class="document"> <!-- Header region --> <header data-glyph-region="header"> {{#branding.logoUrl}} <img src="{{branding.logoUrl}}" alt="Logo" class="logo"> {{/branding.logoUrl}} <h1>{{branding.companyName}}</h1> </header>
<!-- Client info region --> <section data-glyph-region="client-info"> <h2>Prepared For</h2> <p><strong>{{client.name}}</strong></p> {{#client.company}}<p>{{client.company}}</p>{{/client.company}} {{#client.email}}<p>{{client.email}}</p>{{/client.email}} </section>
<!-- Line items region --> <table data-glyph-region="line-items"> <thead> <tr> <th>Description</th> <th>Qty</th> <th>Price</th> <th>Total</th> </tr> </thead> <tbody> {{#lineItems}} <tr> <td>{{description}}</td> <td>{{quantity}}</td> <td>${{unitPrice}}</td> <td>${{total}}</td> </tr> {{/lineItems}} </tbody> </table>
<!-- Totals region --> <section data-glyph-region="totals"> <div class="total-row"> <span>Subtotal</span> <span>${{totals.subtotal}}</span> </div> {{#totals.tax}} <div class="total-row"> <span>Tax</span> <span>${{totals.tax}}</span> </div> {{/totals.tax}} <div class="total-row final"> <span>Total</span> <span>${{totals.total}}</span> </div> </section> </div></body></html>2. Mustache Syntax Reference
Section titled “2. Mustache Syntax Reference”| Syntax | Description | Example |
|---|---|---|
{{variable}} | Output variable | {{client.name}} |
{{#section}}...{{/section}} | Conditional/loop | {{#lineItems}}...{{/lineItems}} |
{{^section}}...{{/section}} | Inverted (if empty) | {{^discount}}No discount{{/discount}} |
{{{raw}}} | Unescaped HTML | {{{customHtml}}} |
3. Define Regions
Section titled “3. Define Regions”Mark interactive regions with data-glyph-region:
<header data-glyph-region="header">...</header><section data-glyph-region="custom-section">...</section>The AI can target these regions for focused modifications.
4. Create Schema
Section titled “4. Create Schema”Define expected data structure in schema.json:
{ "$schema": "http://json-schema.org/draft-07/schema#", "title": "MyTemplateData", "type": "object", "required": ["client", "lineItems", "totals"], "properties": { "client": { "type": "object", "required": ["name"], "properties": { "name": { "type": "string", "description": "Client name" }, "company": { "type": "string", "description": "Company name" }, "email": { "type": "string", "format": "email" } } }, "lineItems": { "type": "array", "minItems": 1, "items": { "type": "object", "required": ["description", "quantity", "unitPrice", "total"], "properties": { "description": { "type": "string" }, "quantity": { "type": "number" }, "unitPrice": { "type": "number" }, "total": { "type": "number" } } } }, "totals": { "type": "object", "required": ["subtotal", "total"], "properties": { "subtotal": { "type": "number" }, "tax": { "type": "number" }, "total": { "type": "number" } } } }}Styling Best Practices
Section titled “Styling Best Practices”Print-Friendly CSS
Section titled “Print-Friendly CSS”/* Base styles */.document { max-width: 8.5in; margin: 0 auto; padding: 0.75in; font-family: system-ui, sans-serif;}
/* Print styles */@media print { body { print-color-adjust: exact; -webkit-print-color-adjust: exact; }
.document { padding: 0; max-width: none; }}
@page { size: letter; margin: 0.5in;}CSS Variables for Theming
Section titled “CSS Variables for Theming”:root { --accent-color: #1e3a5f; --text-primary: #1a1a1a; --text-secondary: #666666; --border-color: #e5e5e5;}
/* Use in template */.header { border-color: var(--accent-color);}Allow overrides via data:
<style> :root { --accent-color: {{styles.accentColor}}; }</style>Region Styling
Section titled “Region Styling”/* Visual feedback for interactive regions */[data-glyph-region] { cursor: pointer; transition: outline 0.15s;}
[data-glyph-region]:hover { outline: 2px dashed rgba(30, 58, 95, 0.3); outline-offset: 2px;}Uploading Custom Templates
Section titled “Uploading Custom Templates”Self-Hosted
Section titled “Self-Hosted”-
Place template files in your templates directory:
templates/my-template/template.htmlstyles.cssschema.json -
Register the template in your template registry
-
Use it:
<glyph-editor template="my-template" ...></glyph-editor>
Glyph Cloud
Section titled “Glyph Cloud”- Go to your dashboard
- Navigate to Templates
- Click Upload Template
- Provide your files and metadata
- Submit for review (Enterprise) or activate (Pro)
Template Development Tips
Section titled “Template Development Tips”1. Start from an Existing Template
Section titled “1. Start from an Existing Template”Fork quote-modern and modify:
cp -r templates/quote-modern templates/my-template2. Test with Sample Data
Section titled “2. Test with Sample Data”Create test data that covers all cases:
{ "client": { "name": "Test Client", "company": "Test Corp" }, "lineItems": [ { "description": "Item 1", "quantity": 1, "unitPrice": 100, "total": 100 }, { "description": "Item with very long description that might wrap", "quantity": 99, "unitPrice": 9999.99, "total": 989900.01 } ], "totals": { "subtotal": 989900.01, "tax": 79192, "discount": 10000, "total": 1059092.01 }}3. Test Print Output
Section titled “3. Test Print Output”Always generate a PDF to verify:
- Page breaks
- Color accuracy
- Font rendering
- Margin handling
4. Handle Edge Cases
Section titled “4. Handle Edge Cases”- Very long text
- Missing optional fields
- Large numbers
- Empty arrays
Example: Invoice Template
Section titled “Example: Invoice Template”<!DOCTYPE html><html lang="en"><head> <style> /* Invoice-specific styles */ .invoice-header { display: flex; justify-content: space-between; border-bottom: 3px solid var(--accent-color); padding-bottom: 1rem; margin-bottom: 2rem; }
.invoice-number { font-size: 2rem; font-weight: bold; color: var(--accent-color); }
.status-badge { display: inline-block; padding: 0.25rem 1rem; background: #fef3c7; color: #92400e; border-radius: 9999px; font-weight: 600; }
.status-badge.paid { background: #d1fae5; color: #065f46; } </style></head><body> <div class="invoice" data-glyph-region="header"> <div class="invoice-header"> <div> <div class="invoice-number">INVOICE #{{meta.invoiceNumber}}</div> <span class="status-badge {{meta.status}}">{{meta.status}}</span> </div> <div> {{#branding.logoUrl}} <img src="{{branding.logoUrl}}" alt="Logo"> {{/branding.logoUrl}} </div> </div> <!-- ... rest of template --> </div></body></html>