diff --git a/src/app/actions/calibration-scoring.ts b/src/app/actions/calibration-scoring.ts index 17abf84..80777c3 100644 --- a/src/app/actions/calibration-scoring.ts +++ b/src/app/actions/calibration-scoring.ts @@ -82,7 +82,7 @@ function calculateDialectScores( if (!answer) continue; const isCorrect = answer.dialectLabel === item.dialectLabel ? 1 : -1; - const confidence = answer.confidence / 5; // Normalize to 0-1 + const confidence = answer.confidence / 4; // Normalize to 0-1 // Score = correctness * confidence // Correct answers: +confidence (0 to 1) diff --git a/src/app/page.tsx b/src/app/page.tsx index a2c1509..b50ecb2 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -47,7 +47,7 @@ export default async function HomePage() { return (
-

Experimente

+

Experimente

Wählen Sie ein Experiment aus, um mit der Annotation zu beginnen oder fortzufahren.

diff --git a/src/components/AnnotationViews/AnnotationPageView.tsx b/src/components/AnnotationViews/AnnotationPageView.tsx index 80d458e..a80a369 100644 --- a/src/components/AnnotationViews/AnnotationPageView.tsx +++ b/src/components/AnnotationViews/AnnotationPageView.tsx @@ -12,6 +12,7 @@ import CalibrationScoresModal from '@/components/CalibrationScoresModal'; export interface EntryViewProps { entry: DatasetEntryForAnnotation; + index: number; onSave: (rating: number) => Promise; isSaving: boolean; ratingOptions?: { value: number; label: JSX.Element | string }[]; @@ -67,7 +68,7 @@ export default function AnnotationPageView({ { value: 4, label: `Klingt eher nach ${DIALECT_LABELS[dialectLabel]}` }, { value: 5, label: `Klingt eindeutig nach ${DIALECT_LABELS[dialectLabel]}` }, ], - question:
Wie authentisch klingt dieses Sample nach dem Dialekt der Region {DIALECT_LABELS[dialectLabel]}?
, + question:
Wie authentisch klingt diese Aufnahme nach dem Dialekt der Region {DIALECT_LABELS[dialectLabel]}?
, }; case 'binary': return { @@ -76,7 +77,7 @@ export default function AnnotationPageView({ { value: 2, label: 'Unklar' }, { value: 1, label: 'Nein' }, ], - question:
Klingt dieses Sample nach dem Dialekt der Region {DIALECT_LABELS[dialectLabel]}?
, + question:
Klingt diese Aufnahme nach dem Dialekt der Region {DIALECT_LABELS[dialectLabel]}?
, }; default: return { @@ -94,6 +95,7 @@ export default function AnnotationPageView({ return ( {/* Top bar */} -
+
{/* Toggle and Home buttons */} -
+
)}
-
+

- {annotatedCount}/{entries.length} annotiert ({progressPct}%) + {annotatedCount}/{entries.length} bewertet ({progressPct}%)

@@ -47,7 +47,7 @@ export default function AnnotationSidebarNavigation({ {/* Entries List - scrollable middle section with max height */}

- Samples + Aufnahmen

{entries.map((entry, index) => ( @@ -77,7 +77,7 @@ export default function AnnotationSidebarNavigation({ /> {/* Entry number and filename */} - {`Sample ${index + 1} - ${DIALECT_LABELS[entry.dialect]}`} + {`Aufnahme ${index + 1} - ${DIALECT_LABELS[entry.dialect]}`}
diff --git a/src/components/AnnotationViews/SingleChoiceBinaryEntryView.tsx b/src/components/AnnotationViews/SingleChoiceBinaryEntryView.tsx index 0d63228..d5507da 100644 --- a/src/components/AnnotationViews/SingleChoiceBinaryEntryView.tsx +++ b/src/components/AnnotationViews/SingleChoiceBinaryEntryView.tsx @@ -8,6 +8,7 @@ const AUTO_ADVANCE_DELAY_MS = 600; export default function SingleChoiceBinaryEntryView({ entry, + index, onSave, isSaving, ratingOptions, @@ -39,14 +40,14 @@ export default function SingleChoiceBinaryEntryView({ return (
{/* Sample header */}
- Sample - {entry.externalId} + Aufnahme {index + 1} {fullyPlayed && ( @@ -64,14 +65,14 @@ export default function SingleChoiceBinaryEntryView({ {/* Must-listen hint */} {!fullyPlayed && ( -

- Bitte das Sample vollständig anhören, bevor Sie eine Bewertung abgeben. +

+ Bitte die Aufnahme vollständig anhören, bevor du eine Bewertung abgibst.

)} {/* Dialect + question */}
-
+
{question}
@@ -99,6 +100,11 @@ export default function SingleChoiceBinaryEntryView({ ); })}
+ + {/* Footnote */} +

+ Vertrau deinem ersten Eindruck – klingt die Aufnahme authentisch nach diesem Dialekt? Es gibt keine richtige oder falsche Antwort. +

); } diff --git a/src/components/AnnotationViews/SingleChoiceEntryView.tsx b/src/components/AnnotationViews/SingleChoiceEntryView.tsx index 01161a3..498e6f3 100644 --- a/src/components/AnnotationViews/SingleChoiceEntryView.tsx +++ b/src/components/AnnotationViews/SingleChoiceEntryView.tsx @@ -9,6 +9,7 @@ const AUTO_ADVANCE_DELAY_MS = 600; export default function SingleChoiceEntryView({ entry, + index, onSave, isSaving, ratingOptions, @@ -40,14 +41,14 @@ export default function SingleChoiceEntryView({ return (
{/* Sample header */}
- Sample - {entry.externalId} + Aufnahme {index + 1} {fullyPlayed && ( @@ -65,14 +66,14 @@ export default function SingleChoiceEntryView({ {/* Must-listen hint */} {!fullyPlayed && ( -

- Bitte das Sample vollständig anhören, bevor Sie eine Bewertung abgeben. +

+ Bitte die Aufnahme vollständig anhören, bevor du eine Bewertung abgibst.

)} {/* Dialect + question */}
-
+
{question}
@@ -109,6 +110,11 @@ export default function SingleChoiceEntryView({ ); })}
+ + {/* Footnote */} +

+ Vertrau deinem ersten Eindruck – klingt die Aufnahme authentisch nach diesem Dialekt? Es gibt keine richtige oder falsche Antwort. +

); } diff --git a/src/components/CalibrationScoresDisplay.tsx b/src/components/CalibrationScoresDisplay.tsx index 43cb1f1..7141053 100644 --- a/src/components/CalibrationScoresDisplay.tsx +++ b/src/components/CalibrationScoresDisplay.tsx @@ -26,9 +26,7 @@ export default function CalibrationScoresDisplay({
{DIALECT_LABELS[dialect]} - - {(score * 100).toFixed(0)}% - +

- Die Scores basieren auf der Genauigkeit und dem Vertrauen in Ihre Kalibrierergebnisse. - Dialekte mit höheren Scores werden zuerst in der Annotation angezeigt. + Die Ergebnisse basieren auf deiner Erkennungsgenauigkeit und Sicherheit. Dialekte die du gut erkennst, werden bei der Bewertungsphase häufiger angezeigt.

); diff --git a/src/components/CalibrationScoresModal.tsx b/src/components/CalibrationScoresModal.tsx index 9851406..341489d 100644 --- a/src/components/CalibrationScoresModal.tsx +++ b/src/components/CalibrationScoresModal.tsx @@ -23,7 +23,7 @@ export default function CalibrationScoresModal({
-

Ihre Kalibrierungsergebnisse

+

Deine Kalibrierungsergebnisse

diff --git a/src/components/OnboardingViews/OnboardingFormView.tsx b/src/components/OnboardingViews/OnboardingFormView.tsx index 5a67e2c..95b21a9 100644 --- a/src/components/OnboardingViews/OnboardingFormView.tsx +++ b/src/components/OnboardingViews/OnboardingFormView.tsx @@ -7,6 +7,7 @@ import { DIALECT_LABELS_WITHOUT_DE } from '@/lib/dialects'; interface OnboardingFormViewProps { experimentId: number; + onBack: () => void; } interface ResidenceEntry { @@ -16,6 +17,7 @@ interface ResidenceEntry { interface FormData { age?: string; + email?: string; residences?: ResidenceEntry[]; dialectQualities?: Record; listeningExperience?: string; @@ -24,22 +26,18 @@ interface FormData { type Step = 1 | 2 | 3; -export default function OnboardingFormView({ experimentId }: OnboardingFormViewProps) { +export default function OnboardingFormView({ experimentId, onBack }: OnboardingFormViewProps) { const router = useRouter(); const [isPending, startTransition] = useTransition(); const [currentStep, setCurrentStep] = useState(1); - // Initialize dialect qualities with default value of '3' for each dialect const initializeDialectQualities = (): Record => { - const qualities: Record = {}; - Object.keys(DIALECT_LABELS_WITHOUT_DE).forEach(key => { - qualities[key] = '3'; - }); - return qualities; + return {}; }; const [formData, setFormData] = useState({ age: '', + email: '', residences: [{ region: '', years: '' }], dialectQualities: initializeDialectQualities() }); @@ -116,10 +114,10 @@ export default function OnboardingFormView({ experimentId }: OnboardingFormViewP case 3: const allDialects = Object.keys(DIALECT_LABELS_WITHOUT_DE); const hasAllDialectQualities = allDialects.every( - (region) => formData.dialectQualities?.[region] + (region) => !!formData.dialectQualities?.[region] ); if (!hasAllDialectQualities) { - setError('Bitte bewerten Sie Ihre Fähigkeit für alle Dialekte.'); + setError('Bitte bewerte deine Fähigkeit für alle Dialekte.'); return false; } break; @@ -138,7 +136,9 @@ export default function OnboardingFormView({ experimentId }: OnboardingFormViewP const handlePrevious = () => { setError(null); - if (currentStep > 1) { + if (currentStep === 1) { + onBack(); + } else { setCurrentStep((currentStep - 1) as Step); } }; @@ -200,33 +200,50 @@ export default function OnboardingFormView({ experimentId }: OnboardingFormViewP {/* Step 1: Persönliche Informationen */} {currentStep === 1 && ( -
- - +
+
+ + +
+ +
+ +

Wird nur für die Gutschein-Verlosung verwendet.

+ handleChange('email', e.target.value)} + placeholder="beispiel@email.ch" + className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent" + /> +
)} {/* Step 2: Aufenthaltsorte */} {currentStep === 2 && (
-

- Bitte geben Sie die Regionen an, in denen Sie länger als 1 Jahr gelebt haben, sowie die Anzahl der Jahre. Diese Informationen helfen uns, Ihre Dialektkenntnisse besser einzuschätzen. +

+ Bitte gib die Regionen an, in denen du länger als 1 Jahr gelebt hast, sowie die Anzahl der Jahre. So können wir deine Dialektkenntnisse besser einschätzen.

{/* Map Placeholder */}
@@ -238,8 +255,8 @@ export default function OnboardingFormView({ experimentId }: OnboardingFormViewP {/* Residence Entries */}
-