Files
cruciverb/frontend/src/components/ui/ReportButton.tsx
T
2026-01-26 21:35:45 +02:00

66 lines
2.4 KiB
TypeScript

import { useState, useEffect, useRef, useCallback } from 'react'
import { useTranslation } from 'react-i18next'
import { IconFlagFilled } from '@tabler/icons-react'
import Select from './Select'
import * as api from '../../api'
import Tooltip from './Tooltip'
export default function ReportButton({ contentType, contentId }: { contentType: string; contentId: string }) {
const { t } = useTranslation()
const wrapRef = useRef<HTMLDivElement>(null)
const REASONS = [
{ value: '', label: t('report.selectReason') },
{ value: 'offensive', label: t('report.offensive') },
{ value: 'spam', label: t('report.spam') },
{ value: 'broken', label: t('report.broken') },
{ value: 'other', label: t('report.other') },
]
const [reported, setReported] = useState(false)
const [showForm, setShowForm] = useState(false)
const [reason, setReason] = useState<string | number>('')
const close = useCallback(() => setShowForm(false), [])
useEffect(() => {
if (!showForm) return
const onKey = (e: KeyboardEvent) => { if (e.key === 'Escape') close() }
const onClick = (e: MouseEvent) => {
const target = e.target
if (wrapRef.current && (!(target instanceof Node) || !wrapRef.current.contains(target))) close()
}
document.addEventListener('keydown', onKey)
document.addEventListener('mousedown', onClick)
return () => {
document.removeEventListener('keydown', onKey)
document.removeEventListener('mousedown', onClick)
}
}, [showForm, close])
const submit = async () => {
try {
await api.submitReport(contentType, contentId, String(reason) || 'No reason given')
setReported(true)
setShowForm(false)
} catch { /* ignored */ }
}
if (reported) return <span className="report-done">{t('common.reported')}</span>
return (
<div className="report-wrap" ref={wrapRef}>
<Tooltip text={t('common.report')}>
<button className="report-btn" onClick={(e) => { e.stopPropagation(); setShowForm(!showForm) }}>
<IconFlagFilled size={10} />
</button>
</Tooltip>
{showForm && (
<div className="report-form" onClick={e => e.stopPropagation()}>
<Select value={reason} options={REASONS} onChange={setReason} className="report-select" />
<button className="btn btn-sm" onClick={submit}>{t('common.submit')}</button>
</div>
)}
</div>
)
}