Image
Dot. Manual
Image
Dot. Manual
Back to home

Dot.

Install Dot. AppDiagnostic Tool

Quote

Quote/0
Pairing Quote/0How to Tap
Fixed ContentLoop Content
Share with Family and FriendsHow to Charge
Update DeviceReset NetworkReset DeviceChangelogNew

Rand The Pocket Prophet

Rand/0
Getting StartedWi-FiCustom Wallpaper
Features
MBTI GuideBook of AnswersFortuneCoin FlipDice RollWooden FishNumber Under TenClock
Bluetooth RemoteNewDownload Pocket NFC App
Update DeviceReset DeviceChangelogNew

Content & Services

Content Studio
RSS
Shortcuts
Co Create
Software
CastCardDiablo II Resurrected Terror Zone & Uber Diablo Alert ToolDot Calendar - Weather Calendar for Quote/0DotCanvasDotClientDot Crypto TickerDot Mate - Quote/0 Automation SchedulerIntelligent Poetry Weather Generation SystemDot ServiceDot Quote/0 Home Assistant Dashboard CardDot Quote/0 Home Assistant IntegrationMindReset Dot MCP (Lakphy)Quote/0 Send DemoQuote/0 + Calendar ShortcutQuote/0 Agent Skill (YangguangZhou)Quote/0 Evening SummaryQuote/0 Flash NoteQuote/0 Health ReminderQuote/0 + Holiday ShortcutQuote/0 MCP (stvlynn)Quote/0 MCP (thomaszdxsn)Quote/0 + WAY 2 Reminder ShortcutQuote/0 Yearly Progress CalendarQuote0 API Serverless MicroserviceQuote/0 AI Usage DashboardNewQuote0 Client Python SDKQuote/0 Token Usage DashboardNewQuote0 SDK & CLI (MrWillCom)Server Status
Hardware
IKEA SKÅDIS MountQuote/0 Carry Case HangerQuote/0 Desktop Charging Mini StandQuote/0 Desktop Stand (Andrrrrrrija)Quote/0 Desktop Stand (MindReset)Quote/0 Desktop Mini StandQuote/0 Monitor Mount (Kiiko)Quote/0 Excerpt Mount (GLB_wegoo777)Quote/0 Monitor Mount (TLL)Rand/0 Single Shoulder Bag Buckle 40mmNew
Developer Platform
What is an APIGet API KeyGet Device Serial NumberGet Device ListGet Device StatusGet TimezonesNewDevice SettingsNewSwitch to Next ContentList Device ContentControl Text ContentNewControl Image ContentNewControl Canvas ContentNewAI SkillNew
Roadmap

Explore More Possibilities

Request New ContentJoin Our Content Studio

Security

MSA-2025-08-001MSA-2025-09-001MSA-2025-09-002MSA-2025-10-001MSA-2025-10-002MSA-2025-10-003MSA-2026-04-001
Responsible Disclosure Policy

More

Service StatusPrivacy PolicyUser AgreementContact UsAbout MindReset
Content & ServicesDeveloper Platform
Image

Control Canvas Content

RSS

Quick Start

Requirements

  1. Get and save an API key from Dot. App;
  2. Get the serial number of a device you own;
  3. Make sure the device is powered and online;
  4. Add the Canvas API content to the device loop task in Dot. App Content Studio.

What Canvas API is for

Text API is best for quickly sending a text card, and Image API is best for showing one image. Canvas API lets you turn your own data into custom cards, dashboards, or small visual experiments.

windowData uses object elements

windowData is written with React-elements-like objects: each element is an object, type selects the element type, props contains style and content, and props.children can be text, one child element, or an array of child elements.

The outer container usually needs no padding

The device layout handles the basic spacing outside windowData.default. Let the outer element focus on structure, background, and alignment. When you need edge-to-edge rendering, a custom background, or FULL layout overrides, pass layoutFull.

Playground

POST
/api/authV2/open/device/:deviceId/canvas

Get your API key from Dot. App

Generated Code
1// Generating...

Request Body

Canvas API requests combine content data with a screen description. Use data for values the screen can read, and use windowData to describe the element structure. You can also pass taskAlias to label the item in the device task list, layoutFull to adjust the FULL layout, link to set the tap-to-open URL, and border to choose the screen border color.

To avoid conflicting meanings, do not use type, key, windowData, layoutFull, taskAlias, link, border, __proto__, constructor, or prototype as keys inside data.

