MeDo

Flip It and It's Done.

A switch is the only control that keeps its promise by having no ceremony at all: flip it and the change happens, instantly, with no save button waiting at the bottom of the page. Describe what you are toggling and MeDo generates the switch — proper role="switch" semantics, keyboard support, a 44px touch target, and a pending state for the moment the request is still in flight — in React + Tailwind.

Switch
Switch

The Save Button Is the Bug

Every control on a form makes an implicit promise about when change happens: the input waits for submit, the checkbox waits for submit, and the switch commits now. Break that contract in either direction and users stop trusting the interface — a switch that only takes effect after clicking Save reads as broken ("I already turned it on"), and a settings page of instant switches with a stray Save button trains people to doubt whether anything happened at all. That is why the switch is the rare component whose design review is mostly a contract review: what fires the change, what happens while the request runs, what un-happens when it fails. Get those three answers right and a settings page needs no form, no submit handler, no unsaved-changes warning — the page is always saved, because every action already saved itself. The cost of getting it wrong is not cosmetic either: a checkbox wearing switch clothing lands in screen readers as "checkbox, not checked", and users announce expectations the component will not meet. Generate the real thing.

6 plantillas

Plantillas de Switch que puedes generar

Cada plantilla es un prompt real, no una captura de pantalla. Cópialo en cualquier editor de IA o ejecútalo en MeDo y obtén código React + Tailwind.

BasicSettings Row

Labeled Switch Rows With Helper Text

The workhorse of every account page: label and explanation on the left, switch on the right, the entire row clickable. No form, no submit — each row commits on flip.

Create a settings section titled Preferences with four switch rows. Each row is a button carrying role="switch" and aria-checked, spanning full width: title in 15px medium, one-line helper text in 14px zinc-500 below it, and the switch graphic on the right. Track 40x24px rounded-full — zinc-200 off, indigo-600 on — with a 20px white knob translating over 150ms ease-out, plus a visible focus-visible ring. Make the whole row the hit area with minimum 44px height and 12px vertical padding, and hover-tint the row subtly. State is optimistic: flip updates immediately, then a PATCH fires per setting; while pending show a 12px spinner centered in the track and disable only that row. On failure, revert that switch, flash the track red for 600ms, and raise a toast saying the setting was not saved. Each row is an independent list item under one h2.

Prueba en MeDo
OptimisticInstant Commit

Switch With Pending, Rollback and Undo

The full contract of instant commitment handled explicitly: pending spinner, visible rollback on failure, and a revert window in the toast for changes people regret immediately.

Build a switch that manages one server-backed boolean through its entire lifecycle. On flip: render the new state immediately, start the request, and show a compact inline spinner replacing the knob. On success: swap to the solid state and pop a toast with the result plus a Revert button that stays for five seconds and flips the switch back through the same request path. On failure: revert to the prior state, flash the track rose for 600ms, and raise an error toast naming the setting that failed. The component owns no global lock — several switches can be pending simultaneously — and it debounces rapid double-flips by aborting the in-flight request before starting the next one. Expose onOptimisticChange and onSettled callbacks, and keep aria-checked on the button reflecting the last known server-confirmed value, with aria-busy while pending.

Prueba en MeDo
AdminFeature Flags

Flag Panel With Confirmation for Risky Flags

One panel, two risk classes: safe flags flip freely, expensive or user-facing ones confirm inline. The distinction itself is the feature.

Create a feature-flags panel for an admin: a list of flags, each with a name in mono, a description, an environment pill, and a switch. Flags carry a risk property — safe flags commit on flip with a pending spinner; risky flags flip to an armed state showing an inline confirmation strip inside the row ("This enables paid checkout for all users") with Confirm and Cancel buttons, and nothing is sent until Confirm. Every settled change appends a line to an audit strip at the bottom: flag, actor, previous to new value, timestamp. Disabled flags — overruled by config — show a locked switch with an explanatory tooltip instead of a dead control. Keep per-row loading isolated, and make the list keyboard-navigable with the confirmation strip focus-trapped inside its row.

Prueba en MeDo
MobileMobile Sheet

Bottom Sheet of iOS-Style Switches

Full-row hit areas, green-on tracks, zero save ceremony — a settings sheet that behaves like the native one users already trust.

