website refactor

This commit is contained in:
2026-01-18 16:18:18 +01:00
parent 0b301feb61
commit 13567d51af
329 changed files with 4701 additions and 4750 deletions

View File

@@ -1,7 +1,6 @@
import { useRef, ChangeEvent } from 'react';
import { Upload, Loader2, Sparkles, Palette, Check, User } from 'lucide-react';
import { Button } from '@/ui/Button';
import { Box } from '@/ui/Box';
import { Stack } from '@/ui/Stack';
import { Text } from '@/ui/Text';
import { Icon } from '@/ui/Icon';
@@ -94,13 +93,13 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
return (
<Stack gap={8}>
{/* Photo Upload */}
<Box>
<Stack>
<Text as="label" size="sm" weight="medium" color="text-gray-300" block mb={3}>
Upload Your Photo *
</Text>
<Stack direction="row" gap={6}>
{/* Upload Area */}
<Box
<Stack
onClick={() => fileInputRef.current?.click()}
flex={1}
display="flex"
@@ -120,7 +119,7 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
hoverBg="bg-primary-blue/5"
position="relative"
>
<Box
<Stack
as="input"
ref={fileInputRef}
type="file"
@@ -136,7 +135,7 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
</Stack>
) : avatarInfo.facePhoto ? (
<Stack alignItems="center" center>
<Box w="24" h="24" rounded="xl" overflow="hidden" mb={3} ring="ring-2 ring-performance-green">
<Stack w="24" h="24" rounded="xl" overflow="hidden" mb={3} ring="ring-2 ring-performance-green">
<Image
src={avatarInfo.facePhoto}
alt="Your photo"
@@ -146,7 +145,7 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
fullWidth
fullHeight
/>
</Box>
</Stack>
<Text size="sm" color="text-performance-green" block>
<Stack flexDirection="row" alignItems="center" gap={1}>
<Icon icon={Check} size={4} />
@@ -166,7 +165,7 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
</Text>
</Stack>
)}
</Box>
</Stack>
{/* Preview area */}
<Stack w="32" alignItems="center" center>
@@ -190,10 +189,10 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
{errors.facePhoto && (
<Text size="sm" color="text-racing-red" block mt={2}>{errors.facePhoto}</Text>
)}
</Box>
</Stack>
{/* Suit Color Selection */}
<Box>
<Stack>
<Text as="label" size="sm" weight="medium" color="text-gray-300" block mb={3}>
<Stack flexDirection="row" alignItems="center" gap={2}>
<Icon icon={Palette} size={4} />
@@ -229,11 +228,11 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
<Text size="xs" color="text-gray-500" block mt={2}>
Selected: {SUIT_COLORS.find(c => c.value === avatarInfo.suitColor)?.label}
</Text>
</Box>
</Stack>
{/* Generate Button */}
{avatarInfo.facePhoto && !errors.facePhoto && (
<Box>
<Stack>
<Button
type="button"
variant="primary"
@@ -244,12 +243,12 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
>
{avatarInfo.isGenerating ? 'Generating your avatars...' : (avatarInfo.generatedAvatars.length > 0 ? 'Regenerate Avatars' : 'Generate Racing Avatars')}
</Button>
</Box>
</Stack>
)}
{/* Generated Avatars */}
{avatarInfo.generatedAvatars.length > 0 && (
<Box>
<Stack>
<Text as="label" size="sm" weight="medium" color="text-gray-300" block mb={3}>
Choose Your Avatar *
</Text>
@@ -274,9 +273,9 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
>
<Image src={url} alt={`Avatar option ${index + 1}`} width={200} height={200} objectFit="cover" fullWidth fullHeight />
{avatarInfo.selectedAvatarIndex === index && (
<Box position="absolute" top={2} right={2} w="6" h="6" rounded="full" bg="bg-primary-blue" display="flex" center>
<Stack position="absolute" top={2} right={2} w="6" h="6" rounded="full" bg="bg-primary-blue" display="flex" center>
<Icon icon={Check} size={4} color="text-white" />
</Box>
</Stack>
)}
</Button>
))}
@@ -284,7 +283,7 @@ export function AvatarStep({ avatarInfo, setAvatarInfo, errors, setErrors, onGen
{errors.avatar && (
<Text size="sm" color="text-error-red" block mt={2}>{errors.avatar}</Text>
)}
</Box>
</Stack>
)}
</Stack>
);

