Skip to main content

Template Components

A comprehensive guide to all available components in document templates (PDF and Excel).


Table of Contents​

  1. Overview
  2. Component Categories
  3. Template Type Support
  4. Layout Components
  5. Content Components
  6. Data Components
  7. Interactive Components
  8. Advanced Components
  9. Best Practices
  10. Complete Examples

Overview​

Templates are built using a component-based architecture. Each component represents a visual or functional element in your document. Components can be simple (like text or images) or complex (like tables with calculations or conditional sections).

Key Concepts​

Component Structure: Every component has:

  • id (string, required): Unique identifier
  • type (string, required): Component type (e.g., "text", "button", "table")
  • props (object, optional): Component properties and configuration
  • children (array, optional): Nested child components
  • content (string, optional): Text content for some components

Template Types: Components can be used in:

  • PDF templates: Rendered as PDF documents
  • Excel templates: Rendered as Excel spreadsheets
  • Both: Works in both template types

Variable Support: Most components support Handlebars syntax {{variableName}} for dynamic content.


Component Categories​

Layout Components​

Structure and organize other components:

  • Container - Wrapper with background, padding, and styling
  • Columns - Multi-column layouts (2-4 columns)
  • Table Layout - Grid-based layout system
  • Divider - Horizontal separator line
  • Spacer - Vertical spacing control

Content Components​

Display text, images, and static content:

  • Text - Simple paragraph text
  • Heading - Headings (H1-H6)
  • Rich Text - Formatted HTML content
  • Image - Images with responsive sizing
  • List - Ordered and unordered lists
  • SVG - Externally-generated SVG graphics (charts, barcodes, diagrams)

Data Components​

Display and manipulate data:

  • Table - Data tables with 5 column types
  • Chart - Visualizations (PDF + Excel)
  • Loop - Repeat content for arrays
  • Conditional - Show/hide based on conditions

Interactive Components​

PDF-specific interactive elements:

  • Button - Call-to-action buttons (links in PDFs)
  • QR Code - QR codes for tickets, URLs, etc.
  • Barcode - Barcodes in multiple formats (Code128, EAN-13, UPC-A, etc.)

Template Type Support​

ComponentPDFExcelNotes
Text✅✅Plain text paragraphs and body content
Heading✅✅H1-H6 section headings
Rich Text✅✅HTML-formatted content (bold, italic, lists)
Button✅❌PDF only (clickable links)
Image✅✅Responsive images
Container✅✅Layout wrapper
Columns✅✅Multi-column layouts
List✅✅Ordered/unordered lists
Table✅✅Data tables
Table Layout✅✅Grid layout
Divider✅✅Horizontal line
Spacer✅✅Vertical spacing
Chart✅✅Data visualizations (rendered images in PDFs, native in Excel)
Loop✅✅Iterate over arrays
Conditional✅✅Conditional rendering
QR Code✅❌PDF only (scannable codes)
Barcode✅❌PDF only (Code128, EAN, UPC, etc.)
SVG✅✅Externally-generated SVG graphics
note

Use text for plain text content, heading for section titles (H1-H6), and rich-text when you need HTML formatting (bold, italic, inline lists).


Layout Components​

Container​

Wrapper component with background, padding, and styling. Use to group and style related content.

Properties​

PropertyTypeRequiredDefaultDescription
backgroundColorstringNotransparentBackground color (hex, rgb, rgba, named)
paddingstringNo"0px"CSS padding value (e.g., "20px", "10px 20px")
maxWidthstringNononeMaximum width (e.g., "600px", "100%")
borderRadiusstringNo"0px"Border radius (e.g., "8px", "50%")
borderstringNononeCSS border value (e.g., "1px solid #000")
alignenumNoleftAlignment: "left", "center", "right"
marginstringNo"0px"CSS margin value
childrenarrayNo[]Child components

Example​

{
"type": "container",
"id": "welcome-section",
"props": {
"backgroundColor": "#f8f9fa",
"padding": "40px 20px",
"maxWidth": "600px",
"borderRadius": "8px",
"align": "center"
},
"children": [
{
"type": "heading",
"id": "welcome-heading",
"props": { "level": 1 },
"content": "Welcome {{userName}}!",
"style": { "textAlign": "center" }
},
{
"type": "text",
"id": "welcome-text",
"content": "Thanks for joining us. Your account is ready.",
"style": { "textAlign": "center" }
}
]
}

Use Cases​

  • Group related content with consistent styling
  • Create card-like sections in documents
  • Add background colors to highlight sections
  • Control maximum width for better readability

Columns​

Multi-column layout component for side-by-side content (2-4 columns).

Properties​

PropertyTypeRequiredDefaultDescription
columnCountnumberNo2Number of columns (1-4)
gapstring/numberNo"20px"Gap between columns
columnWidthsarrayNoequalArray of width values (e.g., ["50%", "50%"])
backgroundColorstringNotransparentBackground color
paddingstringNo"0px"CSS padding value
verticalAlignenumNotopAlignment: "top", "middle", "bottom"
stackOnMobilebooleanNotrueStack columns on small screens
childrenarrayNo[]Child components (one per column)

Example​

{
"type": "columns",
"id": "feature-columns",
"props": {
"columnCount": 3,
"gap": "20px",
"stackOnMobile": true
},
"children": [
{
"type": "container",
"id": "feature-1",
"props": { "padding": "20px", "align": "center" },
"children": [
{
"type": "image",
"id": "icon-1",
"props": {
"source": "https://example.com/icon1.png",
"width": 64,
"height": 64,
"alignment": "center"
}
},
{
"type": "heading",
"id": "title-1",
"props": { "level": 3 },
"content": "Fast Delivery",
"style": { "textAlign": "center" }
},
{
"type": "text",
"id": "desc-1",
"content": "Same-day shipping available",
"style": { "textAlign": "center" }
}
]
},
{
"type": "container",
"id": "feature-2",
"props": { "padding": "20px", "align": "center" },
"children": [
{
"type": "image",
"id": "icon-2",
"props": {
"source": "https://example.com/icon2.png",
"width": 64,
"height": 64,
"alignment": "center"
}
},
{
"type": "heading",
"id": "title-2",
"props": { "level": 3 },
"content": "Secure Payment",
"style": { "textAlign": "center" }
},
{
"type": "text",
"id": "desc-2",
"content": "SSL encrypted checkout",
"style": { "textAlign": "center" }
}
]
},
{
"type": "container",
"id": "feature-3",
"props": { "padding": "20px", "align": "center" },
"children": [
{
"type": "image",
"id": "icon-3",
"props": {
"source": "https://example.com/icon3.png",
"width": 64,
"height": 64,
"alignment": "center"
}
},
{
"type": "heading",
"id": "title-3",
"props": { "level": 3 },
"content": "24/7 Support",
"style": { "textAlign": "center" }
},
{
"type": "text",
"id": "desc-3",
"content": "Always here to help",
"style": { "textAlign": "center" }
}
]
}
]
}

Use Cases​

  • Feature lists with icons
  • Side-by-side product comparisons
  • Contact information with labels and values
  • Multi-column layouts in newsletters

Table Layout​

Grid-based layout component (different from data tables). Creates a fixed grid for positioning components.

