170 lines
5.3 KiB
TypeScript
170 lines
5.3 KiB
TypeScript
'use client';
|
||
|
||
import Button from '@/components/ui/Button';
|
||
import Input from '@/components/ui/Input';
|
||
import { useEffectiveDriverId } from "@/lib/hooks/useEffectiveDriverId";
|
||
import { useCreateTeam } from "@/lib/hooks/team";
|
||
import { useRouter } from 'next/navigation';
|
||
import { useState } from 'react';
|
||
|
||
interface CreateTeamFormProps {
|
||
onCancel?: () => void;
|
||
onSuccess?: (teamId: string) => void;
|
||
}
|
||
|
||
export default function CreateTeamForm({ onCancel, onSuccess }: CreateTeamFormProps) {
|
||
const router = useRouter();
|
||
const createTeamMutation = useCreateTeam();
|
||
const [formData, setFormData] = useState({
|
||
name: '',
|
||
tag: '',
|
||
description: '',
|
||
});
|
||
const [errors, setErrors] = useState<Record<string, string>>({});
|
||
const currentDriverId = useEffectiveDriverId();
|
||
|
||
const validateForm = () => {
|
||
const newErrors: Record<string, string> = {};
|
||
|
||
if (!formData.name.trim()) {
|
||
newErrors.name = 'Team name is required';
|
||
} else if (formData.name.length < 3) {
|
||
newErrors.name = 'Team name must be at least 3 characters';
|
||
}
|
||
|
||
if (!formData.tag.trim()) {
|
||
newErrors.tag = 'Team tag is required';
|
||
} else if (formData.tag.length > 4) {
|
||
newErrors.tag = 'Team tag must be 4 characters or less';
|
||
}
|
||
|
||
if (!formData.description.trim()) {
|
||
newErrors.description = 'Description is required';
|
||
} else if (formData.description.length < 10) {
|
||
newErrors.description = 'Description must be at least 10 characters';
|
||
}
|
||
|
||
setErrors(newErrors);
|
||
return Object.keys(newErrors).length === 0;
|
||
};
|
||
|
||
const handleSubmit = async (e: React.FormEvent) => {
|
||
e.preventDefault();
|
||
|
||
if (!validateForm()) {
|
||
return;
|
||
}
|
||
|
||
createTeamMutation.mutate(
|
||
{
|
||
name: formData.name,
|
||
tag: formData.tag.toUpperCase(),
|
||
description: formData.description,
|
||
},
|
||
{
|
||
onSuccess: (result) => {
|
||
const teamId = result.id;
|
||
if (onSuccess) {
|
||
onSuccess(teamId);
|
||
} else {
|
||
router.push(`/teams/${teamId}`);
|
||
}
|
||
},
|
||
onError: (error) => {
|
||
alert(error instanceof Error ? error.message : 'Failed to create team');
|
||
},
|
||
}
|
||
);
|
||
};
|
||
|
||
return (
|
||
<form onSubmit={handleSubmit} className="space-y-6">
|
||
<div>
|
||
<label className="block text-sm font-medium text-gray-400 mb-2">
|
||
Team Name *
|
||
</label>
|
||
<Input
|
||
type="text"
|
||
value={formData.name}
|
||
onChange={(e) => setFormData({ ...formData, name: e.target.value })}
|
||
placeholder="Enter team name..."
|
||
disabled={createTeamMutation.isPending}
|
||
/>
|
||
{errors.name && (
|
||
<p className="text-danger-red text-xs mt-1">{errors.name}</p>
|
||
)}
|
||
</div>
|
||
|
||
<div>
|
||
<label className="block text-sm font-medium text-gray-400 mb-2">
|
||
Team Tag *
|
||
</label>
|
||
<Input
|
||
type="text"
|
||
value={formData.tag}
|
||
onChange={(e) => setFormData({ ...formData, tag: e.target.value.toUpperCase() })}
|
||
placeholder="e.g., APEX"
|
||
maxLength={4}
|
||
disabled={createTeamMutation.isPending}
|
||
/>
|
||
<p className="text-xs text-gray-500 mt-1">Max 4 characters</p>
|
||
{errors.tag && (
|
||
<p className="text-danger-red text-xs mt-1">{errors.tag}</p>
|
||
)}
|
||
</div>
|
||
|
||
<div>
|
||
<label className="block text-sm font-medium text-gray-400 mb-2">
|
||
Description *
|
||
</label>
|
||
<textarea
|
||
className="w-full px-3 py-3 bg-iron-gray border-0 rounded-md text-white ring-1 ring-inset ring-charcoal-outline focus:ring-2 focus:ring-primary-blue transition-all duration-150 text-sm resize-none"
|
||
rows={4}
|
||
value={formData.description}
|
||
onChange={(e) => setFormData({ ...formData, description: e.target.value })}
|
||
placeholder="Describe your team's goals and racing style..."
|
||
disabled={createTeamMutation.isPending}
|
||
/>
|
||
{errors.description && (
|
||
<p className="text-danger-red text-xs mt-1">{errors.description}</p>
|
||
)}
|
||
</div>
|
||
|
||
<div className="bg-deep-graphite border border-charcoal-outline rounded-lg p-4">
|
||
<div className="flex items-start gap-3">
|
||
<div className="text-2xl">ℹ️</div>
|
||
<div className="flex-1">
|
||
<h4 className="text-white font-medium mb-1">About Team Creation</h4>
|
||
<ul className="text-sm text-gray-400 space-y-1">
|
||
<li>• You will be assigned as the team owner</li>
|
||
<li>• You can invite other drivers to join your team</li>
|
||
<li>• Team standings are calculated across leagues</li>
|
||
<li>• This is alpha data - it resets on page reload</li>
|
||
</ul>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
|
||
<div className="flex gap-3">
|
||
<Button
|
||
type="submit"
|
||
variant="primary"
|
||
disabled={createTeamMutation.isPending}
|
||
className="flex-1"
|
||
>
|
||
{createTeamMutation.isPending ? 'Creating Team...' : 'Create Team'}
|
||
</Button>
|
||
{onCancel && (
|
||
<Button
|
||
type="button"
|
||
variant="secondary"
|
||
onClick={onCancel}
|
||
disabled={createTeamMutation.isPending}
|
||
>
|
||
Cancel
|
||
</Button>
|
||
)}
|
||
</div>
|
||
</form>
|
||
);
|
||
} |