Ballmac UI home

Phone Frame

A modern phone drawn in CSS: titanium band, side buttons, Dynamic Island, status bar and home indicator. Children render as the screen, laid out at a phone resolution and scaled to fit.

Right-to-left: Hardware buttons and bezels sit on fixed physical edges of the device, so the frame keeps its shape; the screen content you place inside follows the page direction.

9:41

Wallet

Acme Card•••• 4821

Balance

$12,480.20

SendRequestTop up

Latest

Corner CaféToday, 8:12−$4.80
From SamYesterday+$120.00
City TransitYesterday−$2.75
Market HallMon−$38.12

Installation

$ pnpm dlx shadcn@latest add @ballmac/phone-frame

Usage

import { PhoneFrame } from "@/components/ballmac/phone-frame"

The full example is in the Code tab above.

Examples

Black, dark screen

9:41
RLRelease team3 members

Today 9:38

Morning! How did the review go?

Approved. Two nits, both fixed.

Is the new build on TestFlight yet?

Uploading now. Crash fix for the share sheet is in.

Nice. I'll run it on the old iPad too.

Build 214 is live 🎉

Delivered

Message

API reference

PropTypeDefault
children

Screen content, laid out below the status bar. Ignored when `src` or `videoSrc` is set.

React.ReactNode—
variant

Finish of the frame. "auto" is natural titanium in light mode and black titanium in dark mode.

"auto" | "natural" | "black""auto"
src

Image shown on the screen, cropped to fill it (status bar and island stay on top).

string—
alt

Alternative text for `src`.

string""
videoSrc

Video shown on the screen: muted, looping, and paused under reduced motion.

string—
poster

Poster image for `videoSrc`.

string—
screenWidth

Width in CSS pixels that the screen content is laid out at (393 matches a 6.1" phone); it is then scaled to fit. Omit to lay content out at the frame's actual size.

number—
statusBar

Show the status bar (time, signal, Wi-Fi, battery).

booleantrue
time

Time shown in the status bar.

string"9:41"
homeIndicator

Show the home indicator bar at the bottom of the screen.

booleantrue
screenClassName

Class names for the screen element (inside the bezel). Use "dark" to give the screen its own theme.

string—

Also accepts the standard attributes of its root element.

Use with AI

Wrap a mobile screen in <PhoneFrame screenWidth={390}>: children render below a status bar at 390 CSS px wide and are scaled to the frame's width. Set the frame width with className (e.g. w-64); height follows the phone's aspect ratio. With the shadcn MCP server set up (guide), ask your agent:

Add the Ballmac UI Phone Frame (@ballmac/phone-frame) to this project with the shadcn MCP, then use it where it fits.

Use it for

  • Showing a mobile app or responsive site on a landing page
  • App Store-style feature sections with live React screens
  • Pairing with laptop-frame to show desktop and mobile together

Not for

  • Desktop apps or websites at desktop width (use laptop-frame or browser-frame)
  • Real device screenshots that already include the bezel

Registry JSON: https://ui.ballmac.com/r/phone-frame.json

Credits

Free to use in personal and commercial projects.