{
	"refreshNow": true,
	"taskAlias": "Morning canvas",
	"data": {
		"title": "Canvas API",
		"message": "Hello Dot."
	},
	"windowData": {
		"default": [
			{
				"type": "div",
				"props": {
					"tw": "flex flex-1 bg-white text-black",
					"children": "{{get inputData \"title\"}}"
				}
			}
		]
	},
	"layoutFull": {
		"tw": "p-0 bg-white",
		"style": {
			"padding": 0
		}
	},
	"link": "https://dot.mindreset.tech",
	"border": 0
}

Writing windowData

  • windowData must contain a default layer array;
  • Elements are usually written as { "type": "div", "props": { ... } };
  • props.tw writes Tailwind-like styles, while props.style writes explicit inline styles;
  • div defaults to a flex container; when another display mode is needed, set block, grid, hidden, or another display class in props.tw, or set props.style.display;
  • props.children can be a string, one element object, or an array of elements;
  • Dynamic content can read request data with {{get inputData "user.name" default="-"}};
  • List structures can use $for inside the repeated node's props; $empty sits next to $for and replaces that node when the array is empty;
  • Common element types are div, span, and img;
  • Images may use data URIs or anonymously accessible http(s) image URLs;
  • The outermost container does not need extra padding; when layoutFull is omitted, the device FULL layout keeps its default spacing. Use layoutFull.tw or layoutFull.style when you need to override the FULL layout;
  • The request is limited by template size and complexity to keep rendering stable.

List Structures: $for / $empty

$for expands elements during JSON compilation. It is not a browser JavaScript loop. Put it inside the props of the node to repeat; the repeated unit is that node itself. items is a JSON path read from the current template context; as and index inject local values for the loop body. limit is optional. When omitted, all rows are rendered, and the device layout decides how many fit on screen.

{
	"type": "div",
	"props": {
		"$for": {
			"items": "inputData.tasks",
			"as": "task",
			"index": "index"
		},
		"$empty": {
			"type": "div",
			"props": {
				"children": "No tasks"
			}
		},
		"children": "{{index}}. {{get task \"title\" default=\"\"}}"
	}
}

Conditions And Formatting

Use $ifAny / $then / $else for structural conditions that add, replace, or remove whole elements. $ifAny may be a single JSON path or an array of paths. If any value exists and has content, $then is used; otherwise $else is used.

{
	"$ifAny": ["inputData.icon", "inputData.signature"],
	"$then": {
		"type": "div",
		"props": {
			"children": "{{get inputData \"signature\" default=\"\"}}"
		}
	},
	"$else": {
		"type": "div",
		"props": {
			"children": "No signature"
		}
	}
}

For short text conditions inside a string, use template if / else syntax or compare. Use if to check whether a value has content, and use compare when two values must be compared explicitly:

{{#if (get inputData "title" default="")}}{{get inputData "title"}}{{else}}Untitled{{/if}}
{{#compare inputData.status "===" "done"}}Done{{else}}In progress{{/compare}}

Use formatDate for dates and formatCompactNumber for numbers. For standard number formatting instead of compact K/M output, set the third argument to standard.

{{formatDate inputData.date "yyyy/MM/dd" "Asia/Shanghai"}}
{{formatDate inputData.date "EEE" "Asia/Shanghai"}}
{{formatCompactNumber inputData.count}}
{{formatCompactNumber inputData.count "en-US" "standard" 0}}

Supported Styles And Custom Tailwind Classes

Canvas API supports a device-oriented static rendering style surface. In practice, the styling boundary is: React object-like elements + a static CSS subset, plus Dot.'s custom Tailwind font utilities, breakpoint handling, and image-processing classes.

SyntaxSourceNotes
props.styleDot Canvas static style subsetBest for deterministic pixel values and explicit styles.
props.twTailwind-like syntax + Dot. extensionsBest for quick layout, color, spacing, font classes, and image-processing classes.
layoutFull.tw / layoutFull.styleDot. layout wrapper overrideUse for full-bleed screens, background, and padding overrides.

The props.style support list is aligned with the static CSS support table. Common categories include CSS variables, display, position, color, margin, padding, top/right/bottom/left, width/height, minWidth/minHeight/maxWidth/maxHeight, border*, borderRadius*, Flexbox, gap, fontFamily, fontSize, fontWeight, fontStyle, tabSize, textAlign, textIndent, textTransform, textOverflow, textDecoration, textShadow, letterSpacing, lineHeight, whiteSpace, lineClamp, wordBreak, textWrap, backgroundColor, backgroundImage, backgroundPosition, backgroundSize, backgroundClip, backgroundRepeat, transform, transformOrigin, objectFit, objectPosition, opacity, boxSizing, boxShadow, overflow, filter, clipPath, mask*, and WebkitTextStroke*.

This style list only describes props.style. The font classes, breakpoint processing, and img-* image-processing classes below are Dot. custom Tailwind extensions on top of props.tw.

Important boundaries: Canvas API is not a full browser environment. It does not support <style>, external <link>, or <script>; it does not support 3D transforms, z-index, or calc(); currentColor is only reliable on the color property; advanced typography features and RTL languages are not the current focus. Canvas API also does not support JSX, arbitrary JS expressions, React hooks, browser APIs, external CSS, or custom components.

Common props.tw classes include flex, flex-row, flex-col, flex-1, shrink-0, grow, items-*, justify-*, w-full, h-full, w-[84px], h-[40px], min-w-0, min-h-0, max-h-[200px], gap-*, gap-[5px], p-*, px-[8px], py-[5px], bg-*, text-*, border*, rounded*, overflow-hidden, box-border, box-content, fill-black, and fill-white. If a Tailwind class is uncertain, prefer props.style.

Text supports two font families of class patterns:

TypeSyntaxExample
Regular fonttext-{size}-{font}text-18-chillduansans
Regular font with arbitrary px sizetext-[Npx]-{font}text-[20px]-playfairdisplay
Tailwind font size keytext-{xs/sm/base/lg/xl/2xl...}-{font}text-lg-chillduansans
Pixel fonttext-pixel-{size}[-variant]text-pixel-12-zpix

Common regular font keys: chillduansans, chillksans, chillorganic, chillroundf, chillroundgothic, logoscunboundedsans, maokenyingbikaishuj0.09, playfairdisplay, zihunzhoukesong.

Pixel font classes: text-pixel-8, text-pixel-8-quan, text-pixel-10, text-pixel-12, text-pixel-12-xiaoya, text-pixel-12-zpix, text-pixel-16, text-pixel-16-cusong, text-pixel-16-unifont, text-pixel-16-unifontmono, text-pixel-24.

For text layout, prefer these props.style fields: fontSize, fontWeight, lineHeight, letterSpacing, whiteSpace, wordBreak, lineClamp, textOverflow, and overflow. A multi-line body usually looks like:

{
	"tw": "text-18-chillduansans",
	"style": {
		"lineHeight": "20px",
		"whiteSpace": "pre-wrap",
		"wordBreak": "break-word",
		"overflow": "hidden"
	}
}

Image elements support extra e-ink image-processing classes in img.props.tw:

img-dither-none
img-dither-diffusion
img-dither-ordered

img-kernel-threshold
img-kernel-atkinson
img-kernel-burkes
img-kernel-floyd-steinberg
img-kernel-sierra2
img-kernel-stucki
img-kernel-jarvis-judice-ninke
img-kernel-diffusion-row
img-kernel-diffusion-column
img-kernel-diffusion-2d

img-levels-2
img-levels-3
img-levels-4
img-levels-8
img-levels-16

For image layout, use style.objectFit and style.objectPosition, such as contain / center bottom. Avoid relying on aspect-ratio, CSS Grid, absolute positioning, pseudo classes, media queries, external CSS, scripts, or custom components; these are not part of the stable Canvas API surface.

Response

{
	"message": "Device ABCD1234ABCD Canvas API content switched."
}

Common Error Examples

Unsupported element type:

{
	"windowData": {
		"default": [
			{
				"type": "button",
				"props": {
					"children": "Bad type"
				}
			}
		]
	}
}

Response:

{
	"message": "The canvas element button for device ABCD1234ABCD is not supported (path: windowData.default[0].type). Only div, span, and img are currently supported."
}

Unsupported property:

{
	"windowData": {
		"default": [
			{
				"type": "div",
				"props": {
					"children": [
						{
							"type": "span",
							"props": {
								"onClick": "alert(1)",
								"children": "Unsafe"
							}
						}
					]
				}
			}
		]
	}
}

Response:

{
	"message": "The canvas property onClick for device ABCD1234ABCD is not supported (path: windowData.default[0].props.children[0].props.onClick)."
}

Invalid image source:

{
	"windowData": {
		"default": [
			{
				"type": "div",
				"props": {
					"children": [
						{
							"type": "img",
							"props": {
								"src": "data:image/png;base64,not-a-png"
							}
						}
					]
				}
			}
		]
	}
}

Response:

{
	"message": "The canvas image src for device ABCD1234ABCD is invalid (path: windowData.default[0].props.children[0].props.src). Provide data:image/*;base64,... or an anonymously accessible http(s) image URL."
}

Did this solve your problem?

Join our community

Control Image ContentNew

Previous

AI SkillNew

Use AI Skill to let AI assistants directly control your Dot. devices.

Contents

Quick StartRequirementsPlaygroundRequest BodyWriting windowDataList Structures: $for / $emptyConditions And FormattingSupported Styles And Custom Tailwind ClassesResponseCommon Error Examples