// Owner path β€” 4 steps for small-business owners replacing their stack. const OWNER_TOTAL = 4; const OWNER_STEP_NAMES = ["Business", "Stack", "First fix", "Scale"]; const BIZ_KINDS = [ { id: "service", icon: "πŸ› ", label: "Trades / home services", desc: "Plumbing, HVAC, landscaping, cleaning" }, { id: "retail", icon: "πŸ›", label: "Retail / shop", desc: "Vintage, boutique, market, online" }, { id: "food", icon: "πŸ₯", label: "Food & drink", desc: "CafΓ©, bakery, food truck, catering" }, { id: "appointments", icon: "πŸ’ˆ", label: "Appointment-based", desc: "Salon, studio, clinic, tutoring" }, { id: "events", icon: "🎟", label: "Events / hospitality", desc: "Venue, rental, planning" }, { id: "other", icon: "✦", label: "Something else", desc: "We'll learn from your answers" }, ]; function OwnerBiz({ value, name, onChange, onNameChange }) { return ( <> ({ id: b.id, label: b.label, desc: b.desc, icon: {b.icon}, }))} value={value} onChange={onChange} columns={2} /> onNameChange(e.target.value)} /> ); } const STACK_TOOLS = [ "Square / POS", "Stripe", "Calendly", "Acuity", "Shopify", "QuickBooks", "Mailchimp", "Instagram", "Google Sheets", "Notion / Airtable", "Wix / Squarespace", "WhatsApp / Slack", "A printed binder", "Head + notepad", ]; function OwnerStack({ tools, spend, onToolsChange, onSpendChange }) { return ( <> v === 0 ? "$0" : v === 1500 ? "$1.5k+" : `$${v}`} /> {(tools || []).length > 0 && (
{tools.length} tool{tools.length === 1 ? "" : "s"} {spend ? <> Β· ~${spend}/mo : null}. Replaced by one workspace, owned by you.
)} ); } const OWNER_FIRST_THINGS = [ { id: "booking", icon: "πŸ“…", label: "Bookings & scheduling", desc: "Customers book themselves." }, { id: "invoicing", icon: "🧾", label: "Quotes, invoices, payments", desc: "Send a quote, get paid, no chasing." }, { id: "customers", icon: "πŸ‘₯", label: "Customer history & portal", desc: "One place per customer." }, { id: "inventory", icon: "πŸ“¦", label: "Inventory & orders", desc: "Track stock, sales, suppliers." }, { id: "team", icon: "πŸͺͺ", label: "Team & job dispatch", desc: "Assign jobs, log hours." }, { id: "marketing", icon: "πŸ“£", label: "Website + email + reviews", desc: "A site that converts, list that follows up." }, ]; function OwnerFirstThing({ value, onChange }) { return ( <> ({ id: f.id, label: f.label, desc: f.desc, icon: {f.icon}, }))} value={value} onChange={onChange} columns={2} /> ); } const OWNER_HOW_LONG = [ { id: "starting", label: "Just starting" }, { id: "1_3", label: "1–3 years" }, { id: "3_10", label: "3–10 years" }, { id: "10_plus", label: "10+ years" }, ]; function OwnerScale({ customers, team, howLong, onCustomers, onTeam, onHowLong }) { return ( <> v === 0 ? "0" : v >= 2000 ? "2k+" : v.toLocaleString()} /> v >= 50 ? "50+" : `${v}`} />
{OWNER_HOW_LONG.map((h) => ( ))}
); } // ── Path wrapper ─────────────────────────────────────────────────────────── function OwnerPath({ data, onUpdate, onBack, onClose, onComplete, onJumpToStep, step }) { const next = () => { if (step < OWNER_TOTAL - 1) onJumpToStep(step + 1); else onComplete(); }; const back = () => { if (step === 0) onBack(); else onJumpToStep(step - 1); }; let body, canNext; if (step === 0) { body = ( onUpdate({ biz: v })} onNameChange={(v) => onUpdate({ bizName: v })} /> ); canNext = !!data.biz && (data.bizName || "").trim().length >= 2; } else if (step === 1) { body = ( onUpdate({ tools: v })} onSpendChange={(v) => onUpdate({ spend: v })} /> ); canNext = (data.tools || []).length >= 1; } else if (step === 2) { body = onUpdate({ firstThing: v })} />; canNext = !!data.firstThing; } else { body = ( onUpdate({ customers: v })} onTeam={(v) => onUpdate({ team: v })} onHowLong={(v) => onUpdate({ howLong: v })} /> ); canNext = !!data.howLong; } return ( <> {body} ); } Object.assign(window, { OwnerPath, OWNER_TOTAL });