PPTX

Shapes and Text

Create shapes with formatted text, paragraphs, alignment, lists, and text fitting

Shapes are the primary building blocks of a slide. Each slide's children array can contain shape objects with textBody for text content.

Basic Shape

import { generatePresentation } from "@office-open/pptx";
{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "1.3cm",
            "width": "13.2cm",
            "height": "7.9cm",
            "textBody": { "text": "Simple text" }
          }
        }
      ]
    }
  ]
}

Geometry Presets

Use the geometry option to set the shape type:

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "2.6cm",
            "y": "2.6cm",
            "width": "5.3cm",
            "height": "4.0cm",
            "geometry": "ellipse",
            "fill": "4472C4",
            "outline": { "color": "2E74B5", "width": 12700 },
            "textBody": { "text": "Ellipse" }
          }
        },
        {
          "shape": {
            "x": "10.6cm",
            "y": "2.6cm",
            "width": "5.3cm",
            "height": "4.0cm",
            "geometry": "triangle",
            "fill": "ED7D31",
            "outline": { "color": "C5504B", "width": 12700 },
            "textBody": { "text": "Triangle" }
          }
        }
      ]
    }
  ]
}

Available geometries:

GeometryShape
"rect"Rectangle (default)
"ellipse"Ellipse / circle
"roundRect"Rounded rectangle
"triangle"Triangle
"diamond"Diamond
"star5"Five-pointed star
"hexagon"Hexagon
"chevron"Chevron arrow
"arrow"Arrow

Use outline to add a border: { "color": "2E74B5", "width": 12700 }. Do NOT use strokeColor or strokeWidth — these are not valid properties.

Paragraphs and Text Runs

Use textBody.paragraphs for full control over text formatting:

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "1.3cm",
            "width": "15.9cm",
            "height": "6.6cm",
            "textBody": {
              "paragraphs": [
                {
                  "children": [{ "text": "Bold title", "bold": true, "size": 28, "fill": "2E74B5" }]
                },
                {
                  "children": [
                    { "text": "Normal text with " },
                    { "text": "italic", "italic": true },
                    { "text": " and " },
                    { "text": "colored", "fill": "FF0000", "underline": "single" }
                  ]
                }
              ]
            }
          }
        }
      ]
    }
  ]
}

TextRun Formatting Options

// Text runs are plain objects with formatting properties:
{
  text: "Formatted text",
  size: 24, // Size in points
  bold: true,
  italic: true,
  underline: "single", // "single" | "double" | "none"
  strike: "sngStrike", // "sngStrike" | "dblStrike" | "noStrike"
  fill: "4472C4", // Hex color without #
  font: "Calibri", // String sets latin + eastAsia; object sets per-script
  // font: { latin: "Calibri", eastAsia: "SimSun", complexScript: "Arial", symbol: "Symbol" },
  highlight: { value: "FFFF00" }, // Text highlight color (a:highlight)
  kern: 12, // Kerning threshold in points
  outline: true, // a:ln — true emits a default line; an OutlineOptions object round-trips
  shadow: true, // a:effectLst — true emits a default outer shadow; an EffectListOptions object round-trips
  hyperlink: { url: "https://example.com" }, // External URL
  // hyperlink: { slide: 2 }, // Internal slide jump (1-based)
}

outline and shadow accept true for a sensible default or a full options object — see Outline and Effects for the complete shapes. See Links for hyperlink (external url or internal slide jump).

Alignment

// Paragraph alignment via the properties option:
{
  paragraph: {
    properties: { alignment: "left" }, // "left" | "center" | "right" | "justify"
    children: [{ text: "Aligned text" }],
  },
}

Paragraph Properties

Beyond alignment, paragraph properties carries indent, spacing, direction, tab stops, and default run formatting (a:defRPr):

{
  paragraph: {
    properties: {
      indentLevel: 1, // Outline level (a:pPr @lvl)
      indent: 457200, // First-line indent in EMU (a:pPr @indent)
      marginIndent: 457200, // Left margin in EMU (@marL)
      marginRight: 457200, // Right margin in EMU (@marR)
      lineSpacingPercent: 150, // 150% of single line spacing (a:lnSpc)
      spaceBefore: 457, // Space before in points (a:spcBef)
      spaceAfter: 457, // Space after in points (a:spcAft)
      rightToLeft: true, // Right-to-left text flow (@rtl)
      eastAsianLineBreak: true, // East Asian line breaking (@eaLnBrk)
      latinLineBreak: true, // Latin line breaking (@latinLnBrk)
      tabStops: [{ position: 914400, alignment: "l" }], // @pos in EMU, "l"|"ctr"|"r"|"dec"
      fontAlignment: "base", // "auto" | "t" | "ctr" | "b" | "base" (@fontAlgn)
      defaultRunProperties: { size: 24, font: "Calibri" }, // a:defRPr — default run formatting
    },
    children: [{ text: "Paragraph text" }],
  },
}

Bullet Lists

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "1.3cm",
            "width": "15.9cm",
            "height": "9.3cm",
            "textBody": {
              "paragraphs": [
                {
                  "properties": { "bullet": { "type": "char", "char": "" } },
                  "children": [{ "text": "First item" }]
                },
                {
                  "properties": { "bullet": { "type": "char", "char": "" } },
                  "children": [{ "text": "Second item" }]
                },
                {
                  "properties": { "bullet": { "type": "autoNum", "format": "arabicPeriod" } },
                  "children": [{ "text": "Numbered item" }]
                }
              ]
            }
          }
        }
      ]
    }
  ]
}

Text Anchor (Vertical Alignment)

Control vertical positioning of text within the shape:

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "1.3cm",
            "width": "13.2cm",
            "height": "7.9cm",
            "textBody": {
              "anchor": "t",
              "text": "Top-aligned text"
            }
          }
        }
      ]
    }
  ]
}

Auto-Fit Text

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "1.3cm",
            "width": "10.6cm",
            "height": "5.3cm",
            "textBody": {
              "text": "This text will shrink to fit the shape",
              "autoFit": "normal"
            }
          }
        }
      ]
    }
  ]
}

Rotation and Flip

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "1.3cm",
            "width": "7.9cm",
            "height": "5.3cm",
            "rotation": 45,
            "flipHorizontal": true,
            "textBody": { "text": "Rotated shape" }
          }
        }
      ]
    }
  ]
}

Text Columns

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "1.3cm",
            "width": "21.2cm",
            "height": "9.3cm",
            "textBody": {
              "columns": 2,
              "columnSpacing": 0.5,
              "paragraphs": [
                { "children": [{ "text": "Column 1 content..." }] },
                { "children": [{ "text": "Column 2 content..." }] }
              ]
            }
          }
        }
      ]
    }
  ]
}

Text Margins

{
  "slides": [
    {
      "children": [
        {
          "shape": {
            "x": "1.3cm",
            "y": "2.6cm",
            "width": "15.9cm",
            "height": "7.9cm",
            "textBody": {
              "margins": { "top": 0.2, "bottom": 0.2, "left": 0.3, "right": 0.3 },
              "text": "Text with custom margins"
            }
          }
        }
      ]
    }
  ]
}
Copyright © 2026