various improvements, edit tournament, etc

This commit is contained in:
yohlo
2025-08-24 22:56:48 -05:00
parent 936ab0ce72
commit 2b8ccf1649
25 changed files with 504 additions and 52 deletions

View File

@@ -4,11 +4,12 @@ import {
useMatch,
useRouter,
useNavigate,
redirect,
} from '@tanstack/react-router'
import type { ErrorComponentProps } from '@tanstack/react-router'
import {
Box,
Button,
Button as MantineButton,
Text,
Title,
Stack,
@@ -23,6 +24,7 @@ import { useEffect } from 'react'
import toast from '@/lib/sonner'
import { logger } from '@/lib/logger'
import { ExclamationMarkIcon, XCircleIcon } from '@phosphor-icons/react'
import Button from './button'
export function DefaultCatchBoundary({ error }: ErrorComponentProps) {
const router = useRouter()
@@ -41,8 +43,8 @@ export function DefaultCatchBoundary({ error }: ErrorComponentProps) {
if (errorMessage.toLowerCase().includes('unauthenticated')) {
toast.error('You\'ve been logged out')
navigate({ to: '/login' })
return
router.history.push('/login')
throw redirect({ to: '/login' })
}
}, [error, errorMessage, navigate])
@@ -73,13 +75,13 @@ export function DefaultCatchBoundary({ error }: ErrorComponentProps) {
>
Go Back
</Button>
<Button
<MantineButton
component={Link}
to="/"
variant="filled"
>
Home
</Button>
</MantineButton>
</Group>
</Stack>
</Box>
@@ -137,13 +139,13 @@ export function DefaultCatchBoundary({ error }: ErrorComponentProps) {
Try Again
</Button>
{isRoot ? (
<Button
<MantineButton
component={Link}
to="/"
variant="filled"
>
Home
</Button>
</MantineButton>
) : (
<Button
variant="filled"

View File

@@ -4,11 +4,14 @@ interface AvatarProps extends Omit<MantineAvatarProps, 'radius' | 'color' | 'siz
name: string;
size?: number;
radius?: string | number;
withBorder?: boolean;
}
const Avatar = ({ name, size = 35, radius = '100%', ...props }: AvatarProps) => {
return <Paper p={size / 20} radius={radius} withBorder>
<MantineAvatar alt={name} key={name} name={name} color='initials' size={size} radius={radius} {...props} />
const Avatar = ({ name, size = 35, radius = '100%', withBorder = true, ...props }: AvatarProps) => {
return <Paper p={size / 20} radius={radius} withBorder={withBorder}>
<MantineAvatar alt={name} key={name} name={name} color='initials' size={size} radius={radius} w='fit-content' styles={{ image: {
objectFit: 'contain'
} }} {...props} />
</Paper>
}

11
src/components/button.tsx Normal file
View File

@@ -0,0 +1,11 @@
import { Button as MantineButton, ButtonProps as MantineButtonProps } from '@mantine/core';
import { forwardRef, ComponentPropsWithoutRef } from 'react';
type ButtonProps = MantineButtonProps & ComponentPropsWithoutRef<'button'>;
const Button = forwardRef<HTMLButtonElement, ButtonProps>((props, ref) => {
return <MantineButton fullWidth ref={ref} {...props} />;
});
Button.displayName = 'Button';
export default Button;

View File

@@ -0,0 +1,78 @@
import { TextInput, Flex, Box, Button } from "@mantine/core";
import { CalendarIcon } from "@phosphor-icons/react";
import { useSheet } from "@/hooks/use-sheet";
import Sheet from "@/components/sheet/sheet";
import { DateTimePicker } from "../features/admin/components/date-time-picker";
interface DateInputProps {
label: string;
value: string;
onChange: (value: string) => void;
withAsterisk?: boolean;
error?: React.ReactNode;
placeholder?: string;
}
// Date input that opens a sheet with mantine date time picker when clicked
export const DateInputSheet = ({
label,
value,
onChange,
withAsterisk,
error,
placeholder
}: DateInputProps) => {
const sheet = useSheet();
const formatDisplayValue = (dateString: string) => {
if (!dateString) return '';
const date = new Date(dateString);
if (isNaN(date.getTime())) return '';
return date.toLocaleDateString('en-US', {
weekday: 'short',
year: 'numeric',
month: 'short',
day: 'numeric',
hour: 'numeric',
minute: 'numeric',
hour12: true
});
};
const handleDateChange = (newValue: string | null) => {
onChange(newValue || '');
sheet.close();
};
const dateValue = value ? new Date(value) : null;
return (
<>
<TextInput
label={label}
value={formatDisplayValue(value)}
onClick={sheet.open}
readOnly
withAsterisk={withAsterisk}
error={error}
placeholder={placeholder || "Click to select date"}
rightSection={<CalendarIcon size={16} />}
style={{ cursor: 'pointer' }}
/>
<Sheet {...sheet.props} title={`Select ${label}`}>
<Flex gap='xs' direction='column' justify='center' p="md">
<Box mx='auto'>
<DateTimePicker
value={dateValue}
onChange={handleDateChange}
/>
</Box>
<Button onClick={sheet.close} variant="subtle">
Close
</Button>
</Flex>
</Sheet>
</>
);
};

View File

@@ -1,16 +0,0 @@
import { AuthProvider } from "@/contexts/auth-context"
import MantineProvider from "@/lib/mantine/mantine-provider"
import { Toaster } from "sonner"
const Providers = ({ children }: { children: React.ReactNode }) => {
return (
<AuthProvider>
<MantineProvider>
<Toaster position='top-center' />
{children}
</MantineProvider>
</AuthProvider>
)
}
export default Providers;

View File

@@ -1,7 +1,8 @@
import { Box, Text, Group, ActionIcon, Button, ScrollArea, Divider } from "@mantine/core";
import { Box, Text, Group, ActionIcon, ScrollArea, Divider } from "@mantine/core";
import { ArrowLeftIcon, CheckIcon } from "@phosphor-icons/react";
import { useState, ReactNode} from "react";
import { SlidePanelContext, type PanelConfig } from "./slide-panel-context";
import Button from "@/components/button";
interface SlidePanelProps {
children: ReactNode;

View File

@@ -1,4 +1,4 @@
import { FloatingIndicator, UnstyledButton, Box, Text } from "@mantine/core";
import { FloatingIndicator, UnstyledButton, Box, Text, ScrollArea } from "@mantine/core";
import { Carousel } from "@mantine/carousel";
import { useState, useEffect, ReactNode } from "react";