Live widgets, powered by your API

Every change that matters.Right at a glance.

Glance Widgets turns any HTTPS API into a live, beautifully rendered Home Screen widget. Pixel grids, text, curves, images and Liquid Glass — composed from a single JSON response.

API request
1
API request
ways to express it
ways to express it
widget materials, incl. Liquid Glass
6
widget materials, incl. Liquid Glass
servers in between, protecting your privacy
0
servers in between, protecting your privacy
9:41

Showcase

Any use case. Any style.

Every widget below is drawn live from data — whatever your API returns is what your widget shows. Pick one to see the data behind it.

Release watch

Request matrix, replica health and P95 after a deploy.

Large · ambient
The data behind it · JSON
{
  "protocol": 1,
  "pixels": [
    [
      { "empty": true }
    ]
  ],
  "data": {
    "icon": {
      "frame": {
        "left": 0.07,
        "top": 0.065,
        "width": 0.07,
        "height": 0.07
      },
      "zIndex": 2,
      "content": {
        "icon": "ph_rocket",
        "iconCodePoint": 58366,
        "iconFont": "phosphorBold"
      },
      "style": { "color": "#8EC8FB" }
    },
    "service": {
      "frame": { "left": 0.16, "top": 0.06, "width": 0.8, "height": 0.08 },
      "zIndex": 2,
      "content": { "text": "Checkout · v4.12.0" },
      "style": {
        "color": "#FFFFFF",
        "fontWeight": "600",
        "horizontalAlignment": "left",
        "verticalAlignment": "center",
        "fontSizeRatio": 0.05
      }
    },
    "state": {
      "frame": { "left": 0.07, "top": 0.15, "width": 0.86, "height": 0.07 },
      "zIndex": 2,
      "content": { "text": "Deployed 14:20 · watching" },
      "style": {
        "color": "#8EA3C4",
        "fontWeight": "500",
        "horizontalAlignment": "left",
        "verticalAlignment": "top",
        "fontSizeRatio": 0.038
      }
    },
    "requests": {
      "frame": { "left": 0.07, "top": 0.27, "width": 0.86, "height": 0.38 },
      "zIndex": 1,
      "content": {
        "default": { "color": "#FFFFFF", "opacity": 0.06, "cornerRadius": 0.3 },
        "layout": { "gapMode": "near", "cellAspectRatio": 0.9 },
        "pixels": [
          [null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null],
          [null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null, null],
          [
            null,
            null,
            null,
            null,
            null,
            null,
            { "color": "#8EC8FB", "opacity": 0.9500000000000001 },
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            { "color": "#8EC8FB", "opacity": 0.9500000000000001 },
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null
          ],
          [
            null,
            null,
            null,
            null,
            null,
            { "color": "#8EC8FB", "opacity": 0.9 },
            { "color": "#8EC8FB", "opacity": 0.9 },
            { "color": "#8EC8FB", "opacity": 0.9 },
            { "color": "#8EC8FB", "opacity": 0.9 },
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            { "color": "#8EC8FB", "opacity": 0.9 },
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null,
            null
          ],
          "… 6 more"
        ]
      }
    },
    "rule": {
      "frame": { "left": 0.07, "top": 0.7, "width": 0.86, "height": 0.02 },
      "zIndex": 1,
      "content": { "direction": "horizontal" },
      "style": {
        "color": "#FFFFFF",
        "opacity": 0.16,
        "strokeWidth": 1,
        "pattern": "dotted"
      }
    },
    "replicasLabel": {
      "frame": { "left": 0.07, "top": 0.75, "width": 0.28, "height": 0.06 },
      "zIndex": 2,
      "content": { "text": "Replicas" },
      "style": {
        "color": "#8EA3C4",
        "fontWeight": "500",
        "horizontalAlignment": "left",
        "verticalAlignment": "top",
        "fontSizeRatio": 0.034
      }
    },
    "errorsLabel": {
      "frame": { "left": 0.37, "top": 0.75, "width": 0.28, "height": 0.06 },
      "zIndex": 2,
      "content": { "text": "Error rate" },
      "style": {
        "color": "#8EA3C4",
        "fontWeight": "500",
        "horizontalAlignment": "left",
        "verticalAlignment": "top",
        "fontSizeRatio": 0.034
      }
    },
    "p95Label": {
      "frame": { "left": 0.67, "top": 0.75, "width": 0.28, "height": 0.06 },
      "zIndex": 2,
      "content": { "text": "P95" },
      "style": {
        "color": "#8EA3C4",
        "fontWeight": "500",
        "horizontalAlignment": "left",
        "verticalAlignment": "top",
        "fontSizeRatio": 0.034
      }
    },
    "replicas": {
      "frame": { "left": 0.07, "top": 0.82, "width": 0.28, "height": 0.12 },
      "zIndex": 2,
      "content": { "text": "6/6" },
      "style": {
        "color": "#7EDDB5",
        "fontWeight": "700",
        "horizontalAlignment": "left",
        "verticalAlignment": "top",
        "fontSizeRatio": 0.075
      }
    },
    "errors": {
      "frame": { "left": 0.37, "top": 0.82, "width": 0.28, "height": 0.12 },
      "zIndex": 2,
      "content": { "text": "0.02%" },
      "style": {
        "color": "#FFFFFF",
        "fontWeight": "700",
        "horizontalAlignment": "left",
        "verticalAlignment": "top",
        "fontSizeRatio": 0.075
      }
    },
    "p95": {
      "frame": { "left": 0.67, "top": 0.82, "width": 0.28, "height": 0.12 },
      "zIndex": 2,
      "content": { "text": "183 ms" },
      "style": {
        "color": "#FFFFFF",
        "fontWeight": "700",
        "horizontalAlignment": "left",
        "verticalAlignment": "top",
        "fontSizeRatio": 0.075
      }
    }
  },
  "layers": [
    { "id": "remote:icon", "type": "icon", "dataPath": "data.icon" },
    { "id": "remote:service", "type": "text", "dataPath": "data.service" },
    { "id": "remote:state", "type": "text", "dataPath": "data.state" },
    {
      "id": "remote:requests",
      "type": "matrix",
      "dataPath": "data.requests"
    },
    { "id": "remote:rule", "type": "line", "dataPath": "data.rule" },
    {
      "id": "remote:replicasLabel",
      "type": "text",
      "dataPath": "data.replicasLabel"
    },
    {
      "id": "remote:errorsLabel",
      "type": "text",
      "dataPath": "data.errorsLabel"
    },
    { "id": "remote:p95Label", "type": "text", "dataPath": "data.p95Label" },
    { "id": "remote:replicas", "type": "text", "dataPath": "data.replicas" },
    { "id": "remote:errors", "type": "text", "dataPath": "data.errors" },
    { "id": "remote:p95", "type": "text", "dataPath": "data.p95" }
  ]
}