View File

@@ -2,7 +2,6 @@ import { Button } from '@/ui/Button';
import { Stack } from '@/ui/Stack';
import { Icon } from '@/ui/Icon';
import { ChevronLeft, ChevronRight, Check } from 'lucide-react';
import { Box } from '@/ui/Box';
interface OnboardingPrimaryActionsProps {
onBack?: () => void;
@@ -41,7 +40,7 @@ export function OnboardingPrimaryActions({
Back
</Button>
) : (
<Box />
<Stack />
)}
<Button

View File

@@ -1,6 +1,5 @@
import { Box } from '@/ui/Box';
import { Container } from '@/ui/Container';
import { Stack } from '@/ui/Stack';
import { Container } from '@/ui/Container';
interface OnboardingShellProps {
children: React.ReactNode;
@@ -17,40 +16,40 @@ interface OnboardingShellProps {
*/
export function OnboardingShell({ children, header, footer, sidebar }: OnboardingShellProps) {
return (
<Box minH="screen" bg="bg-near-black" color="text-white" display="flex" flexDirection="column">
<Stack minHeight="screen" bg="bg-near-black" color="text-white">
{header && (
<Box borderB borderColor="border-charcoal-outline" py={4} bg="bg-deep-charcoal">
<Stack borderBottom borderColor="border-charcoal-outline" py={4} bg="bg-deep-charcoal">
<Container size="md">
{header}
</Container>
</Box>
</Stack>
)}
<Box flex={1} display="flex" py={12}>
<Stack flex={1} py={12}>
<Container size="md">
<Box display="flex" gap={12}>
<Box flex={1}>
<Stack direction="row" gap={12}>
<Stack flex={1}>
<Stack gap={8}>
{children}
</Stack>
</Box>
</Stack>
{sidebar && (
<Box w="80" display={{ base: 'none', lg: 'block' }}>
<Stack w="80" display={{ base: 'none', lg: 'block' }}>
{sidebar}
</Box>
</Stack>
)}
</Box>
</Stack>
</Container>
</Box>
</Stack>
{footer && (
<Box borderT borderColor="border-charcoal-outline" py={6} bg="bg-deep-charcoal">
<Stack borderTop borderColor="border-charcoal-outline" py={6} bg="bg-deep-charcoal">
<Container size="md">
{footer}
</Container>
</Box>
</Stack>
)}
</Box>
</Stack>
);
}

View File

@@ -1,4 +1,4 @@
import { Surface } from '@/ui/Surface';
import { Panel } from '@/ui/Panel';
import { Stack } from '@/ui/Stack';
import { Text } from '@/ui/Text';
@@ -28,7 +28,7 @@ export function OnboardingStepPanel({ title, description, children }: Onboarding
)}
</Stack>
<Surface
<Panel
variant="dark"
rounded="xl"
border
@@ -37,7 +37,7 @@ export function OnboardingStepPanel({ title, description, children }: Onboarding
bg="bg-deep-charcoal/50"
>
{children}
</Surface>
</Panel>
</Stack>
);
}

View File

@@ -1,6 +1,5 @@
'use client';
import { Box } from '@/ui/Box';
import { Stack } from '@/ui/Stack';
import { Text } from '@/ui/Text';
import { motion } from 'framer-motion';
@@ -22,8 +21,8 @@ export function OnboardingStepper({ currentStep, totalSteps, steps }: Onboarding
return (
<Stack gap={4} w="full">
<Box w="full" h="1.5" bg="bg-iron-gray" rounded="full" overflow="hidden" position="relative">
<Box
<Stack w="full" h="1.5" bg="bg-iron-gray" rounded="full" overflow="hidden" position="relative">
<Stack
as={motion.div}
initial={{ width: 0 }}
animate={{ width: `${progress}%` }}
@@ -31,9 +30,9 @@ export function OnboardingStepper({ currentStep, totalSteps, steps }: Onboarding
h="full"
bg="bg-primary-blue"
/>
</Box>
</Stack>
<Box display="flex" justify="between">
<Stack display="flex" justify="between">
{steps.map((label, index) => {
const stepNumber = index + 1;
const isActive = stepNumber === currentStep;
@@ -41,7 +40,7 @@ export function OnboardingStepper({ currentStep, totalSteps, steps }: Onboarding
return (
<Stack key={label} direction="row" align="center" gap={2}>
<Box
<Stack
w="6"
h="6"
rounded="full"
@@ -59,7 +58,7 @@ export function OnboardingStepper({ currentStep, totalSteps, steps }: Onboarding
>
{stepNumber}
</Text>
</Box>
</Stack>
<Text
size="sm"
weight={isActive ? 'bold' : 'medium'}
@@ -72,7 +71,7 @@ export function OnboardingStepper({ currentStep, totalSteps, steps }: Onboarding
</Stack>
);
})}
</Box>
</Stack>
</Stack>
);
}

View File

@@ -1,7 +1,6 @@
import { Clock, ChevronRight } from 'lucide-react';
import { Input } from '@/ui/Input';
import { CountrySelect } from '@/components/shared/CountrySelect';
import { Box } from '@/ui/Box';
import { Stack } from '@/ui/Stack';
import { Text } from '@/ui/Text';
import { Icon } from '@/ui/Icon';
@@ -44,7 +43,7 @@ export function PersonalInfoStep({ personalInfo, setPersonalInfo, errors, loadin
return (
<Stack gap={6}>
<Grid cols={2} gap={4}>
<Box>
<Stack>
<Text as="label" htmlFor="firstName" size="sm" weight="medium" color="text-gray-300" block mb={2}>
First Name *
</Text>
@@ -60,9 +59,9 @@ export function PersonalInfoStep({ personalInfo, setPersonalInfo, errors, loadin
placeholder="John"
disabled={loading}
/>
</Box>
</Stack>
<Box>
<Stack>
<Text as="label" htmlFor="lastName" size="sm" weight="medium" color="text-gray-300" block mb={2}>
Last Name *
</Text>
@@ -78,10 +77,10 @@ export function PersonalInfoStep({ personalInfo, setPersonalInfo, errors, loadin
placeholder="Racer"
disabled={loading}
/>
</Box>
</Stack>
</Grid>
<Box>
<Stack>
<Text as="label" htmlFor="displayName" size="sm" weight="medium" color="text-gray-300" block mb={2}>
Display Name * <Text color="text-gray-500" weight="normal">(shown publicly)</Text>
</Text>
@@ -97,10 +96,10 @@ export function PersonalInfoStep({ personalInfo, setPersonalInfo, errors, loadin
placeholder="SpeedyRacer42"
disabled={loading}
/>
</Box>
</Stack>
<Grid cols={2} gap={4}>
<Box>
<Stack>
<Text as="label" htmlFor="country" size="sm" weight="medium" color="text-gray-300" block mb={2}>
Country *
</Text>
@@ -113,16 +112,16 @@ export function PersonalInfoStep({ personalInfo, setPersonalInfo, errors, loadin
errorMessage={errors.country ?? ''}
disabled={loading}
/>
</Box>
</Stack>
<Box>
<Stack>
<Text as="label" htmlFor="timezone" size="sm" weight="medium" color="text-gray-300" block mb={2}>
Timezone
</Text>
<Box position="relative">
<Box position="absolute" left={3} top="50%" transform="translateY(-50%)" zIndex={10}>
<Stack position="relative">
<Stack position="absolute" left={3} top="50%" transform="translateY(-50%)" zIndex={10}>
<Icon icon={Clock} size={4} color="text-gray-500" />
</Box>
</Stack>
<Select
id="timezone"
value={personalInfo.timezone}
@@ -136,11 +135,11 @@ export function PersonalInfoStep({ personalInfo, setPersonalInfo, errors, loadin
pl={10}
disabled={loading}
/>
<Box position="absolute" right={3} top="50%" transform="translateY(-50%)" pointerEvents="none">
<Stack position="absolute" right={3} top="50%" transform="translateY(-50%)" pointerEvents="none">
<Icon icon={ChevronRight} size={4} color="text-gray-500" transform="rotate(90deg)" />
</Box>
</Box>
</Box>
</Stack>
</Stack>
</Stack>
</Grid>
</Stack>
);