{isVocab
? `Eintrag ${activeIndex + 1} von ${editedEntries.length}`
: `Zeile ${activeIndex + 1} von ${getUniqueRowCount()}`
}
{/* eslint-disable-next-line @next/next/no-img-element */}
}`})
{/* Highlight overlay for active row/entry */}
{isVocab && editedEntries[activeIndex]?.bbox && (
)}
{!isVocab && (() => {
const rowCells = getRowCells(activeIndex)
return rowCells.map(cell => (
))
})()}
{/* Navigation */}
{activeIndex + 1} / {isVocab ? editedEntries.length : getUniqueRowCount()}
{/* Status badge */}
{isVocab && (
<>
{editedEntries[activeIndex]?.status || 'pending'}
{editedEntries[activeIndex]?.confidence}% Konfidenz
>
)}
{!isVocab && (() => {
const rowCells = getRowCells(activeIndex)
const avgConf = rowCells.length
? Math.round(rowCells.reduce((s, c) => s + c.confidence, 0) / rowCells.length)
: 0
return (
{avgConf}% Konfidenz
)
})()}
{/* Cell crops (vocab mode) */}
{isVocab && editedEntries[activeIndex]?.bbox_en && (
)}
{isVocab && editedEntries[activeIndex]?.bbox_de && (
)}
{/* Editable fields */}
{isVocab ? (
/* Vocab mode: EN/DE/Example fields */
<>
>
) : (
/* Generic mode: one field per column */
<>
{(() => {
const rowCells = getRowCells(activeIndex)
return columnsUsed.map((col) => {
const cell = rowCells.find(c => c.col_index === col.index)
if (!cell) return null
return (
{cell.cell_id}
{/* Cell crop */}
)
})
})()}
>
)}
{/* Action buttons */}
{/* Shortcuts hint */}
Enter = Bestaetigen & weiter
Ctrl+Down = Ueberspringen
Ctrl+Up = Zurueck
{/* Entry/Row list (compact) */}
{isVocab ? 'Alle Eintraege' : 'Alle Zeilen'}
{isVocab ? (
editedEntries.map((entry, idx) => (
setActiveIndex(idx)}
className={`flex items-center gap-1 px-2 py-1 rounded text-[10px] cursor-pointer transition-colors ${
idx === activeIndex
? 'bg-teal-50 dark:bg-teal-900/30 border border-teal-200 dark:border-teal-700'
: 'hover:bg-gray-50 dark:hover:bg-gray-700/50'
}`}
>
{idx + 1}
{(entry.english || '\u2014').replace(/\n/g, ' ')} → {(entry.german || '\u2014').replace(/\n/g, ' ')}
))
) : (
sortedRowIndices.map((rowIdx, posIdx) => {
const rowCells = cellsByRow.get(rowIdx) || []
const firstText = rowCells.find(c => c.text)?.text || ''
return (
setActiveIndex(posIdx)}
className={`flex items-center gap-1 px-2 py-1 rounded text-[10px] cursor-pointer transition-colors ${
posIdx === activeIndex
? 'bg-teal-50 dark:bg-teal-900/30 border border-teal-200 dark:border-teal-700'
: 'hover:bg-gray-50 dark:hover:bg-gray-700/50'
}`}
>
R{String(rowIdx).padStart(2, '0')}
{firstText.replace(/\n/g, ' ').substring(0, 60) || '\u2014'}
)
})
)}