mirror of
https://github.com/pdfme/pdfme.git
synced 2026-06-21 20:59:38 -04:00
* feat(playground): add presets and jsx form preview * fix(jsx): normalize table width weights * refactor(jsx): rename table column weights prop * fix(playground): handle invalid jsx templates * fix(playground): improve mobile preview sizing * docs(jsx): clarify table column weights * fix(playground): refine jsx preview followups * test(jsx): narrow table column weights assertion * fix(playground): ignore removed form input values
@pdfme/jsx
Small JSX authoring layer for creating pdfme templates from stacking layout primitives.
/** @jsxImportSource @pdfme/jsx */
import { MultiVariableText, Page, Stack, Text, renderToTemplate } from '@pdfme/jsx';
const { template, inputs } = await renderToTemplate(
<Page margin={{ x: 12, y: 16 }}>
<Stack gap={4}>
<Text size={18}>Invoice</Text>
<Text name="customerName">Alice</Text>
<MultiVariableText
name="message"
text="Hello **{name}**, status: `{status}`"
values={{ name: 'Alice **literal**', status: 'draft' }}
textFormat="inline-markdown"
/>
</Stack>
</Page>,
);
This package emits regular pdfme Template and inputs values. It does not depend on React;
it provides its own jsx-runtime and jsx-dev-runtime.
renderToTemplate is async because automatic text height measurement may need font data.
MVP constraints
TextandMultiVariableTextheights are measured with pdfme's text/rich text wrapping helpers whenheightis omitted. Pass an explicitheightwhen you need a fixed field box.Text textFormat="inline-markdown"is read-only only. EditableTextvalues use plain content.MultiVariableTextusestextor children as the template string and storesvaluesas the JSON input. Variable names are inferred from{name}placeholders and can also be passed withvariables.Imageusessrcas its initial content and is intended to be self-closing.Svgusessvgor children as its initial content.- With
name,ImageandSvgbecome input-backed schemas; withoutname, they are read-only content. Rectangle,Ellipse, andLineare static visual schemas for backgrounds, dividers, and simple shapes.Static,Header, andFootercan be used as direct children of the firstPageto render read-only header/footer style content into blankbasePdf.staticSchema. Their children use page coordinates, not page margin coordinates, and custombasePdfis not supported.Headeris a shorthand for<Static placement="top">;Footeris a shorthand for<Static placement="bottom">.
<Header>
<Text height={8}>Header</Text>
</Header>
<Footer>
<Text height={8}>Footer</Text>
</Footer>
- Multiple
Staticblocks with the same placement are concatenated in declaration order. Top blocks start at the top of the page; bottom blocks are stacked together in declaration order and anchored to the page bottom, so the last bottom block sits at the page edge. If top and bottom static content together exceed the page height, they may overlap. - Static content currently accepts read-only
Stack,Row,Box,Spacer,Text,Image,Svg,Rectangle,Ellipse, andLinecontent.MultiVariableText,List,Table, input-backed schemas, andPageBreakare rejected. Absolutecan be used insidePage, topStatic, orBoxas a small manual placement escape hatch. It uses the parent layout frame as its coordinate origin and does not advance the surrounding stack/row flow. Whenwidthorheightis omitted, it uses the remaining parent frame size fromx/y. DirectStack/Rowsupport is intentionally left for later; wrap with an explicit-sizeBoxwhen you need a local manual-placement frame inside flow content.
<Page margin={12}>
<Text height={8}>Body starts here</Text>
<Absolute x={120} y={0} width={60}>
<Text height={6}>Top-right note</Text>
</Absolute>
</Page>
- Layout children can use
margin.StackandRowsupportalignItemsfor simple cross-axis alignment without trying to implement full CSS/Flexbox. StackandRowsupportjustifyContent="start" | "center" | "end" | "space-between"for main-axis spacing.Stackuses this most predictably with an explicitheight;Rowuses it most predictably with an explicitwidth.Stackdefaults toalignItems="stretch"to preserve full-width stacking. Use an explicit childwidthwhen you wantalignItems="center"or"end"to visibly move that child.Rowdefaults toalignItems="start"and intentionally does not support cross-axis stretch yet.- Row children can use
flexGroworflexas a grow weight. Ifwidthis also set, it is used as the basis before remaining width is distributed.flexis only a short alias forflexGrow, not the CSSflexshorthand.
<Row width={120}>
<Text width={20} flex={1}>A</Text>
<Text width={20} flex={3}>B</Text>
</Row>
// A width: 40, B width: 80
flexGrow={0}withoutwidthproduces a zero-width Row child.PageBreakis supported only along aPage/Stack/Boxlayout path. It is rejected insideRow, leaf schemas,List, andTable.- All
Pagenodes in onerenderToTemplatecall must use the same page size, orientation, and margin because a pdfme blankbasePdfhas one shared size and padding. Table columnWeightsare relative column width weights, not millimeter widths. They are normalized to pdfmeheadWidthPercentages, for examplecolumnWeights={[70, 30]}. Missing or invalid weights default to1, so pass one weight per column when you need exact ratios. Earlier beta builds usedwidths; usecolumnWeightsgoing forward.