67 lines
2.0 KiB
TypeScript
67 lines
2.0 KiB
TypeScript
'use client';
|
|
|
|
import Link from 'next/link';
|
|
import { useEffect, useState } from 'react';
|
|
import { UserRound } from 'lucide-react';
|
|
import { AssessmentProfile } from '@/lib/assessment-types';
|
|
import {
|
|
ensureActiveProfile,
|
|
getProfiles,
|
|
setActiveProfileId,
|
|
} from '@/lib/assessment-db';
|
|
|
|
interface ProfilePickerProps {
|
|
onChange?: (profile: AssessmentProfile) => void;
|
|
}
|
|
|
|
export function ProfilePicker({ onChange }: ProfilePickerProps) {
|
|
const [profiles, setProfiles] = useState<AssessmentProfile[]>([]);
|
|
const [active, setActive] = useState('');
|
|
|
|
useEffect(() => {
|
|
let mounted = true;
|
|
async function load() {
|
|
const profile = await ensureActiveProfile();
|
|
const all = await getProfiles();
|
|
if (!mounted) return;
|
|
setProfiles(all);
|
|
setActive(profile.id);
|
|
onChange?.(profile);
|
|
}
|
|
void load();
|
|
return () => { mounted = false; };
|
|
}, [onChange]);
|
|
|
|
const select = (profileId: string) => {
|
|
const profile = profiles.find((item) => item.id === profileId);
|
|
if (!profile) return;
|
|
setActive(profileId);
|
|
setActiveProfileId(profileId);
|
|
onChange?.(profile);
|
|
};
|
|
|
|
return (
|
|
<div className="mb-6 flex flex-col gap-3 border bg-muted/30 p-3 sm:flex-row sm:items-center sm:justify-between">
|
|
<div className="flex items-center gap-2 text-sm font-medium">
|
|
<UserRound className="h-4 w-4" />
|
|
本次记录到
|
|
</div>
|
|
<div className="flex items-center gap-2">
|
|
<select
|
|
aria-label="选择测评档案"
|
|
className="h-11 min-w-32 border bg-background px-3 text-base md:h-9 md:text-sm"
|
|
value={active}
|
|
onChange={(event) => select(event.target.value)}
|
|
>
|
|
{profiles.map((profile) => (
|
|
<option key={profile.id} value={profile.id}>{profile.name}</option>
|
|
))}
|
|
</select>
|
|
<Link href="/records" className="flex min-h-11 items-center text-sm text-primary underline-offset-4 hover:underline md:min-h-9">
|
|
管理档案
|
|
</Link>
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|