Properties​

PropertyTypeRequiredDefaultDescription
rowsnumberNo1Number of rows (1-20)
colsnumberNo1Number of columns (1-10)
borderWidthstringNo"0px"Border width (e.g., "1px")
borderColorstringNo#000000Border color
cellPaddingstringNo"0px"CSS padding for each cell
cellBackgroundColorstringNotransparentBackground color for cells
cellAlignenumNoleftCell alignment: "left", "center", "right"
cellVerticalAlignenumNotopVertical alignment: "top", "middle", "bottom"
borderCollapsebooleanNotrueCollapse borders between cells
widthstringNo100%Table width
childrenarrayNo[]Child components (one per cell)

Example​

{
"type": "table-layout",
"id": "info-grid",
"props": {
"rows": 2,
"cols": 2,
"borderWidth": "1px",
"borderColor": "#e0e0e0",
"cellPadding": "10px",
"width": "100%"
},
"children": [
{
"type": "text",
"id": "label-1",
"content": "Order Number:",
"style": { "fontWeight": "bold" }
},
{
"type": "text",
"id": "value-1",
"content": "{{orderNumber}}"
},
{
"type": "text",
"id": "label-2",
"content": "Order Date:",
"style": { "fontWeight": "bold" }
},
{
"type": "text",
"id": "value-2",
"content": "{{orderDate}}"
}
]
}

Use Cases​

  • Form-like layouts (label + value pairs)
  • Invoice headers with structured data
  • Fixed grid positioning for components
  • Simple data displays without table headers

Divider​

Horizontal separator line for visual separation.

Properties​

PropertyTypeRequiredDefaultDescription
styleenumNosolidLine style: "solid", "dashed", "dotted"
thicknessnumberNo1Line thickness in pixels (1-10)
colorstringNo#e0e0e0Line color
widthstringNo100%Divider width (e.g., "80%", "600px")
marginstringNo20px 0CSS margin value

Example​

{
"type": "divider",
"id": "section-divider",
"props": {
"style": "solid",
"thickness": 2,
"color": "#cccccc",
"width": "80%",
"margin": "30px 0"
}
}

Use Cases​

  • Separate sections in documents
  • Visual breaks between content blocks
  • Footer separators
  • Section headers

Spacer​

Vertical spacing component for controlling whitespace.

Properties​

PropertyTypeRequiredDefaultDescription
heightstring/numberNo20pxVertical spacing (e.g., "40px", 60)

Example​

{
"type": "spacer",
"id": "section-spacing",
"props": {
"height": "40px"
}
}

Use Cases​

  • Add vertical spacing between sections
  • Control whitespace in layouts
  • Improve readability with breathing room
  • Consistent spacing throughout template

Content Components​

Text​

Simple paragraph text component for body content.

Properties​

PropertyTypeRequiredDefaultDescription
contentstringYes-Text content (supports {{variables}})
styleobjectNo-Styling options
style.fontSizenumberNo16Font size (6-72)
style.fontWeightstring/numberNonormalWeight: "normal", "bold", "bolder", "lighter", 100-900
style.colorstringNo#000000Text color
style.backgroundColorstringNotransparentBackground color
style.textAlignenumNoleftAlignment: "left", "center", "right", "justify"
style.lineHeightstring/numberNo1.5Line height
positionobjectNo-Position in attachment (x, y coordinates)

Example​

{
"type": "text",
"id": "intro-text",
"content": "Hello {{userName}}, your order #{{orderNumber}} has been confirmed!",
"style": {
"fontSize": 16,
"color": "#333333",
"textAlign": "left",
"lineHeight": 1.6
}
}

Use Cases​

  • Body paragraphs
  • Descriptions
  • Explanatory text
  • Dynamic content with variables

Heading​

Heading component for section titles (H1-H6).

Properties​

PropertyTypeRequiredDefaultDescription
contentstringYes-Heading text (supports {{variables}})
levelnumberYes1Heading level (1-6)
styleobjectNo-Styling options (same as Text)
positionobjectNo-Position in attachment (x, y coordinates)

Example​

{
"type": "heading",
"id": "page-title",
"props": {
"level": 1
},
"content": "Order Confirmation",
"style": {
"fontSize": 32,
"fontWeight": "bold",
"color": "#007bff",
"textAlign": "center"
}
}

Use Cases​

  • Page titles
  • Section headings
  • Document title headings
  • Hierarchical content structure

Rich Text​

Enhanced text component with HTML formatting support.

Properties​

PropertyTypeRequiredDefaultDescription
contentstringNo""HTML content
propsobjectNo-Styling options
props.alignenumNoleftAlignment: "left", "center", "right", "justify"
props.colorstringNo#000000Text color
props.backgroundColorstringNotransparentBackground color
props.fontSizestring/numberNo16pxFont size (8-72 or CSS value)
props.lineHeightstring/numberNo1.5Line height
props.paddingstringNo0pxCSS padding value
props.maxWidthstringNononeMaximum width

Example​

{
"type": "rich-text",
"id": "formatted-content",
"content": "<p>Your order includes:</p><ul><li><strong>Premium Plan</strong> - $99/month</li><li>24/7 Support</li><li>Unlimited API calls</li></ul>",
"props": {
"align": "left",
"fontSize": "16px",
"padding": "20px"
}
}

Use Cases​

  • Complex formatted content
  • Lists with formatting
  • Mixed content (bold, italic, links)
  • Pre-formatted HTML sections

Image​

Responsive image component for displaying images.

Properties​

PropertyTypeRequiredDefaultDescription
sourcestringYes-Image URL or data URI (supports {{variables}})
altstringNo""Alt text for accessibility
widthnumber/stringNoautoImage width (pixels or CSS value, max 2000)
heightnumber/stringNoautoImage height (pixels or CSS value, max 2000)
alignmentenumNoleftAlignment: "left", "center", "right"
positionobjectNo-Position (attachment): x and y coordinates
styleobjectNo-Additional styling

Example​

{
"type": "image",
"id": "product-image",
"props": {
"source": "{{productImageUrl}}",
"alt": "{{productName}}",
"width": 400,
"height": 300,
"alignment": "center"
}
}

Use Cases​

  • Product images
  • Logos and branding
  • Illustrations
  • User avatars
  • Dynamic images from variables

List​

Ordered or unordered list component.

Properties​

PropertyTypeRequiredDefaultDescription
itemsarrayNo[]Array of list items (strings, max 100)
orderedbooleanNofalseTrue for ordered list, false for unordered
listStyleTypeenumNodisc/decimalList style: "disc", "circle", "square" (unordered), "decimal", "lower-alpha", etc. (ordered)
colorstringNo#000000Text color
backgroundColorstringNotransparentBackground color
fontSizestring/numberNo16pxFont size (8-72 or CSS value)
lineHeightstring/numberNo1.5Line height (0.5-3)
paddingstringNo0pxCSS padding value
marginstringNo0pxCSS margin value
itemSpacingstring/numberNo8pxSpacing between items (0-50)
indentstring/numberNo20pxList indentation (0-100)

Example​