Create a mobile settings bottom sheet with five iOS-style switches: dark mode, sounds, haptics, auto-play, data saver. Style tracks 51x31px — light grey off, emerald-500 on — with a spring-like knob transition of 200ms. Each setting is a full-width 56px row inside the sheet, entirely tappable, with a 16px label and the switch at the trailing edge; hit areas must never be smaller than the row. The sheet handles its own state locally with no network, and a footer link "More settings" navigates out. Dismissing the sheet by drag or backdrop tap preserves all toggled state, and a dark-mode switch flips the sheet's own theme immediately as a live demonstration. Add swipe-to-dismiss with velocity threshold, a grabber handle, and proper focus handling so keyboard users can reach every row.

Prueba en MeDo
NestedDependent Toggles

Master Switch With Preserved Sub-Switches

Master off dims and disables the children without erasing their values — the correct behavior, and the one most implementations get wrong by unmounting.

Build a dependent settings group: a master switch "Email notifications" with two indented sub-switches, "Product updates" and "Weekly digest", rendered 24px deeper with a subtle left guide line. When the master is off, sub-rows become disabled at 50% opacity with a helper line "Turn on email notifications to change these" — but their values stay in state untouched, so re-enabling the master restores exactly what was chosen before. The master switch commits on flip like any other; sub-switches are individually server-backed. Keep disabled rows excluded from the tab order but visible to screen readers with aria-disabled and the explaining helper text, rather than hidden. Show a tiny count on the master row like "2 sub-settings" so the dependency is discoverable before flipping.

Prueba en MeDo
EphemeralView Options

Dashboard Toggles With No Persistence

Some switches are not settings at all — they shape the current view and live in component state. The fastest switch to build and the easiest to over-engineer.

Create a dashboard toolbar with three view switches: compact rows, show grid lines, auto-refresh every 30s. These are ephemeral: pure component state, no API calls, no toasts, effect on the current page only — though "auto-refresh" additionally shows a live countdown label next to it while active. Switches render at 36x20px, tighter than settings-page tracks since they sit in a toolbar, with zinc-900 tracks when on for contrast against dashboard chrome. Each toggle immediately affects the table below: compact reduces row padding, grid lines add column borders, auto-refresh triggers a refetch interval with a spinner in the toolbar. Persist nothing on the server but optionally mirror to localStorage so a refresh keeps the view. Label the group "View" and keep the switches under 200ms apart in effect — the whole point is immediacy.

Prueba en MeDo

Cómo personalizar tu Switch

Use role="switch", not a styled checkbox

Assistive tech announces a switch as "on or off, toggle-able", which matches what users intend. Ask for role="switch" with aria-checked bound to state on a real button element — a visually restyled checkbox reports the wrong control type and the wrong interaction model.

Show what happens while the request runs

Instant commitment still takes network time, and pretending otherwise produces double-flips. A brief pending state — spinner in the track, that one switch disabled — tells the user the flip registered and is being honored. On failure, revert the switch and say so in a toast; silent rollback is how mistrust in settings pages starts.

Never pair switches with a Save button

Pick one contract per surface. If the page has a Save button, use checkboxes or inputs and submit together; if the values commit on change, delete the button entirely. The half-and-half page — instant switches plus Save — leaves users unable to tell which model applies.

Make the touch target bigger than the track

The track is often 40x24px, which is half the 44px minimum for comfortable touch. Stretch the clickable area to the whole row or an invisible padded hit area around the track — on a phone, the difference between tapping the switch and tapping near it is whether the setting changes at all.

Quién usa el componente Switch

Account settings page

Notification, privacy and appearance preferences as labeled switch rows that patch the server on flip. No save button, an explicit pending state, and dependent sub-options that disable under a master toggle without losing their values.

Feature flags panel

Internal admin toggling features per environment. Each switch is a deploy-adjacent action, so it confirms for risky flags, logs who flipped what, and shows the current value bolded while a change is pending.

Mobile app-style settings sheet

A bottom sheet of iOS-style switches — green when on — for dark mode, sounds, haptics. Full-row hit areas and immediate effect, because the sheet exists precisely to avoid a save-then-dismiss flow.

Dashboard view options

Show grid lines, compact mode, auto-refresh — toggles that change the current view with zero persistence ceremony, stored in local state or a preference API depending on whether they should survive the next login.

Patrones de Switch para distintos sitios web

El mismo componente switch, adaptado al tipo de sitio donde se publica.

01 / 05

SaaS Account Settings

Notifications, privacy, appearance — each a labeled switch row that commits on flip with per-row pending and rollback. The page needs no form state at all, which is the quiet argument for building it entirely out of switches.

Estilos y variantes de Switch

Elige la variante que encaje con el resto de la página y genérala.

01 / 05

Classic Track-and-Knob Switch

