# Simmer Mobile App UI Kit

> A phone app component library on one token file: tab bar, collapsing large titles, grouped lists with swipe actions, sheets that drag between detents, wheel pickers, timers and nutrition rings, plus six working screens of a recipe app, light and dark.

Canonical: https://gsapvault.com/ui-elements/simmer-mobile-app-ui-kit
Live demo: https://gsapvault.com/demos/simmer-mobile-app-ui-kit/index.html

| Property | Value |
|----------|-------|
| Type | ui-kit |
| Tier | paid |
| Price | £25 |
| Difficulty | advanced |
| Plugins | Flip, Draggable, InertiaPlugin |
| Techniques | token-theming, theme-switch, touch-gestures, touch-drag, drag, snap, flip-layout, keyboard-navigation, focus-management, dialog-animation, count-up, countdown, svg-draw, stagger, state-transition, micro-interaction, tabs, carousel, spring-physics, view-transitions |
| Uses Lenis | No |

## Overview

Simmer is a component library for a phone app, not a demo of one screen. The page you see is the library itself: an index down the left, a search that filters it, and sixty components shown live at product density inside a 390px column, grouped into foundations, controls, inputs, navigation, data display, feedback and overlays, sections, and six screens composed from the parts above.

The register is the rhythm a phone user already knows: a grouped grey ground with white cells, hairline separators inset to the text edge, 44px rows and hit targets, a tab bar, a large title that collapses into the bar as you scroll, sheets that rise from the bottom edge, and one warm accent that means primary or selected. Photographs carry the rest of the colour. One typeface carries hierarchy through weight and size, and the dark theme is the same design at a second set of values.

Every component reads one token file, so cards, lists, sheets, pickers and timers agree about surface, ink, line, radius, spacing and motion. Each ships in its own folder with its markup, its stylesheet and its script, so you can take one part or link the two bundled files and take everything. Overlays share one Escape, one focus trap and one scroll lock; motion is short, springy phone motion, and every animated part has a reduced-motion state.

The six screens are not screenshots. Home, recipe, cook mode, shopping, settings and onboarding each open as a full page you can click around: the tab bar navigates between them, the servings stepper rescales the ingredients, the shopping list checks items off and moves them down, the timer counts, the bottom sheet drags. At desktop widths each screen sits inside a phone-sized frame on the page; on a real phone it fills the viewport edge to edge. Every screen is composed from the components with include directives and a short glue script, so each one is also the worked example of how the parts fit together.

## Features

- Sixty components in eight families, each in its own folder with markup, styles and script
- A searchable catalogue page with an index rail, family groups and a theme toggle
- One token file driving light and dark themes; no component holds a colour of its own
- Navigation bar with a large title that collapses as the content scrolls, a five-tab bar with badges, and a page stack with swipe back
- Bottom sheet with half and full detents, drag to dismiss and the content behind scaling back; action sheet, alert, pull-down menu and long-press context menu on one overlay layer
- Grouped lists with swipe actions, a reorder handle and check-off rows that move to the bottom
- Wheel pickers for quantities and timer durations, a calendar sheet, a search bar whose Cancel slides in, an add-recipe form with a sticky Save
- Timer ring, nutrition rings, a servings stepper that rescales an ingredient list, a step list with a one-step-at-a-time cook mode, a week chart
- Sections ready to place: photo recipe header, collection shelves, shopping list by aisle, week planner, settings groups, profile header, onboarding pager, plan picker, permission prompt
- Twenty baked recipe photographs at card and thumbnail sizes, licensed for redistribution inside your product
- Keyboard and ARIA contracts on every control, with 44px hit targets and live announcements for state changes
- Reduced-motion end states throughout; nothing animates while off screen
- Six screens that open as working pages and navigate between each other, framed as a phone at desktop widths and full-bleed on a phone

## Use Cases

- A progressive web app or hybrid app (Capacitor, Cordova, a WebView) that should feel like a native phone app
- A mobile-first product where the phone layout is the product, not a breakpoint
- A recipe, fitness, travel, habit or learning app that starts from finished lists, sheets, timers and a tab bar
- A phone prototype or demo that has to survive a real thumb, not just a screenshot

## Questions about this component kit

### Can I take one component without the rest?

Yes. Each component lives in its own folder with its markup, its stylesheet and, where it needs one, its script, so a bottom sheet, a wheel picker or a swipe row travels on its own into a screen you already have. Link tokens.css, base.css and base.js, then that folder's files, and paste the fragment. To use everything, link the two bundled files instead. The catalogue page, its phone frame and its rail are demo furniture; nothing in a product needs them.