How it works

Return one JSON.We’ll handle the rest.

Glance Widgets validates it, binds your data and draws it natively — then keeps it fresh on the system’s refresh schedule.

01 · RequestHTTPS

Request

The widget calls your HTTPS endpoint with its family, canvas size and aspect ratio — so you can draw for the exact space.

GET https://api.acme.dev/widget
  ?gw_protocol=1
  &gw_platform=ios
  &gw_family=small
  &gw_canvas_width_pt=158.00
  &gw_canvas_height_pt=158.00
  &gw_aspect_ratio=1.0000
  &gw_context=app_preview
02 · Response200 · application/json

Respond

Return a dot matrix plus text, curves, images, icons, lines and shapes — as much or as little as the moment calls for.

{
  "protocol": 1,
  "default": { "color": "#8EC8FB", "opacity": 0.07 },
  "pixels": [[null, null, …], …],
  "batch": [{ "pixel": { "color": "#5F9CF0" },
              "coordinates": [[12, 0], …] }],
  "data": { "api": { "latency": {
    "frame": { "left": 0.09, "top": 0.19, … },
    "content": { "text": "170 ms" }, …
  } } },
  "layers": [{ "id": "remote:latency", "type": "text",
               "dataPath": "data.api.latency" }]
}
03 · On screenLive

Render

The app validates and normalizes the frame, then WidgetKit draws it on the Home Screen, StandBy and beyond.

Capabilities

A small canvas withroom for almost any idea.

Powerful where it counts, controlled where it matters. A flexible pixel grid and a flat layer system carry anything from a status light to a full dashboard.

Little pixels. Big possibilities.

Anything can be drawn in dots. Per-dot color, opacity, corner radius, rotation and halo — from crisp LED boards to soft pixel art.

cornerRadiusrotationhaloopacity

Seven layer types

Text, curve, image, icon, line, shape and local matrix. Flat, z-ordered, positioned in relative frames.

matrix
text
curve
image
icon
line
shape

More ways to look

Liquid Glass, transparent glass, solid, gradient, ambient light and images — widgets that feel right at home.

Liquid Glass
Glass
Solid
Gradient
Ambient
Image

Data binding

Point any layer at an object in your response with a path like data.orders.total — its position, content and style are read from there. No templates, no expressions to debug.

"dataPath": "data.orders.total"112

You draw it. It just shows it.

Skip Glance Widgets’ content syntax entirely. Render each live frame as an image on your own server — with any language, chart library or headless browser — and simply return it, then set the material to Image in the app. Glance Widgets becomes a window for your content: the lowest learning curve, the most freedom.

Nothing to learnAny language or toolURL or Base64
Learn about server images

System-scheduled refresh

Widgets re-fetch on the WidgetKit timeline. Nothing to host, nothing to push.

Private by design

Requests go straight from the device to your server, optionally HMAC-signed. We never relay, proxy or see your data.

Every size. StandBy too.

Small, medium and large families, each told its exact canvas in points.

Make a change. See it happen.

Drag, resize and style local layers in the visual editor, previewed at true Home Screen size.

For developers

Let your server do the drawing.