Rounded track, circular knob, color change on state. The universal shape — users do not need to learn it, which is the entire reason to keep it recognizable even when restyling the colors.

Switch en React, Next.js, Vue y Svelte

React, Next.js, Vue 3, SvelteKit, Astro o HTML puro: el mismo switch, seis formas de integrarlo.

01 / 03

React Switch

A button with role="switch" and aria-checked is the whole accessible core. The optimistic pattern lives in one handler: flip, request, revert on failure.

src/components/Switch.tsx

function Switch({ checked, onChange, label }) {
  return (
    <button
      role="switch"
      aria-checked={checked}
      aria-label={label}
      onClick={() => onChange(!checked)}
      className={`relative h-6 w-10 rounded-full transition-colors
        ${checked ? 'bg-indigo-600' : 'bg-zinc-200'}`}
    >
      <span className={`absolute top-0.5 h-5 w-5 rounded-full bg-white
        transition-transform ${checked ? 'translate-x-4' : 'translate-x-0.5'}`} />
    </button>
  )
}

Cómo añadir tu Switch a un proyecto

Cuatro pasos, desde elegir una plantilla de switch hasta llevarlo a producción.

01~2min

Decide the Commit Model per Surface

Go through your settings and mark each one: instant, or submit-with-form? Instant ones get switches and no save button; form-bound ones get checkboxes. Doing this before generation prevents the half-and-half page that confuses everyone.

02~10s

Generate From a Template Prompt

Paste a prompt above with your real setting names and helper text. Say explicitly whether values are server-backed or view-local, and whether any sub-settings depend on a master toggle — those two facts shape the state logic.

03~1min

Generate and Refine

Refine in plain language: "flash the track red when the request fails", "make the whole row clickable", "dim the sub-switches when the master is off". Each behavior is one follow-up message, not a rewrite.

04~5min

Test Failure, Touch and Screen Reader

Flip a switch with the API disconnected and confirm it reverts with a visible explanation. Try it on a phone with one thumb, and run a screen reader over the page to hear "switch, on" rather than "checkbox". Those three checks are the component.

Preguntas frecuentes sobre Switch

When should I use a switch instead of a checkbox?

Use a switch when the setting takes effect immediately, on its own, with no other fields involved and nothing to submit. Use a checkbox when the value joins other fields in a form that is submitted as a whole — shipping preferences inside checkout, consent at signup. The deciding question is "when does this change apply?", not "how many options are there?": two instant options are two switches, and one option inside a save-later form is a checkbox, even if a switch shape would look nicer.

Is it wrong to have a save button on a page with switches?

Yes, and it is the most common settings-page anti-pattern. The switch contract is commit-on-flip; a visible Save button contradicts it, and users genuinely cannot tell whether the toggle worked. Pick one model per surface: instant settings drop the button entirely, and anything requiring review — billing details, a group of related fields — uses checkboxes or inputs with a submit. If only some controls on a page are instant, visually separate those into their own section so the two contracts never share one form.

How big should a switch be for touch screens?

The track can look like 40x24px, but the interactive target must reach about 44x44px, or 48px if the switch sits in a dense list. The reliable approach is making the entire settings row — label, helper text and switch — one clickable control, which both enlarges the target and removes the ambiguity of tapping the label. A switch that renders as a small standalone pill with nothing else tappable forces precise aiming and fails the thumb test on every phone shipped this decade.

What should happen when the request to save the setting fails?

Revert the switch visibly and explain it — the switch returns to its previous position with a brief error indication, and a toast states that the change did not stick. Never leave the switch showing the new state when the server rejected it: the user believes email notifications are off, and discovers otherwise when the emails keep coming. Also avoid disabling every switch on the page because one is pending — each row should fail and recover independently.

Should flipping a switch require confirmation?

Only when the flip is expensive to undo or affects other people — deleting all session data, enabling a paid feature, publishing a change to a production environment. For reversible personal preferences, confirmation is friction that teaches users to flip without reading. The middle path for risky flags is an optimistic flip with a short "Revert" window in the toast: fast, but self-forgiving. A switch that asks "Are you sure?" on every toggle is telling you it should not be a switch.

How do I handle settings that depend on a master toggle?

When the master turns off, render the sub-switches disabled and dimmed but keep their stored values intact — turning email off entirely should not silently unsubscribe the user from digests forever. Bind disabled rather than unmounting, and say why in a tooltip or helper line so the dimming reads as dependency, not breakage. The alternative, hiding sub-options, is worse: the settings vanish, and re-enabling the master surfaces values the user does not remember choosing.