### Is this for iOS, Android or the web?

It is HTML, CSS and JavaScript, so it runs anywhere a web view does: a progressive web app, a Capacitor or Cordova app, a WebView inside a native shell, or a mobile-first website. The conventions are the ones phone users know from the platform (a tab bar, a collapsing large title, grouped lists, sheets), drawn in our own type, icons and accent rather than copying any vendor's system look.

### What kind of app does this suit, and how do I rebrand it?

Anything built from lists, cards, a detail page, a step-by-step mode and settings: a recipe app is the worked example, but a workout app, a travel guide, a habit tracker or a course app uses the same parts with the words changed. Rebranding is editing tokens.css: change the accent, the ground, the ink ramp or the face and every component follows, in both themes, with no component-level overrides. The photographs are yours to replace in assets/img.

### Is there a backend, and do the components hold state?

No backend. Every recipe, ingredient, plan and setting is sample content in the markup, and the interactions change the page rather than a database: checking an item moves it down the list, the stepper rescales the quantities, the timer counts from the moment you start it. Wiring it to your data means rendering the same markup from whatever you already have; the scripts initialise any instance they find.

### What happens at desktop widths?

The catalogue is a desktop page with the specimens laid out in a phone's width. The six screens open inside a phone-sized frame centred on the page above 520px, and fill the viewport edge to edge below it, so the same file is a demo on a laptop and the app on a phone.

### Do the gestures really work on a phone?

Yes. The bottom sheet drags between its detents and dismisses when thrown down, list rows swipe to reveal their actions and swipe fully to commit, the wheel picker flicks and settles on a value, the page stack swipes back from the left edge, and pull to refresh pulls. Each one gives the vertical axis back to the list so the page still scrolls, and every gesture has a keyboard route listed in the README.

## Vibe-Code Ready Setup

This component kit includes `START-HERE-AI.md`, a product-specific copy-paste setup prompt for Cursor, Claude Code, ChatGPT, GitHub Copilot, Windsurf, and other coding assistants. It tells the assistant to inspect the existing stack, integrate the supplied files, preserve the design, scope selectors, retain accessibility and responsive behaviour, add framework-appropriate GSAP cleanup, and report what it tested.

