Button
Button
Field-level catalog tables below stay in English — they match the machine design schema used by the editor, API, and MCP.
Decoration and visibility use Decoration & visibility (BlockShell).
Call-to-action or named dataRequest trigger. Prefer sitemap routes for navigate. For forms/search use action runRequest|runMutation with requestName — request behavior (filters, fieldValues, resultWrites) lives on root.props.dataRequests. loadingText/successText/errorText update the label and a status line under the button. resetOnSuccess (default true for runMutation) clears request field variables after a short success display. Client validation blocks empty required fields via native validity before the request runs (does not set request error / errorText). Fill and outline chrome come from decoration (background and border), not a separate style prop. Icons live as
{{icon:…}}chips intext(not a separate icon prop). Icon-only controls get an accessible name fromariaLabel, else a derived label (social brands, Menu for bars-*, Theme for theme action). Modal toggles set aria-expanded. OptionaliconSize/iconGap(px) override auto icon scale (~0.85× fontSize) and gap. For non-stretch CTAs keepshell.box.sizeByBreakpoint.*.widthMode: "fitContent"(ButtonBlock defaults include this).
Examples
Primary CTA
{
"text": "Create thread",
"action": {
"url": "/categories/[id]/new"
}
}
Run search request
{
"text": "Search",
"action": {
"action": "runRequest",
"requestName": "searchX",
"loadingText": "Searching…"
}
}
Icon-only menu toggle
{
"text": "{{icon:bars-3}}",
"ariaLabel": "Menu",
"action": {
"action": "modal",
"modalId": "ModalBlock-header-menu"
}
}
Fields
text
Button label. Mix literal text with {{var:id}}, {{bind:id}}, and {{icon:iconId}} chips. The icon picker appends an icon chip at the end; drag chips in the label to reposition. An older icon prop is migrated into a leading {{icon:…}} chip on design write / editor mount.
text: "Browse {{icon:arrow-right}}"
ariaLabel
Accessible name for icon-only buttons/links. Overrides icon-derived labels. Ignored when visible text is present.
ariaLabel: "Menu"
typography
textAlign
Horizontal text alignment.
typography: {
textAlign: "center"
}
fontSize
Unit: px
Font size in pixels.
typography: {
fontSize: 48
}
fontWeight
Numeric font weight (CSS font-weight).
typography: {
fontWeight: 600
}
fontFamily
Font family id. Theme tokens (theme-heading, theme-body, theme-mono) or a rich-text font id.
typography: {
fontFamily: "theme-heading"
}
italic
When true, renders the text in italic style.
typography: {
italic: false
}
style
iconSize
Optional icon size in px. When omitted, icons auto-scale to ~0.85× fontSize.
style: {
iconSize: 20
}
iconGap
Optional gap between icon chips and text in px. When omitted, uses a font-based gap.
style: {
iconGap: 8
}
color
textColorLight
Text color used in light theme.
color: {
textColorLight: "#111827"
}
action
action
See shared option catalog action.
action: {
action: "navigate"
}
url
Href. May include object route params like /threads/[id].
modalId
When action is modal, the target ModalBlock’s stable props.id. Renaming the modal does not change this id. Missing targets no-op at runtime.
action: {
modalId: "ModalBlock-abc123"
}
requestName
Named dataRequest for runRequest/runMutation.
loadingText
Label while the named request is loading.
successText
Label after a successful run.
errorText
Label when the named request fails.
resetOnSuccess
When true (default for runMutation), clear request field variables after a short delay. Success text still displays for several seconds either way. When false, keep field values.
action: {
resetOnSuccess: false
}
Default props
{
"text": "Button",
"typography": {
"textAlign": "left",
"fontSize": 18,
"fontWeight": 600,
"fontFamily": "theme-heading",
"italic": false
},
"color": {
"textColorLight": "",
"textColorDark": "",
"textColorHoverLight": "",
"textColorHoverDark": "",
"textColorActiveLight": "",
"textColorActiveDark": ""
},
"action": {
"action": "navigate",
"openInNewTab": false,
"copiedText": "Copied",
"socialNetwork": "whatsapp",
"returnUrl": "/",
"unreadBadge": true
},
"shell": {
"customizeEnabled": false,
"pointerEvents": "auto",
"decorationBySelector": {},
"visibility": {
"showOnBreakpoints": {},
"showOnLocales": {},
"authVisibility": "all",
"routeLockVisibility": "all",
"roleVisibility": [],
"entryActionVisibility": "all",
"queryPageVisibility": "all",
"hideWhenEmpty": ""
},
"anchor": {
"anchorId": "",
"anchorKey": ""
},
"box": {
"padding": "none",
"paddingEnabled": false,
"marginsEnabled": false,
"sizeByBreakpoint": {
"mobile": {
"widthMode": "fitContent"
},
"desktop": {
"widthMode": "fitContent"
}
},
"positionEnabled": false,
"positionByBreakpoint": {}
},
"background": {
"backgroundEnabled": false,
"backgroundWidth": "page",
"backgroundKind": "solid",
"backgroundColorLight": "",
"backgroundColorDark": "",
"gradientType": "linear",
"gradientAngle": 180,
"gradientColors": [
{
"light": "",
"dark": "",
"offset": 50
},
{
"light": "",
"dark": "",
"offset": 50
}
],
"gradientColor1Light": "",
"gradientColor1Dark": "",
"gradientColor2Light": "",
"gradientColor2Dark": "",
"backgroundImageSrc": "",
"backgroundImageMode": "cover",
"backgroundRepeatSize": 100,
"backgroundPosition": "center",
"backgroundMotionEnabled": false,
"backgroundMotionDirectionDeg": 0,
"backgroundMotionSpeed": 20,
"backgroundMotionRotateDegPerSec": 0,
"backgroundVideoSrc": "",
"backgroundVideoFit": "cover",
"backgroundVideoLoop": true,
"backgroundVideoRepeatSize": 100,
"backgroundAnimationMode": "particle",
"backgroundAnimShape": "circle",
"backgroundAnimSvgSrc": "",
"backgroundAnimColorMode": "solid",
"backgroundAnimColorLight": "#ffffff88",
"backgroundAnimColorDark": "#ffffff66",
"backgroundAnimSize": 12,
"backgroundAnimJitter": 0.2,
"backgroundParticleCount": 40,
"backgroundParticleLifetimeSec": 4,
"backgroundParticleSpeed": 40,
"backgroundParticleAnimType": "fade",
"backgroundParticleFromSide": "left",
"backgroundParticleToSide": "right",
"backgroundGridStyle": "cells",
"backgroundGridMotionDirectionDeg": 0,
"backgroundGridMotionSpeed": 0,
"backgroundGridRotateDegPerSec": 0,
"backgroundGridHoverGrowLimitPct": 50,
"backgroundGridHoverRotateLimitDeg": 0,
"backgroundGridReactionTimeSec": 1,
"backgroundGridHoverGrow": true,
"backgroundGridHoverRotate": false,
"backgroundGridHoverColor": false,
"backgroundGridHoverColorLight": "#ffffff55",
"backgroundGridHoverColorDark": "#ffffff33",
"backgroundGridReactionSpeed": 1,
"backgroundBackdropEnabled": false,
"backgroundBackdropBlurPx": 0,
"backgroundBackdropBrightness": 1,
"backgroundBackdropContrast": 1,
"backgroundBackdropSaturate": 1,
"backgroundBackdropGrayscale": 0,
"backgroundBackdropSepia": 0,
"backgroundBackdropHueRotateDeg": 0
},
"border": {
"borderEnabled": false,
"borderColorLight": "",
"borderColorDark": "",
"borderStyle": "solid"
},
"shadow": {
"shadowEnabled": false,
"shadowValueLight": "",
"shadowValueDark": ""
},
"effects": {
"effectsEnabled": false,
"opacity": 1,
"filterBlurPx": 0,
"filterBrightness": 1,
"filterContrast": 1,
"filterSaturate": 1,
"filterGrayscale": 0,
"filterSepia": 0,
"filterHueRotateDeg": 0,
"filterDropShadowOffsetX": 0,
"filterDropShadowOffsetY": 0,
"filterDropShadowBlur": 0,
"filterDropShadowColorLight": "",
"filterDropShadowColorDark": "",
"mixBlendMode": "normal"
},
"scrollAnimation": {
"scrollAnimationEnabled": false,
"scrollAnimationType": "fadeIn",
"scrollAnimationDuration": 600,
"scrollAnimationDelay": 0
},
"cursorTilt": {
"cursorTiltEnabled": false,
"cursorTiltIntensity": 12
},
"wander": {
"wanderEnabled": false,
"wanderSpeed": 40,
"wanderJitter": 40,
"wanderTurnRadius": 50,
"wanderTurnSmoothness": 40,
"wanderLimits": "parent"
},
"transform": {
"transformEnabled": false,
"transformRotateX": 0,
"transformRotateY": 0,
"transformRotateZ": 0,
"transformTranslateX": 0,
"transformTranslateY": 0,
"transformTranslateZ": 0,
"transformScale": 1
}
}
}