If you can return JSON, you can ship a widget. Any language, any stack, any host — a cron job, a serverless function or your production API.

  • Plain HTTPS GET with canvas context in the query
  • Strict, documented protocol with clear limits
  • Skip the protocol: return a whole image rendered on your server
  • Optional HMAC-SHA256 request signing
  • A browser playground that renders like the app
server.ts
import express from 'express'

const app = express()

app.get('/widget', async (req, res) => {
  // The widget tells you exactly how much space it has.
  const family = req.query.gw_family          // small | medium | large
  const orders = await db.orders.today()

  res.json({
    protocol: 1,
    default: { color: '#8EC8FB', opacity: 0.08, cornerRadius: 0.5 },
    pixels: Array.from({ length: 8 }, () => Array(20).fill(null)),
    data: {
      // Where the layer sits, what it shows, how it looks.
      total: {
        frame: { left: 0.08, top: 0.3, width: 0.84, height: 0.4 },
        content: { text: orders.count },
        style: { fontSizeRatio: 0.24, fontWeight: '700', horizontalAlignment: 'left' },
      },
    },
    // Declare a layer and point it at its object.
    layers: [{ id: 'remote:total', type: 'text', dataPath: 'data.total' }],
  })
})

app.listen(3000)
{ }SDKs for popular languages ship pixel templates, dot fonts and charts — so you describe what you want, not 2D arrays.

Privacy

Your data. In your hands.

Core features run on your device. Signed requests go straight to your server — Glance Widgets never relays, proxies or stores what you show.

Pro

Every plan. Every Pro feature.

Every plan comes with all Pro features. Pick the option that works for you — new platforms and features we ship later are yours at no extra cost.

Early-bird pricingPrice roadmap
Get Glance Widgets

Included in every plan

  • Unlimited API-driven widgets
  • All seven layer types
  • Liquid Glass, glass, gradient, ambient & image materials
  • Signed requests with your own secret
  • Small, medium, large and StandBy
  • Encrypted backups
  • New platforms & features, free as they ship

Prices shown are US prices and for reference only. The price you see in the app at checkout is final. Prices vary by country or region due to exchange rates, local pricing and other factors.

Every subscription plan starts with a 7-day free trial, then renews automatically on the plan you chose. You can cancel in your Apple Account settings.

There’s a free version, too.

Get the essentials for free. Upgrade to Pro when you want more on your Home Screen.

On Free, you can still edit and preview every Pro feature.

FeatureFreePro
Widgets you can create5 Unlimited
Widgets on Home Screen1 Unlimited
Layers per widget8 Free limit lifted
Card stylesBasic All styles
StandBy Included
Backup & migration Included

What’s next

What matters to you.On more screens.

Dynamic Island

Coming soon

Live status where your eyes already are.

Apple Watch

Coming soon

Your frames on your wrist.

iPadOS & macOS

Coming soon

Bigger canvases, same protocol.

Web editor

Coming soon

Design and preview widgets right here.

Cross-device sync

Coming soon

Your widgets on every device, via your online account and iCloud.

Community templates

Coming soon

Discover. Make. Share.

Macros & Shortcuts

Coming soon

Assign actions to areas of a widget: tap to open a webpage or run a Shortcut you’ve set up.

Price roadmap

Early-bird pricing

Glance Widgets launches at an early-bird price. As more features land, the price will rise in stages.

Back to plans
  1. 01

    Early bird

    Now

    Launch pricing, until Stage 2 begins

  2. 02

    Stage 2

    After cross-device sync, Dynamic Island, Apple Watch, the web editor and more roll out

  3. 03

    Full price

    After iPadOS, macOS, the template library, Macros & Shortcuts and more are complete

  • Keep the price you joined at until one year after full pricing takes effect
  • Every price increase is announced at least 2 weeks in advance
  • Buy Lifetime now and lock in the lower early-bird price.

If you cancel, switch plans or let your subscription lapse, you lose the locked-in price. Any period you’ve already paid for is always honored.

FAQ

Questions, answered.

To show live data you need an HTTPS endpoint that returns JSON — anything from a serverless function to a script. The visual editor also lets you compose static text, images, shapes and pixels without any API.

Widgets request a new frame on the WidgetKit timeline, roughly every 15 minutes. iOS decides the exact moment based on battery, usage and system budget, so design frames that stay meaningful between updates.

No. The device calls your endpoint directly. You can add a secret so every request carries an HMAC-SHA256 signature your server can verify.

Dot matrices, text, curves, images, icons, lines and shapes all serve the same purpose — expressing your content — and you can combine as many as you need, each bound to your data with a simple path. The card they sit on has its own style: Liquid Glass, glass, solid, gradient, ambient light or an image.

iPhone Home Screen widgets in small, medium and large sizes, plus StandBy. iPadOS, Apple Watch, Dynamic Island and more are on the roadmap, and when they ship, they’re included in your plan at no extra cost.

Yes. We provide SDKs for nine languages: TypeScript, Python, Go, Java, C#, PHP, Ruby, Lua and C++. They help you build protocol-compliant API responses. You can also skip the SDK, implement your own API and construct the response data yourself.

Your screen. Your way.

Keep what matters in view — starting with your next API response.