import { useState } from "react"; import { useCreateCategory } from "../hooks/useCategories"; import { useCreateItem } from "../hooks/useItems"; import { useUpdateSetting } from "../hooks/useSettings"; import { LucideIcon } from "../lib/iconData"; import { IconPicker } from "./IconPicker"; interface OnboardingWizardProps { onComplete: () => void; } export function OnboardingWizard({ onComplete }: OnboardingWizardProps) { const [step, setStep] = useState(1); // Step 2 state const [categoryName, setCategoryName] = useState(""); const [categoryIcon, setCategoryIcon] = useState(""); const [categoryError, setCategoryError] = useState(""); const [createdCategoryId, setCreatedCategoryId] = useState( null, ); // Step 3 state const [itemName, setItemName] = useState(""); const [itemWeight, setItemWeight] = useState(""); const [itemPrice, setItemPrice] = useState(""); const [itemError, setItemError] = useState(""); const createCategory = useCreateCategory(); const createItem = useCreateItem(); const updateSetting = useUpdateSetting(); function handleSkip() { updateSetting.mutate( { key: "onboardingComplete", value: "true" }, { onSuccess: onComplete }, ); } function handleCreateCategory() { const name = categoryName.trim(); if (!name) { setCategoryError("Please enter a category name"); return; } setCategoryError(""); createCategory.mutate( { name, icon: categoryIcon.trim() || undefined }, { onSuccess: (created) => { setCreatedCategoryId(created.id); setStep(3); }, onError: (err) => { setCategoryError(err.message || "Failed to create category"); }, }, ); } function handleCreateItem() { const name = itemName.trim(); if (!name) { setItemError("Please enter an item name"); return; } if (!createdCategoryId) return; setItemError(""); const payload: any = { name, categoryId: createdCategoryId, }; if (itemWeight) payload.weightGrams = Number(itemWeight); if (itemPrice) payload.priceCents = Math.round(Number(itemPrice) * 100); createItem.mutate(payload, { onSuccess: () => setStep(4), onError: (err) => { setItemError(err.message || "Failed to add item"); }, }); } function handleDone() { updateSetting.mutate( { key: "onboardingComplete", value: "true" }, { onSuccess: onComplete }, ); } return (
{/* Backdrop */}
{/* Card */}
{/* Step indicator */}
{[1, 2, 3].map((s) => (
))}
{/* Step 1: Welcome */} {step === 1 && (

Welcome to GearBox!

Track your gear, compare weights, and plan smarter purchases. Let's set up your first category and item.

)} {/* Step 2: Create category */} {step === 2 && (

Create a category

Categories help you organize your gear (e.g. Shelter, Cooking, Clothing).

setCategoryName(e.target.value)} className="w-full px-3 py-2 border border-gray-200 rounded-lg text-sm focus:outline-none focus:ring-2 focus:ring-gray-400 focus:border-transparent" placeholder="e.g. Shelter" />
{categoryError && (

{categoryError}

)}
)} {/* Step 3: Add item */} {step === 3 && (

Add your first item

Add a piece of gear to your collection.

setItemName(e.target.value)} className="w-full px-3 py-2 border border-gray-200 rounded-lg text-sm focus:outline-none focus:ring-2 focus:ring-gray-400 focus:border-transparent" placeholder="e.g. Big Agnes Copper Spur" />
setItemWeight(e.target.value)} className="w-full px-3 py-2 border border-gray-200 rounded-lg text-sm focus:outline-none focus:ring-2 focus:ring-gray-400 focus:border-transparent" placeholder="e.g. 1200" />
setItemPrice(e.target.value)} className="w-full px-3 py-2 border border-gray-200 rounded-lg text-sm focus:outline-none focus:ring-2 focus:ring-gray-400 focus:border-transparent" placeholder="e.g. 349.99" />
{itemError &&

{itemError}

}
)} {/* Step 4: Done */} {step === 4 && (

You're all set!

Your first item has been added. You can now browse your collection, add more gear, and track your setup.

)}
); }