show EmptyCard in face rec when face library is empty

This commit is contained in:
Josh Hawkins 2026-05-10 13:35:59 -05:00
parent 4da33493cd
commit 208b80939b
2 changed files with 22 additions and 1 deletions

View File

@ -32,7 +32,11 @@
"title": "Recent Recognitions", "title": "Recent Recognitions",
"titleShort": "Recent", "titleShort": "Recent",
"aria": "Select recent recognitions", "aria": "Select recent recognitions",
"empty": "There are no recent face recognition attempts" "empty": "There are no recent face recognition attempts",
"emptyNoLibrary": {
"title": "Upload a face",
"description": "You must add at least one face to the library for face recognition to function."
}
}, },
"deleteFaceLibrary": { "deleteFaceLibrary": {
"title": "Delete Name", "title": "Delete Name",

View File

@ -1,5 +1,6 @@
import AddFaceIcon from "@/components/icons/AddFaceIcon"; import AddFaceIcon from "@/components/icons/AddFaceIcon";
import ActivityIndicator from "@/components/indicators/activity-indicator"; import ActivityIndicator from "@/components/indicators/activity-indicator";
import { EmptyCard } from "@/components/card/EmptyCard";
import CreateFaceWizardDialog from "@/components/overlay/detail/FaceCreateWizardDialog"; import CreateFaceWizardDialog from "@/components/overlay/detail/FaceCreateWizardDialog";
import TextEntryDialog from "@/components/overlay/dialog/TextEntryDialog"; import TextEntryDialog from "@/components/overlay/dialog/TextEntryDialog";
import UploadImageDialog from "@/components/overlay/dialog/UploadImageDialog"; import UploadImageDialog from "@/components/overlay/dialog/UploadImageDialog";
@ -474,6 +475,7 @@ export default function FaceLibrary() {
faceNames={faces} faceNames={faces}
selectedFaces={selectedFaces} selectedFaces={selectedFaces}
onClickFaces={onClickFaces} onClickFaces={onClickFaces}
onAddFace={() => setAddFace(true)}
onRefresh={refreshFaces} onRefresh={refreshFaces}
/> />
) : ( ) : (
@ -692,6 +694,7 @@ type TrainingGridProps = {
faceNames: string[]; faceNames: string[];
selectedFaces: string[]; selectedFaces: string[];
onClickFaces: (images: string[], ctrl: boolean) => void; onClickFaces: (images: string[], ctrl: boolean) => void;
onAddFace: () => void;
onRefresh: ( onRefresh: (
data?: data?:
| FaceLibraryData | FaceLibraryData
@ -709,6 +712,7 @@ function TrainingGrid({
faceNames, faceNames,
selectedFaces, selectedFaces,
onClickFaces, onClickFaces,
onAddFace,
onRefresh, onRefresh,
}: TrainingGridProps) { }: TrainingGridProps) {
const { t } = useTranslation(["views/faceLibrary"]); const { t } = useTranslation(["views/faceLibrary"]);
@ -762,6 +766,19 @@ function TrainingGrid({
]); ]);
if (attemptImages.length == 0) { if (attemptImages.length == 0) {
if (faceNames.length == 0) {
return (
<EmptyCard
className="absolute left-1/2 top-1/2 -translate-x-1/2 -translate-y-1/2 items-center text-center"
icon={<AddFaceIcon className="size-16" />}
title={t("train.emptyNoLibrary.title")}
description={t("train.emptyNoLibrary.description")}
buttonText={t("button.addFace")}
onClick={onAddFace}
/>
);
}
return ( return (
<div className="absolute left-1/2 top-1/2 flex -translate-x-1/2 -translate-y-1/2 flex-col items-center justify-center text-center"> <div className="absolute left-1/2 top-1/2 flex -translate-x-1/2 -translate-y-1/2 flex-col items-center justify-center text-center">
<LuFolderCheck className="size-16" /> <LuFolderCheck className="size-16" />