{
"type": "list",
"id": "feature-list",
"props": {
"ordered": false,
"listStyleType": "disc",
"items": [
"Free shipping on all orders",
"30-day money-back guarantee",
"24/7 customer support",
"Lifetime warranty"
],
"color": "#333333",
"fontSize": 16,
"itemSpacing": "12px"
}
}

Use Cases​

  • Feature lists
  • Benefit lists
  • Instructions or steps
  • Table of contents
  • Bullet points

SVG​

Embed externally-generated SVG graphics from any programming language. Use Python, R, Go, Node.js, or any tool that can produce SVG to create custom charts, barcodes, diagrams, and more.

Template Support: Both PDF and Excel templates

Properties​

PropertyTypeRequiredDefaultDescription
contentstringYes-SVG markup or variable reference (supports {{variables}})
encodingenumNoraw"raw" for plain SVG, "base64" for encoded SVG
widthnumber/stringNo200Width (pixels or percentage, e.g., "100%", 400)
heightnumber/stringNo150Height (pixels or percentage)
alignenumNoleftAlignment: "left", "center", "right"
preserveAspectRatiostringNo-SVG preserveAspectRatio attribute (e.g., "xMidYMid meet")

Example - Basic SVG​

{
"type": "svg",
"id": "custom-diagram",
"props": {
"content": "<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 200 100\"><rect x=\"10\" y=\"10\" width=\"80\" height=\"80\" fill=\"#007bff\"/><circle cx=\"150\" cy=\"50\" r=\"40\" fill=\"#28a745\"/></svg>",
"width": 200,
"height": 100,
"align": "center"
}
}

Example - Dynamic SVG from Variable​

The recommended approach is to generate the SVG externally and pass it as a variable:

{
"type": "svg",
"id": "python-chart",
"props": {
"content": "{{chartSvg}}",
"encoding": "base64",
"width": 600,
"height": 400,
"align": "center"
}
}

Then pass the SVG when generating the document:

// Node.js example
const chartSvg = Buffer.from(svgString).toString('base64');

await client.documents.generate({
templateId: 'my-template',
variables: {
chartSvg: chartSvg
}
});
# Python example
import base64

chart_svg = base64.b64encode(svg_string.encode()).decode()

client.documents.generate(
template_id="my-template",
variables={"chartSvg": chart_svg}
)

Base64 Encoding​

Use base64 encoding for SVGs with special characters, unicode, or complex content:

{
"type": "svg",
"id": "encoded-svg",
"props": {
"content": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjxyZWN0IHdpZHRoPSIxMDAiIGhlaWdodD0iMTAwIiBmaWxsPSIjMDA3YmZmIi8+PC9zdmc+",
"encoding": "base64",
"width": 100,
"height": 100
}
}

Security​

SVG content is automatically sanitized to prevent security vulnerabilities:

Elements Removed:

  • <script> tags
  • <foreignObject> elements
  • Event handlers (onclick, onload, etc.)
  • External URL references

Allowed Image Sources in SVG:

  • Base64 data URIs: data:image/png;base64,...
  • Rynko assets: assets://asset_id (references your uploaded assets)
  • Internal references: #id (for internal SVG elements)