[How AI-assisted setup works](https://gsapvault.com/vibe-coding)

## How It Works

### The library is the page

The catalogue is generated from the component folders, so what you browse is exactly what you download. The rail lists every component by family, the search filters both the rail and the specimens, and each specimen is the component in every state a buyer would check, laid out in a phone's width with product copy rather than placeholder text.

### One token file, two themes

Surfaces, ink, lines, accent, status colours, chart series, radii, spacing, control heights, bar heights, safe areas, durations and eases are role-named custom properties in one file. The dark theme re-values the same names, so a component never branches on the theme and a rebrand is one edit.

### Built for a thumb

Every row, tab and icon button is 44px to hit. The sheet, the swipe actions, the wheel picker and the page stack are dragged with inertia and settle to their nearest resting point, and each one hands the vertical axis back to the list so a phone still scrolls. Everything that opens over a screen goes through a shared layer that owns Escape, the focus trap, focus return, scroll lock and stacking.

## Documentation

How this component kit works and how it goes into a page. The reference you use once you own the files (worked examples, events, the programmatic API, the class list) ships with the download.

### Quick Start

There are two ways in. Both need GSAP (core; Flip for the lists that reorder, Draggable and InertiaPlugin for the sheet, the swipe rows, the wheel picker and the page stack).

**Everything, two files.** In `<head>`:

_Code snippet omitted: it ships with the download._

At the top of `<body>`, paste the contents of `assets/icons.svg` once (it is an SVG sprite; the icons reference it with `<use href="#i-name">`). Before `</body>`:

_Code snippet omitted: it ships with the download._

Then copy any component's fragment from `components/<name>/specimen.html` into your page.

**One component.** Link `assets/tokens.css`, `assets/base.css` and the component's `components/<name>/style.css`; load GSAP, `assets/base.js` and the component's `components/<name>/script.js`; paste its `specimen.html`. `tokens.css`, `base.css` and `base.js` are required by everything; a component's own files are all it adds.

The scripts find every instance of their component by its `data-kit` attribute and initialise each once, so the same fragment can appear as many times as you need. If you render the markup from a framework, call the init after mount (each script is an IIFE that runs on `DOMContentLoaded` or immediately if the DOM is already parsed; reloading it, or dispatching a synthetic `DOMContentLoaded`, initialises anything new).

### A phone app in a web page

The kit lays everything out in a 390px column. A handset component is built on the `.screen` scaffold from `base.css`: the root is the column, `.screen__status` reserves the status region, `.screen__bar` holds the navigation bar, `.screen__scroll` is the only thing that scrolls, `.screen__dock` holds a tab bar or toolbar and `.screen__home` the home-indicator inset. Overlays that belong to a screen (a sheet, a menu, an alert) are `.layer` children of that column and lock the column's scroll region rather than the document.

On a real phone, make the app's root a `.screen` that fills the viewport (`height: 100svh`) and the components take the width. In the shipped screen pages the same root sits inside a phone-sized frame above 520px wide and fills the viewport below it; that frame is a few lines of CSS in each page's `<head>`, and you can delete it.

### What's Included

- `index.html`: the catalogue, every component assembled. Generated from `components/` and `kit.json`; the rail and search are demo furniture
- `home.html`, `recipe.html`, `cook.html`, `shopping.html`, `settings.html`, `onboarding.html`: the six screens as pages
- `components/<name>/`: one folder per component: `specimen.html` (the fragment), `style.css`, `script.js`
- `assets/tokens.css`: **the design system**: every surface, ink, line, accent, status and series colour, the type ramp, spacing, radii, control and bar heights, safe areas, durations and eases, in two themes
- `assets/base.css`: reset, type ramp, the shared primitives (`.btn`, `.input`, `.badge`, `.avatar`, `.icon`, `.group`, `.menu`, `.screen`, `.layer`, `.hscroll`) and layout utilities
- `assets/base.js`: `window.Kit`, the shared runtime: the overlay layer stack, positioning, focus helpers, motion tokens, the theme switch, long press, a live region
- `assets/icons.svg`: the icon sprite
- `assets/img/`: twenty recipe photographs as baked WebP derivatives, at 640x480 and 240x240
- `assets/style.css` and `assets/script.js`: the two bundles, generated from the files above
- `assets/catalogue.css` and `assets/catalogue.js`: the catalogue page chrome only; not needed in a product

### The six screens

Each screen has two lives. In the catalogue it is a specimen in the phone stage, so you can see the parts compose. As a page it is the app: the tab bar and the back buttons navigate between the screens, and a cross-document view transition holds the bars still while the content changes.

- **Home** is the entry: tonight's plan, the weeknight shelf, recently cooked, a large title that collapses into the bar as you scroll, the tab bar.
- **Recipe** is the worked example: the photo header, nutrition rings that draw on enter, a servings stepper that rescales every ingredient, the method with inline timers, and a Start cooking toolbar that leads to cook mode.
- **Cook mode** shows one step at a time with the timer, progress along the top, next and back by button or swipe, and the finished alert.
- **Shopping** is the list by aisle: check an item and it strikes through and moves down, swipe to delete with undo, an add field, pull to refresh.
- **Settings** carries the profile header, grouped settings with toggles and value rows, the plan picker and the sign-out alert.
- **Onboarding** is the pager, a diet chips step, the notifications prompt, and into the app.

### Components

<!-- kit:components -->

#### Foundations

The tokens every screen reads: two themes, one type ramp, the handset column and its safe areas.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| Colour roles | `components/colors/` |  |  |
| Type ramp | `components/typography/` |  |  |
| Icons | `components/icons/` |  |  |
| Layout | `components/layout/` |  |  |

#### Controls

Buttons and the small things a thumb rests on, every one 44px to hit.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| Button | `components/button/` | `[data-kit="button"] .btn` | Enter, Space |
| Icon button | `components/icon-button/` | `[data-kit="icon-button"] .btn--icon` | Enter, Space |
| Switch | `components/switch/` | `.k-switch` | Space |
| Checkbox and radio | `components/checkbox-radio/` | `.k-checkbox-radio__row` | Space; arrows in a radio group |
| Segmented control | `components/segmented-control/` | `.k-segmented-control` | Arrows, Home, End |
| Stepper | `components/stepper/` | `.k-stepper` | Arrows, Home, End |
| Slider | `components/slider/` | `.k-slider` | Arrows, Home, End, PgUp, PgDn |
| Chips | `components/chip/` | `.k-chip` | Enter, Space; arrows move along the row |
| Rating | `components/rating/` | `.k-rating` | Arrows, Home, End |

#### Inputs

Grouped form fields, search, a wheel picker and a calendar, in the shapes a phone keyboard expects.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| Text field | `components/text-field/` | `.k-text-field` | Native; Escape clears |
| Search bar | `components/search-bar/` | `.k-search-bar` | Escape cancels; arrows through recents |
| Wheel picker | `components/picker/` | `.k-picker` | Arrows, PgUp, PgDn, Home, End |
| Date picker | `components/date-picker/` | `.k-date-picker` | Arrows move days, PgUp and PgDn months, Enter picks, Escape |
| Form layout | `components/form-layout/` | `.k-form-layout` | Native; Enter adds an ingredient row |
| Photo picker | `components/photo-picker/` | `.k-photo-picker` | Enter opens the picker; Delete removes the focused tile |

#### Navigation

The shell a phone app lives in: bars, tabs, a page stack with swipe back, and the menus that hang off them.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| App shell | `components/app-shell/` | `.k-app-shell` | Tab order: nav bar, content, tab bar |
| Navigation bar | `components/nav-bar/` | `.k-nav-bar` | Native |
| Tab bar | `components/tab-bar/` | `.k-tab-bar` | Arrows between tabs, Enter or Space selects |
| Page stack | `components/page-stack/` | `.k-page-stack` | Escape pops; Backspace on the back button |
| Tabs | `components/tabs/` | `.k-tabs` | Arrows, Home, End |
| Page indicator | `components/page-indicator/` | `.k-page-indicator` | Arrows page |
| Context menu | `components/context-menu/` | `.k-context-menu` | Shift+F10 or the menu key opens; arrows; Escape |
| Toolbar | `components/toolbar/` | `.k-toolbar` | Native |

#### Data display

Recipes as cards and rows, the numbers a cook watches, and the lists a cook works through.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| Recipe card | `components/recipe-card/` | `.k-recipe-card` | Enter opens; the save button is its own control |
| List | `components/list/` | `.k-list` | Arrows move focus; the actions also appear on focus |
| Carousel | `components/carousel/` | `.k-carousel` | Arrows page |
| Nutrition rings | `components/nutrition-ring/` | `.k-nutrition-ring` | None |
| Timer | `components/timer/` | `.k-timer` | Space starts and pauses; Escape resets |
| Step list | `components/step-list/` | `.k-step-list` | Arrows move; Space completes; Enter starts a timer |
| Ingredient list | `components/ingredient-list/` | `.k-ingredient-list` | Space checks; the stepper is a control |
| Avatar | `components/avatar/` | `.avatar` | None |
| Badges | `components/badge/` | `.badge` | None |
| Progress | `components/progress/` | `.k-progress` | None |
| Bar chart | `components/bar-chart/` | `.k-bar-chart` | Arrows move between bars |

#### Feedback and overlays

Everything that rises over a screen shares one layer: Escape, focus, scroll lock and stacking are one implementation.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| Toast | `components/toast/` | `.k-toast` | Escape dismisses the newest |
| Alert | `components/alert/` | `.k-alert` | Escape, focus trap, return |
| Action sheet | `components/action-sheet/` | `.k-action-sheet` | Escape, arrows, focus trap, return |
| Bottom sheet | `components/bottom-sheet/` | `.k-bottom-sheet` | Escape; the grabber is a button that cycles detents |
| Menu | `components/menu/` | `.k-menu` | Arrows, Enter, Escape, type-ahead |
| Empty state | `components/empty-state/` | `.k-empty-state` | Native |
| Skeleton | `components/skeleton/` | `.k-skeleton` | None |
| Pull to refresh | `components/pull-to-refresh/` | `.k-pull-to-refresh` | A Refresh button for the keyboard |
| Banner | `components/banner/` | `.k-banner` | Native |

#### Sections

The assembled parts of a recipe app, ready to place: heroes, shelves, the shopping list, the week, settings.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| Recipe header | `components/recipe-header/` | `.k-recipe-header` | Native |
| Collection shelf | `components/collection-shelf/` | `.k-collection-shelf` | Native |
| Shopping list | `components/shopping-list/` | `.k-shopping-list` | Space checks; Enter adds |
| Meal plan | `components/meal-plan/` | `.k-meal-plan` | Arrows across days |
| Settings group | `components/settings-group/` | `.k-settings-group` | Native |
| Profile header | `components/profile-header/` | `.k-profile-header` | Native |
| Onboarding pager | `components/onboarding-pager/` | `.k-onboarding-pager` | Arrows page; Enter continues |
| Plan picker | `components/plan-picker/` | `.k-plan-picker` | Arrows between plans |
| Permission prompt | `components/permission-prompt/` | `.k-permission-prompt` | Native |

#### Screens

Six pages composed from the parts above, verbatim. Each opens full screen and navigates to the others.

| Component | Folder | Root | Keyboard |
|---|---|---|---|
| Home | `components/home-screen/` and `home.html` | `.k-home-screen` |  |
| Recipe | `components/recipe-screen/` and `recipe.html` | `.k-recipe-screen` |  |
| Cook mode | `components/cook-screen/` and `cook.html` | `.k-cook-screen` |  |
| Shopping | `components/shopping-screen/` and `shopping.html` | `.k-shopping-screen` |  |
| Settings | `components/settings-screen/` and `settings.html` | `.k-settings-screen` |  |
| Onboarding | `components/onboarding-screen/` and `onboarding.html` | `.k-onboarding-screen` |  |

<!-- /kit:components -->

### Themes

`<html data-theme="light">` or `dark`. The toggle in the catalogue rail calls `Kit.theme.set(name)`, remembers the choice in `localStorage`, and dispatches `kit:theme` so a chart or a ring can re-read a colour. Light is the default; every foreground and background pair in both themes clears 4.5:1.

### Motion and reduced motion

Durations and eases are tokens (`--dur-fast` 150ms, `--dur-base` 260ms, `--dur-slow` 400ms; a soft ease-out for lands, a short overshoot for a tab pop or a toggle knob) read by `Kit.dur()` and `Kit.ease()`. Under `prefers-reduced-motion` every duration reads as zero and continuous motion (shimmer, an indeterminate bar, the timer's ring) shows its end state. Nothing runs while it is off screen: rings draw and counters count when they enter, and stop when they leave.

### Gestures and the keyboard

Every gesture has a keyboard route, listed per component in the table above. The rules the touch pieces follow, in case you extend them: a vertical sheet takes the drag; a horizontal swipe row hands the vertical axis back to the list; swipe back starts only from the left edge; a long press is 500ms and cancels on 8px of movement; pull to refresh only begins with the list at the top. Every hit target is 44px in both directions.

### Photographs

The twenty recipe photographs are Pexels photographs, cropped and re-encoded as WebP and shipped inside `assets/img/`. The Pexels licence permits use, modification and redistribution without attribution; the originals are credited below anyway. Replace them by dropping your own files over the same names, or edit `assets/img-manifest.json` and re-run the bake script in the repository this kit was built from.

Sources (Pexels photo ids): ramen 7490494, shakshuka 29177374, chicken 10821330, aubergine 34492423, burrata 22882531, babka 6150700, carbonara 29039082, tacos 33614224, pancakes 4790406, curry 27287005, soup 17402671, pizza 18437684, smoothie 7937002, salmon 8862746, banana 9928323, risotto 14537701, toast 8335331, cake 19791251, dumplings 7364113, granola 6823360.

### What is demo-only

`assets/catalogue.css`, `assets/catalogue.js`, `kit.json` and the rail, search and stage markup in `index.html`. The phone frame CSS in each screen page's `<head>`. Everything else is product.

### Requirements

GSAP 3.12+ with Flip, Draggable and InertiaPlugin. No other dependency. Built against GSAP 3.15.0.

## What You Get

- `index.html`: working demo page
- `assets/script.js`: commented, readable source
- `assets/style.css`: effect styles
- `README.md`: full documentation with examples and framework integration notes
- `START-HERE-AI.md`: product-specific copy-paste prompt for AI-assisted setup
- `LICENSE.txt`: standard license terms
- Lifetime updates: re-download anytime from your library

## Get the Code

This is a premium component kit. The standard license costs £25 one-time and covers unlimited personal and commercial projects with no attribution required. The only restrictions: no redistribution of the code itself and no competing effect libraries.

- [Buy Simmer Mobile App UI Kit](https://gsapvault.com/ui-elements/simmer-mobile-app-ui-kit)
- [The Vault (£99 one-time, best value): every current and future effect, template and UI element](https://gsapvault.com/effects)

---

From [GSAP Vault](https://gsapvault.com): production-ready GSAP animation effects. Full catalog for agents: https://gsapvault.com/llms-full.txt