External URLs (http://, https://) are blocked to prevent SSRF attacks.

Example - SVG with Embedded Image​

{
"type": "svg",
"id": "svg-with-logo",
"props": {
"content": "<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"300\" height=\"100\"><image href=\"assets://company-logo\" x=\"0\" y=\"0\" width=\"80\" height=\"80\"/><text x=\"100\" y=\"50\" font-size=\"24\">Company Name</text></svg>",
"width": 300,
"height": 100,
"align": "center"
}
}

Use Cases​

  • Custom charts from Python (matplotlib, plotly, seaborn)
  • Data visualizations from R (ggplot2)
  • Custom barcodes from specialized libraries
  • Architecture diagrams from D3.js or other tools
  • Floor plans and technical drawings
  • Custom gauges and meters
  • Infographics with dynamic data

Data Components​

Table​

Powerful data table component with 5 column types. See the Variables & Dynamic Content guide for complete details.

Properties​

PropertyTypeRequiredDefaultDescription
dataSourcestringYes-Variable name containing array data
columnsarrayYes-Array of column definitions
showHeaderbooleanNotrueShow table header row
showBorderbooleanNotrueShow table borders
showTotalsRowbooleanNofalseShow totals row (attachment only)
styleobjectNo-Table styling options

Column Types​

1. Simple Field Column: Display a field directly from data

{
"header": "Product Name",
"field": "name",
"width": "40%",
"align": "left"
}

2. Calculated Column: JavaScript expression calculated per row

{
"header": "Total",
"isCalculated": true,
"expression": "quantity * unitPrice",
"format": {
"type": "number",
"preset": "CURRENCY",
"currency": "USD",
"decimals": 2
}
}

3. Calculated Column: JavaScript expressions for computed values

{
"header": "Total",
"isCalculated": true,
"expression": "row.quantity * row.unitPrice",
"format": {
"type": "number",
"preset": "CURRENCY",
"currency": "USD"
}
}

4. Component-Based Column: Render components in cells (PDF only)

{
"header": "Actions",
"renderType": "component",
"component": {
"type": "button",
"props": {
"text": "View",
"url": "https://example.com/products/{{id}}"
},
"contentField": "id"
}
}

Example - Order Items Table​

{
"type": "table",
"id": "order-items",
"props": {
"dataSource": "{{orderItems}}",
"showHeader": true,
"showBorder": true,
"columns": [
{
"header": "Item",
"field": "name",
"width": "40%",
"align": "left"
},
{
"header": "Qty",
"field": "quantity",
"width": "15%",
"align": "center",
"format": {
"type": "number",
"preset": "DECIMAL",
"decimals": 0
}
},
{
"header": "Price",
"field": "unitPrice",
"width": "20%",
"align": "right",
"format": {
"type": "number",
"preset": "CURRENCY",
"currency": "USD",
"decimals": 2
}
},
{
"header": "Total",
"isCalculated": true,
"expression": "quantity * unitPrice",
"width": "25%",
"align": "right",
"format": {
"type": "number",
"preset": "CURRENCY",
"currency": "USD",
"decimals": 2
}
}
],
"style": {
"headerBackgroundColor": "#f8f9fa",
"headerTextColor": "#333333",
"rowBackgroundColor": "#ffffff",
"alternateRowColor": "#f8f9fa",
"borderColor": "#dee2e6"
}
}
}

Totals Row (Attachment Only)​

For Excel and PDF attachments, you can add a totals row with aggregation formulas:

{
"type": "table",
"id": "sales-report",
"props": {
"dataSource": "{{salesData}}",
"showTotalsRow": true,
"totalsConfig": {
"label": "Total",
"labelColumn": "product",
"aggregations": {
"quantity": "SUM",
"revenue": "SUM",
"profit": "SUM"
}
},
"columns": [
{ "header": "Product", "field": "product" },
{ "header": "Quantity", "field": "quantity" },
{ "header": "Revenue", "field": "revenue" },
{ "header": "Profit", "field": "profit" }
]
}
}

Supported Aggregations: SUM, AVERAGE, COUNT, MIN, MAX

Use Cases​

  • Order summaries
  • Invoice line items
  • Product catalogs
  • Price lists
  • Sales reports
  • Inventory lists

Chart​

Data visualization component for creating charts (bar, line, pie, doughnut, area, scatter).

Template Support: Both PDF and Excel templates

  • PDFs: Charts are rendered as static images via QuickCharts API (high resolution, transparent backgrounds)
  • Attachments (PDF/Excel): Charts are rendered natively with full interactivity in Excel

Properties​

PropertyTypeRequiredDefaultDescription
chartTypeenumYes-Chart type: "bar", "line", "pie", "doughnut", "area", "scatter"
dataSourcestringYes-Variable name containing chart data
xAxisstringYes-Field name for X-axis
yAxisstringYes-Field name for Y-axis
titlestringNo""Chart title
widthnumberNo600Chart width in pixels
heightnumberNo400Chart height in pixels
positionobjectNo-Position in attachment: x and y coordinates
styleobjectNo-Chart styling options
legendobjectNo-Legend configuration
xAxisLabelstringNo""X-axis label
yAxisLabelstringNo""Y-axis label
pdfRenderingenumNoimagePDF rendering mode (image recommended for reliability)
excelRenderingenumNonativeExcel rendering: "native", "image"

Chart Styles​

{
"style": {
"colors": ["#007bff", "#28a745", "#ffc107", "#dc3545", "#6f42c1"],
"showLegend": true,
"showGridLines": true,
"backgroundColor": "#ffffff",
"borderColor": "#dee2e6"
}
}

Legend Configuration​

{
"legend": {
"show": true,
"position": "bottom"
}
}

Position Options: "top", "bottom", "left", "right"

PDF-Specific Rendering​

How it works in PDFs:

  • Charts are converted to static PNG images via QuickCharts API
  • High resolution (2x pixel ratio) for crisp display
  • Transparent backgrounds blend with document design
  • Standard fonts (Arial, Helvetica) for maximum compatibility
  • Static images ensure consistent rendering

Recommended sizing for PDFs:

  • Width: 600px or less (fits standard A4/Letter width)
  • Height: 300-400px (optimal readability)

Example - Sales Chart (PDF + Excel)​

{
"type": "chart",
"id": "monthly-sales",
"props": {
"chartType": "bar",
"dataSource": "{{monthlySales}}",
"xAxis": "month",
"yAxis": "revenue",
"title": "Monthly Sales Performance",
"width": 600,
"height": 400,
"xAxisLabel": "Month",
"yAxisLabel": "Revenue ($)",
"style": {
"colors": ["#007bff"],
"showLegend": false,
"showGridLines": true,
"backgroundColor": "transparent"
}
}
}

Example - Pie Chart​

{
"type": "chart",
"id": "revenue-breakdown",
"props": {
"chartType": "pie",
"dataSource": "{{revenueByCategory}}",
"xAxis": "category",
"yAxis": "amount",
"title": "Revenue by Category",
"width": 600,
"height": 400,
"legend": {
"show": true,
"position": "right"
},
"style": {
"colors": ["#007bff", "#28a745", "#ffc107", "#dc3545", "#6f42c1", "#17a2b8"]
}
}
}

Chart Type Guide​

Bar Chart: Compare values across categories

  • Use for: Sales by product, revenue by region, etc.
  • Best for: Comparing discrete categories

Line Chart: Show trends over time

  • Use for: Monthly sales, growth trends, etc.
  • Best for: Time-series data

Pie Chart: Show proportions of a whole

  • Use for: Market share, revenue breakdown, etc.
  • Best for: Percentage distributions (5-7 categories max)

Doughnut Chart: Similar to pie, with center hole

  • Use for: Same as pie chart, with modern aesthetic
  • Best for: Highlighting a key metric in the center

Area Chart: Show cumulative trends

  • Use for: Cumulative revenue, stacked categories
  • Best for: Volume and trends combined

Scatter Chart: Show correlation between variables

  • Use for: Price vs. quantity, correlation analysis
  • Best for: Identifying relationships in data

Attachment-Specific Properties​

For PDF and Excel attachments, additional rendering options are available:

{
"pdfRendering": "image", // Renders chart as high-quality PNG for reliable cross-platform display
"excelRendering": "native", // "native" or "image" (native creates Excel charts)
"position": { // Absolute positioning (attachments only)
"x": 50,
"y": 100
}
}

Use Cases​

PDF Templates:

  • Weekly performance summaries
  • Marketing campaign results
  • Monthly sales reports
  • Customer engagement metrics
  • Newsletter analytics

Attachment Templates:

  • Quarterly financial reports
  • Sales performance dashboards
  • Annual business reviews
  • Analytics reports with drill-down
  • KPI dashboards

Loop​

Repeat content for each item in an array variable.

Properties​

PropertyTypeRequiredDefaultDescription
dataSourcestringYes-Variable name containing array data
itemVariablestringYes-Variable name for each item (must be valid JS identifier)
indexVarstringNo"index"Variable name for index (must be valid JS identifier)
childrenarrayNo[]Components to repeat for each item

Valid Nested Components​

In PDF Templates:

  • text, heading, button, image, table, table-layout, divider, spacer, columns

In Attachment Templates:

  • text, heading, image, table, table-layout, divider, spacer, chart, columns

Not Allowed: Loop and Conditional components cannot be nested inside loops.

Example - Product List​

{
"type": "loop",
"id": "product-loop",
"props": {
"dataSource": "{{products}}",
"itemVariable": "product",
"indexVar": "i"
},
"children": [
{
"type": "container",
"id": "product-card-{{i}}",
"props": {
"padding": "20px",
"margin": "10px 0",
"backgroundColor": "#f8f9fa",
"borderRadius": "8px"
},
"children": [
{
"type": "heading",
"id": "product-name-{{i}}",
"props": { "level": 3 },
"content": "{{product.name}}"
},
{
"type": "text",
"id": "product-desc-{{i}}",
"content": "{{product.description}}",
"style": { "color": "#666666" }
},
{
"type": "text",
"id": "product-price-{{i}}",
"content": "Price: ${{product.price}}",
"style": { "fontSize": 18, "fontWeight": "bold", "color": "#007bff" }
},
{
"type": "button",
"id": "view-button-{{i}}",
"props": {
"text": "View Details",
"href": "https://example.com/products/{{product.id}}",
"backgroundColor": "#007bff",
"color": "#ffffff"
}
}
]
},
{
"type": "divider",
"id": "divider-{{i}}",
"props": {
"style": "solid",
"thickness": 1,
"color": "#e0e0e0",
"margin": "10px 0"
}
}
]
}

Example - Order Items Loop​

{
"type": "loop",
"id": "order-items-loop",
"props": {
"dataSource": "{{orderItems}}",
"itemVariable": "item"
},
"children": [
{
"type": "columns",
"id": "item-row",
"props": {
"columnCount": 3,
"gap": "10px"
},
"children": [
{
"type": "text",
"id": "item-name",
"content": "{{item.name}}"
},
{
"type": "text",
"id": "item-qty",
"content": "Qty: {{item.quantity}}",
"style": { "textAlign": "center" }
},
{
"type": "text",
"id": "item-total",
"content": "${{item.total}}",
"style": { "textAlign": "right", "fontWeight": "bold" }
}
]
}
]
}

Use Cases​

  • Product lists
  • Order item listings
  • Project member profiles
  • Event schedules
  • FAQ lists
  • Blog post summaries

Conditional​

Show or hide content based on a condition.

Properties​

PropertyTypeRequiredDefaultDescription
conditionstringYes-JavaScript boolean expression
childrenarrayNo[]Components to show if condition is true

Valid Nested Components​

In PDF Templates:

  • text, heading, button, image, table, table-layout, divider, spacer, columns, container

In Attachment Templates:

  • text, heading, image, table, table-layout, divider, spacer, chart, columns, container

Not Allowed: Conditional and Loop components cannot be nested inside conditionals.

Condition Syntax​

Conditions are JavaScript boolean expressions evaluated at render time:

Comparison Operators:

  • ===, !==, >, >=, <, <=

Logical Operators:

  • && (AND), || (OR), ! (NOT)

Examples:

"isPremium === true"
"orderTotal > 100"
"quantity >= 10 && status === 'active'"
"!isExpired"
"membershipLevel === 'gold' || membershipLevel === 'platinum'"

Example - Premium Member Badge​

{
"type": "conditional",
"id": "premium-badge",
"props": {
"condition": "isPremium === true"
},
"children": [
{
"type": "container",
"id": "badge-container",
"props": {
"backgroundColor": "#ffd700",
"padding": "10px 20px",
"borderRadius": "20px",
"align": "center"
},
"children": [
{
"type": "text",
"id": "badge-text",
"content": "⭐ Premium Member",
"style": {
"fontSize": 14,
"fontWeight": "bold",
"color": "#000000",
"textAlign": "center"
}
}
]
}
]
}

Example - Discount Notice​

{
"type": "conditional",
"id": "discount-notice",
"props": {
"condition": "orderTotal >= 100"
},
"children": [
{
"type": "container",
"id": "discount-banner",
"props": {
"backgroundColor": "#d4edda",
"padding": "15px",
"borderRadius": "4px",
"border": "1px solid #c3e6cb"
},
"children": [
{
"type": "text",
"id": "discount-text",
"content": "🎉 Congratulations! You've qualified for free shipping on orders over $100.",
"style": {
"color": "#155724",
"fontSize": 16,
"textAlign": "center"
}
}
]
}
]
}

Example - Status-Based Content​

{
"type": "conditional",
"id": "shipping-status",
"props": {
"condition": "status === 'shipped'"
},
"children": [
{
"type": "heading",
"id": "shipped-heading",
"props": { "level": 2 },
"content": "Your Order Has Shipped! 📦",
"style": { "color": "#28a745", "textAlign": "center" }
},
{
"type": "text",
"id": "tracking-info",
"content": "Track your package: {{trackingNumber}}",
"style": { "textAlign": "center" }
},
{
"type": "button",
"id": "track-button",
"props": {
"text": "Track Package",
"href": "https://example.com/tracking/{{trackingNumber}}",
"backgroundColor": "#28a745",
"alignment": "center"
}
}
]
}

Use Cases​

  • Premium/VIP content
  • Discount notifications
  • Shipping status messages
  • Membership tier benefits
  • Conditional calls-to-action
  • Personalized content sections

Interactive Components​

Button​

Call-to-action button with clickable link.

Template Support: PDF templates only (not available in Excel)

Properties​

PropertyTypeRequiredDefaultDescription
textstringYes-Button text (supports {{variables}})
hrefstringYes-Button URL (supports {{variables}})
alignmentenumNoleftAlignment: "left", "center", "right"
backgroundColorstringNo#007bffBackground color
colorstringNo#ffffffText color
borderRadiusstringNo"4px"Border radius
fontSizenumberNo16Font size (8-48)
fontWeightstringNo"normal"Font weight: "normal", "bold", etc.
paddingstringNo"12px 24px"CSS padding value
textDecorationstringNo"none"Text decoration: "none", "underline"

Example - Primary CTA​

{
"type": "button",
"id": "get-started-btn",
"props": {
"text": "Get Started",
"href": "https://example.com/signup",
"alignment": "center",
"backgroundColor": "#007bff",
"color": "#ffffff",
"borderRadius": "8px",
"fontSize": 18,
"fontWeight": "bold",
"padding": "16px 32px"
}
}

Example - Dynamic URL​

{
"type": "button",
"id": "view-order-btn",
"props": {
"text": "View Order #{{orderNumber}}",
"href": "https://example.com/orders/{{orderId}}",
"alignment": "center",
"backgroundColor": "#28a745",
"color": "#ffffff"
}
}

Button Styling Presets​

Primary Button (default):

{
"backgroundColor": "#007bff",
"color": "#ffffff",
"borderRadius": "4px",
"padding": "12px 24px"
}

Success Button:

{
"backgroundColor": "#28a745",
"color": "#ffffff",
"borderRadius": "4px",
"padding": "12px 24px"
}

Danger/Alert Button:

{
"backgroundColor": "#dc3545",
"color": "#ffffff",
"borderRadius": "4px",
"padding": "12px 24px"
}

Secondary/Outline Button:

{
"backgroundColor": "transparent",
"color": "#007bff",
"border": "2px solid #007bff",
"borderRadius": "4px",
"padding": "10px 22px"
}

Use Cases​

  • Call-to-action buttons
  • Order confirmation links
  • Account activation
  • Password reset links
  • Survey/feedback links
  • Download buttons

QR Code​

QR code component for scannable information.

Template Support: PDF templates only (not available in Excel)

Properties​

PropertyTypeRequiredDefaultDescription
valuestringYes-QR code content (max 2,953 chars, supports {{variables}})
sizenumber/stringNo200QR code size (50-1000 pixels or CSS value)
errorCorrectionLevelenumNoMError correction: "L" (7%), "M" (15%), "Q" (25%), "H" (30%)
marginnumberNo4Quiet zone margin (0-10)
colorstringNo#000000Foreground color
backgroundColorstringNo#ffffffBackground color
alignenumNoleftAlignment: "left", "center", "right"
altstringNo""Alt text for accessibility
styleobjectNo-Additional styling

Error Correction Levels​

  • L (Low): 7% error correction - smallest QR code, best for clean environments
  • M (Medium): 15% error correction - balanced size and reliability (recommended)
  • Q (Quartile): 25% error correction - good for printed materials
  • H (High): 30% error correction - largest code, best for damaged/dirty environments

Example - Event Ticket​

{
"type": "qr-code",
"id": "ticket-qr",
"props": {
"value": "TICKET:{{ticketId}}:{{eventId}}:{{attendeeEmail}}",
"size": 250,
"errorCorrectionLevel": "H",
"margin": 4,
"align": "center",
"alt": "Event Ticket QR Code"
}
}

Example - vCard Contact​

{
"type": "qr-code",
"id": "contact-qr",
"props": {
"value": "BEGIN:VCARD\nVERSION:3.0\nFN:{{fullName}}\nEMAIL:{{email}}\nTEL:{{phone}}\nEND:VCARD",
"size": 200,
"errorCorrectionLevel": "M",
"align": "center"
}
}

Example - WiFi Credentials​

{
"type": "qr-code",
"id": "wifi-qr",
"props": {
"value": "WIFI:T:WPA;S:{{networkName}};P:{{password}};;",
"size": 200,
"errorCorrectionLevel": "H",
"margin": 4,
"align": "center",
"alt": "WiFi Network QR Code"
}
}
{
"type": "qr-code",
"id": "payment-qr",
"props": {
"value": "https://example.com/pay/{{invoiceId}}?amount={{amount}}&currency={{currency}}",
"size": 300,
"errorCorrectionLevel": "M",
"align": "center"
}
}

Common QR Code Formats​

URL:

https://example.com/path

PDF:

mailto:support@example.com?subject=Support%20Request

Phone:

tel:+1234567890

SMS:

sms:+1234567890?body=Hello

vCard (Contact):

BEGIN:VCARD
VERSION:3.0
FN:John Doe
EMAIL:john@example.com
TEL:+1234567890
END:VCARD

WiFi:

WIFI:T:WPA;S:NetworkName;P:Password;;

Geo Location:

geo:37.7749,-122.4194

Use Cases​

  • Event tickets
  • Contact information sharing
  • WiFi access
  • Payment links
  • Product authentication
  • Mobile app downloads
  • Survey links
  • Loyalty program enrollment

Advanced Components​

Component Nesting Rules​

Allowed Nesting:

  • Container → any component (except itself)
  • Columns → any component per column
  • Table Layout → any component per cell
  • Loop → most components (no nested loops or conditionals)
  • Conditional → most components (no nested conditionals or loops)

Forbidden Nesting:

  • Loop inside Loop
  • Loop inside Conditional
  • Conditional inside Loop
  • Conditional inside Conditional
  • Button inside Button
  • QR Code inside QR Code

Component Positioning (Attachments Only)​

For PDF and Excel attachments, most components support absolute positioning:

{
"position": {
"x": 100,
"y": 200
}
}
  • x: Horizontal position in pixels
  • y: Vertical position in pixels (or "auto" for flow layout)

Variable References in Components​

All text-based properties support Handlebars syntax:

Simple Variables:

{{userName}}
{{orderNumber}}
{{companyName}}

Nested Properties:

{{user.firstName}}
{{order.shippingAddress.city}}
{{product.pricing.amount}}

Array Elements (in loops):

{{item.name}}
{{product[0].price}}

Constants:

{{COMPANY_NAME}}
{{SUPPORT_EMAIL}}
{{TAX_RATE}}

Best Practices​

Design Principles​

1. Mobile-First Design

  • Use stackOnMobile: true for columns
  • Limit image widths (max 600px for standard page width)
  • Use readable font sizes (16px minimum)
  • Provide adequate spacing and padding

2. Accessibility

  • Always include alt text for images
  • Use semantic heading levels (H1 → H2 → H3)
  • Ensure sufficient color contrast (4.5:1 minimum)
  • Provide descriptive button text

3. Performance

  • Optimize image sizes before uploading
  • Limit nested component depth (max 5 levels)
  • Use calculated columns instead of loops when possible

4. Consistency

  • Use consistent colors throughout template
  • Maintain uniform spacing between sections
  • Apply consistent button styling
  • Use standard font sizes for hierarchy

Component Selection Guide​

When to use Container:

  • Group related content
  • Apply consistent styling to sections
  • Create visual cards or panels
  • Control maximum width

When to use Columns:

  • Side-by-side layouts
  • Feature grids
  • Responsive layouts that stack on mobile

When to use Table Layout:

  • Fixed grid positioning
  • Label-value pairs
  • Simple structured data without headers

When to use Table:

  • Tabular data with headers
  • Dynamic data from arrays
  • Calculations and formulas
  • Sortable/filterable data

When to use Loop:

  • Repeating content blocks
  • Product listings
  • Dynamic item counts
  • Personalized content per item

When to use Conditional:

  • Show/hide based on user attributes
  • Personalized content
  • Status-dependent sections
  • Feature toggles

Common Patterns​

Pattern: Product Grid​

{
"type": "columns",
"id": "product-grid",
"props": { "columnCount": 3, "gap": "20px", "stackOnMobile": true },
"children": [
{
"type": "loop",
"id": "product-loop",
"props": { "dataSource": "{{products}}", "itemVariable": "product" },
"children": [
{
"type": "container",
"id": "product-card",
"props": { "padding": "20px", "backgroundColor": "#f8f9fa", "borderRadius": "8px" },
"children": [
{
"type": "image",
"id": "product-image",
"props": { "source": "{{product.imageUrl}}", "width": 200, "alignment": "center" }
},
{
"type": "heading",
"id": "product-name",
"props": { "level": 4 },
"content": "{{product.name}}"
},
{
"type": "text",
"id": "product-price",
"content": "${{product.price}}"
},
{
"type": "button",
"id": "buy-button",
"props": { "text": "Buy Now", "href": "{{product.buyUrl}}", "alignment": "center" }
}
]
}
]
}
]
}

Pattern: Invoice Header​

{
"type": "columns",
"id": "invoice-header",
"props": { "columnCount": 2, "gap": "20px" },
"children": [
{
"type": "container",
"id": "company-info",
"children": [
{
"type": "image",
"id": "logo",
"props": { "source": "{{companyLogo}}", "width": 150 }
},
{
"type": "text",
"id": "company-name",
"content": "{{companyName}}"
},
{
"type": "text",
"id": "company-address",
"content": "{{companyAddress}}"
}
]
},
{
"type": "table-layout",
"id": "invoice-details",
"props": { "rows": 3, "cols": 2, "cellPadding": "8px" },
"children": [
{ "type": "text", "id": "invoice-label", "content": "Invoice #:", "style": { "fontWeight": "bold" } },
{ "type": "text", "id": "invoice-num", "content": "{{invoiceNumber}}" },
{ "type": "text", "id": "date-label", "content": "Date:", "style": { "fontWeight": "bold" } },
{ "type": "text", "id": "date-value", "content": "{{invoiceDate}}" },
{ "type": "text", "id": "due-label", "content": "Due Date:", "style": { "fontWeight": "bold" } },
{ "type": "text", "id": "due-value", "content": "{{dueDate}}" }
]
}
]
}

Pattern: Status Card with Conditional​

{
"type": "container",
"id": "status-card",
"props": {
"padding": "20px",
"borderRadius": "8px",
"backgroundColor": "#ffffff",
"border": "2px solid #dee2e6"
},
"children": [
{
"type": "heading",
"id": "status-title",
"props": { "level": 2 },
"content": "Order Status"
},
{
"type": "conditional",
"id": "pending-status",
"props": { "condition": "status === 'pending'" },
"children": [
{
"type": "container",
"id": "pending-container",
"props": { "backgroundColor": "#fff3cd", "padding": "15px", "borderRadius": "4px" },
"children": [
{
"type": "text",
"id": "pending-text",
"content": "⏳ Your order is being processed.",
"style": { "color": "#856404" }
}
]
}
]
},
{
"type": "conditional",
"id": "shipped-status",
"props": { "condition": "status === 'shipped'" },
"children": [
{
"type": "container",
"id": "shipped-container",
"props": { "backgroundColor": "#d4edda", "padding": "15px", "borderRadius": "4px" },
"children": [
{
"type": "text",
"id": "shipped-text",
"content": "📦 Your order has shipped! Track: {{trackingNumber}}",
"style": { "color": "#155724" }
},
{
"type": "button",
"id": "track-button",
"props": {
"text": "Track Package",
"href": "{{trackingUrl}}",
"backgroundColor": "#28a745",
"alignment": "center"
}
}
]
}
]
}
]
}

Complete Examples​

Example 1: Order Confirmation Document​

{
"subject": "Order Confirmation #{{orderNumber}}",
"preheader": "Thank you for your order!",
"body": [
{
"type": "container",
"id": "header",
"props": {
"backgroundColor": "#007bff",
"padding": "30px 20px",
"maxWidth": "600px"
},
"children": [
{
"type": "image",
"id": "logo",
"props": {
"source": "https://example.com/logo-white.png",
"width": 200,
"alignment": "center"
}
}
]
},
{
"type": "container",
"id": "main-content",
"props": {
"padding": "40px 20px",
"maxWidth": "600px",
"backgroundColor": "#ffffff"
},
"children": [
{
"type": "heading",
"id": "thank-you",
"props": { "level": 1 },
"content": "Thank You for Your Order!",
"style": { "textAlign": "center", "color": "#333333" }
},
{
"type": "text",
"id": "confirmation-message",
"content": "Hi {{customerName}}, we've received your order and will send you shipping confirmation as soon as your order ships.",
"style": { "textAlign": "center", "fontSize": 16, "color": "#666666" }
},
{
"type": "spacer",
"id": "spacer-1",
"props": { "height": "30px" }
},
{
"type": "table-layout",
"id": "order-info",
"props": {
"rows": 3,
"cols": 2,
"borderWidth": "0px",
"cellPadding": "10px",
"width": "100%"
},
"children": [
{ "type": "text", "id": "order-label", "content": "Order Number:", "style": { "fontWeight": "bold" } },
{ "type": "text", "id": "order-value", "content": "{{orderNumber}}" },
{ "type": "text", "id": "date-label", "content": "Order Date:", "style": { "fontWeight": "bold" } },
{ "type": "text", "id": "date-value", "content": "{{orderDate}}" },
{ "type": "text", "id": "total-label", "content": "Total:", "style": { "fontWeight": "bold" } },
{ "type": "text", "id": "total-value", "content": "${{orderTotal}}", "style": { "fontWeight": "bold", "color": "#007bff" } }
]
},
{
"type": "spacer",
"id": "spacer-2",
"props": { "height": "30px" }
},
{
"type": "divider",
"id": "divider-1",
"props": { "thickness": 2, "color": "#e0e0e0" }
},
{
"type": "spacer",
"id": "spacer-3",
"props": { "height": "30px" }
},
{
"type": "heading",
"id": "items-heading",
"props": { "level": 2 },
"content": "Order Items",
"style": { "color": "#333333" }
},
{
"type": "table",
"id": "order-items",
"props": {
"dataSource": "{{orderItems}}",
"showHeader": true,
"columns": [
{ "header": "Item", "field": "name", "width": "50%", "align": "left" },
{ "header": "Qty", "field": "quantity", "width": "15%", "align": "center" },
{ "header": "Price", "field": "unitPrice", "width": "20%", "align": "right", "format": { "type": "number", "preset": "CURRENCY", "currency": "USD" } },
{ "header": "Total", "isCalculated": true, "expression": "quantity * unitPrice", "width": "15%", "align": "right", "format": { "type": "number", "preset": "CURRENCY", "currency": "USD" } }
]
}
},
{
"type": "spacer",
"id": "spacer-4",
"props": { "height": "30px" }
},
{
"type": "button",
"id": "view-order-button",
"props": {
"text": "View Order Details",
"href": "https://example.com/orders/{{orderId}}",
"alignment": "center",
"backgroundColor": "#007bff",
"padding": "16px 32px",
"fontSize": 18
}
}
]
},
{
"type": "container",
"id": "footer",
"props": {
"backgroundColor": "#f8f9fa",
"padding": "30px 20px",
"maxWidth": "600px"
},
"children": [
{
"type": "text",
"id": "footer-text",
"content": "Questions? Contact us at support@example.com",
"style": { "textAlign": "center", "fontSize": 14, "color": "#666666" }
}
]
}
]
}

Example 2: Sales Report (PDF Attachment)​

{
"title": "Monthly Sales Report",
"body": [
{
"type": "heading",
"id": "report-title",
"props": { "level": 1 },
"content": "Sales Report - {{reportMonth}}",
"style": { "fontSize": 24, "fontWeight": "bold", "color": "#333333" }
},
{
"type": "text",
"id": "generated-date",
"content": "Generated: {{generatedDate}}",
"style": { "fontSize": 12, "color": "#666666" }
},
{
"type": "spacer",
"id": "spacer-1",
"props": { "height": "20px" }
},
{
"type": "columns",
"id": "summary-cards",
"props": { "columnCount": 3, "gap": "20px" },
"children": [
{
"type": "container",
"id": "revenue-card",
"props": { "padding": "20px", "backgroundColor": "#e7f3ff", "borderRadius": "8px" },
"children": [
{ "type": "text", "id": "revenue-label", "content": "Total Revenue", "style": { "fontSize": 14, "color": "#666666" } },
{ "type": "text", "id": "revenue-value", "content": "${{totalRevenue}}", "style": { "fontSize": 28, "fontWeight": "bold", "color": "#007bff" } }
]
},
{
"type": "container",
"id": "orders-card",
"props": { "padding": "20px", "backgroundColor": "#d4edda", "borderRadius": "8px" },
"children": [
{ "type": "text", "id": "orders-label", "content": "Total Orders", "style": { "fontSize": 14, "color": "#666666" } },
{ "type": "text", "id": "orders-value", "content": "{{totalOrders}}", "style": { "fontSize": 28, "fontWeight": "bold", "color": "#28a745" } }
]
},
{
"type": "container",
"id": "avg-card",
"props": { "padding": "20px", "backgroundColor": "#fff3cd", "borderRadius": "8px" },
"children": [
{ "type": "text", "id": "avg-label", "content": "Avg Order Value", "style": { "fontSize": 14, "color": "#666666" } },
{ "type": "text", "id": "avg-value", "content": "${{avgOrderValue}}", "style": { "fontSize": 28, "fontWeight": "bold", "color": "#ffc107" } }
]
}
]
},
{
"type": "spacer",
"id": "spacer-2",
"props": { "height": "30px" }
},
{
"type": "chart",
"id": "revenue-chart",
"props": {
"chartType": "bar",
"dataSource": "{{dailySales}}",
"xAxis": "date",
"yAxis": "revenue",
"title": "Daily Revenue",
"width": 800,
"height": 400,
"xAxisLabel": "Date",
"yAxisLabel": "Revenue ($)",
"style": {
"colors": ["#007bff"],
"showGridLines": true,
"backgroundColor": "#ffffff"
}
}
},
{
"type": "spacer",
"id": "spacer-3",
"props": { "height": "30px" }
},
{
"type": "heading",
"id": "products-heading",
"props": { "level": 2 },
"content": "Top Products",
"style": { "fontSize": 20, "fontWeight": "bold" }
},
{
"type": "table",
"id": "top-products",
"props": {
"dataSource": "{{topProducts}}",
"showHeader": true,
"showTotalsRow": true,
"totalsConfig": {
"label": "Total",
"labelColumn": "productName",
"aggregations": {
"unitsSold": "SUM",
"revenue": "SUM"
}
},
"columns": [
{ "header": "Product", "field": "productName", "width": "40%", "align": "left" },
{ "header": "Units Sold", "field": "unitsSold", "width": "20%", "align": "center" },
{ "header": "Revenue", "field": "revenue", "width": "20%", "align": "right", "format": { "type": "number", "preset": "CURRENCY", "currency": "USD" } },
{ "header": "% of Total", "isCalculated": true, "expression": "(revenue / totalRevenue) * 100", "width": "20%", "align": "right", "format": { "type": "number", "preset": "PERCENT", "decimals": 1 } }
]
}
}
]
}

Example 3: Event Invitation with QR Code​

{
"subject": "You're Invited: {{eventName}}",
"preheader": "{{eventDate}} at {{eventLocation}}",
"body": [
{
"type": "container",
"id": "hero",
"props": {
"backgroundColor": "#667eea",
"padding": "60px 20px",
"maxWidth": "600px"
},
"children": [
{
"type": "heading",
"id": "event-title",
"props": { "level": 1 },
"content": "{{eventName}}",
"style": { "fontSize": 32, "fontWeight": "bold", "color": "#ffffff", "textAlign": "center" }
},
{
"type": "text",
"id": "event-tagline",
"content": "{{eventTagline}}",
"style": { "fontSize": 18, "color": "rgba(255,255,255,0.9)", "textAlign": "center" }
}
]
},
{
"type": "container",
"id": "main-content",
"props": {
"padding": "40px 20px",
"maxWidth": "600px",
"backgroundColor": "#ffffff"
},
"children": [
{
"type": "text",
"id": "greeting",
"content": "Hi {{attendeeName}},",
"style": { "fontSize": 18, "fontWeight": "bold", "color": "#333333" }
},
{
"type": "spacer",
"id": "spacer-1",
"props": { "height": "15px" }
},
{
"type": "text",
"id": "invitation-text",
"content": "You're invited to join us for {{eventName}}! We're excited to have you there.",
"style": { "fontSize": 16, "color": "#666666", "lineHeight": 1.6 }
},
{
"type": "spacer",
"id": "spacer-2",
"props": { "height": "30px" }
},
{
"type": "divider",
"id": "divider-1",
"props": { "thickness": 1, "color": "#e0e0e0" }
},
{
"type": "spacer",
"id": "spacer-3",
"props": { "height": "30px" }
},
{
"type": "columns",
"id": "event-details",
"props": { "columnCount": 2, "gap": "20px" },
"children": [
{
"type": "container",
"id": "details-left",
"children": [
{ "type": "text", "id": "date-label", "content": "📅 Date", "style": { "fontSize": 14, "fontWeight": "bold", "color": "#999999" } },
{ "type": "text", "id": "date-value", "content": "{{eventDate}}", "style": { "fontSize": 16, "color": "#333333", "marginTop": "5px" } },
{ "type": "spacer", "id": "detail-spacer-1", "props": { "height": "15px" } },
{ "type": "text", "id": "time-label", "content": "🕐 Time", "style": { "fontSize": 14, "fontWeight": "bold", "color": "#999999" } },
{ "type": "text", "id": "time-value", "content": "{{eventTime}}", "style": { "fontSize": 16, "color": "#333333", "marginTop": "5px" } }
]
},
{
"type": "container",
"id": "details-right",
"children": [
{ "type": "text", "id": "location-label", "content": "📍 Location", "style": { "fontSize": 14, "fontWeight": "bold", "color": "#999999" } },
{ "type": "text", "id": "location-value", "content": "{{eventLocation}}", "style": { "fontSize": 16, "color": "#333333", "marginTop": "5px" } },
{ "type": "spacer", "id": "detail-spacer-2", "props": { "height": "15px" } },
{ "type": "text", "id": "dress-label", "content": "👔 Dress Code", "style": { "fontSize": 14, "fontWeight": "bold", "color": "#999999" } },
{ "type": "text", "id": "dress-value", "content": "{{dressCode}}", "style": { "fontSize": 16, "color": "#333333", "marginTop": "5px" } }
]
}
]
},
{
"type": "spacer",
"id": "spacer-4",
"props": { "height": "30px" }
},
{
"type": "divider",
"id": "divider-2",
"props": { "thickness": 1, "color": "#e0e0e0" }
},
{
"type": "spacer",
"id": "spacer-5",
"props": { "height": "30px" }
},
{
"type": "heading",
"id": "ticket-heading",
"props": { "level": 2 },
"content": "Your Ticket",
"style": { "fontSize": 20, "textAlign": "center", "color": "#333333" }
},
{
"type": "text",
"id": "ticket-instructions",
"content": "Present this QR code at the entrance for quick check-in",
"style": { "fontSize": 14, "textAlign": "center", "color": "#666666" }
},
{
"type": "spacer",
"id": "spacer-6",
"props": { "height": "20px" }
},
{
"type": "qr-code",
"id": "ticket-qr",
"props": {
"value": "EVENT:{{eventId}}:ATTENDEE:{{attendeeId}}:TICKET:{{ticketId}}",
"size": 250,
"errorCorrectionLevel": "H",
"align": "center",
"alt": "Event Ticket QR Code"
}
},
{
"type": "text",
"id": "ticket-number",
"content": "Ticket #{{ticketId}}",
"style": { "fontSize": 12, "textAlign": "center", "color": "#999999", "marginTop": "10px" }
},
{
"type": "spacer",
"id": "spacer-7",
"props": { "height": "30px" }
},
{
"type": "button",
"id": "add-calendar-button",
"props": {
"text": "Add to Calendar",
"href": "{{calendarLink}}",
"alignment": "center",
"backgroundColor": "#667eea",
"padding": "14px 28px"
}
}
]
},
{
"type": "container",
"id": "footer",
"props": {
"backgroundColor": "#f8f9fa",
"padding": "30px 20px",
"maxWidth": "600px"
},
"children": [
{
"type": "text",
"id": "footer-text",
"content": "Can't make it? Let us know at {{eventEmail}}",
"style": { "textAlign": "center", "fontSize": 14, "color": "#666666" }
}
]
}
]
}

Summary​

This guide covered the available template components:

  • 5 Layout Components: Container, Columns, Table Layout, Divider, Spacer
  • 6 Content Components: Text, Heading, Rich Text, Image, List, SVG
  • 4 Data Components: Table, Chart, Loop, Conditional
  • 3 Interactive Components: Button, QR Code, Barcode
  • 3 Utility Components: Key-Value, Page Break, Formula
  • 9 Form Components (PDF only, Starter plan+): Text Field, Textarea, Checkbox, Radio, Dropdown, Date, Signature, Button, Image

Each component includes detailed property specifications, examples, and use cases. Combined with the Variables & Dynamic Content guide, you have everything needed to create powerful, dynamic templates for PDF and Excel documents.

For more information:


Need Help? Contact support at support@rynko.dev