96 lines
2.8 KiB
TypeScript
96 lines
2.8 KiB
TypeScript
'use client';
|
|
|
|
import { useEffect, useState } from 'react';
|
|
import { useLocale } from 'next-intl';
|
|
|
|
interface ApiStatement {
|
|
id: number;
|
|
text: string;
|
|
active?: boolean;
|
|
}
|
|
|
|
export default function PoliticalStatementBanner() {
|
|
const locale = useLocale();
|
|
const [statement, setStatement] = useState<ApiStatement | null>(null);
|
|
const [visible, setVisible] = useState(false);
|
|
|
|
useEffect(() => {
|
|
const today = new Date().toISOString().split('T')[0];
|
|
const storageKey = `hoerdle_political_statement_shown_${today}_${locale}`;
|
|
|
|
try {
|
|
const alreadyShown = typeof window !== 'undefined' && window.localStorage.getItem(storageKey);
|
|
if (alreadyShown) {
|
|
return;
|
|
}
|
|
} catch {
|
|
// ignore localStorage errors
|
|
}
|
|
|
|
let timeoutId: number | undefined;
|
|
|
|
const fetchStatement = async () => {
|
|
try {
|
|
const res = await fetch(`/api/political-statements?locale=${encodeURIComponent(locale)}`, {
|
|
cache: 'no-store',
|
|
});
|
|
if (!res.ok) return;
|
|
const data = await res.json();
|
|
if (!data || !data.text) return;
|
|
setStatement(data);
|
|
setVisible(true);
|
|
|
|
timeoutId = window.setTimeout(() => {
|
|
setVisible(false);
|
|
try {
|
|
window.localStorage.setItem(storageKey, 'true');
|
|
} catch {
|
|
// ignore
|
|
}
|
|
}, 5000);
|
|
} catch (e) {
|
|
console.warn('[PoliticalStatementBanner] Failed to load statement', e);
|
|
}
|
|
};
|
|
|
|
fetchStatement();
|
|
|
|
return () => {
|
|
if (timeoutId) {
|
|
window.clearTimeout(timeoutId);
|
|
}
|
|
};
|
|
}, [locale]);
|
|
|
|
if (!visible || !statement) return null;
|
|
|
|
return (
|
|
<div
|
|
style={{
|
|
position: 'fixed',
|
|
bottom: '1.25rem',
|
|
left: '50%',
|
|
transform: 'translateX(-50%)',
|
|
maxWidth: '640px',
|
|
width: 'calc(100% - 2.5rem)',
|
|
zIndex: 1050,
|
|
background: 'rgba(17,24,39,0.95)',
|
|
color: '#e5e7eb',
|
|
padding: '0.75rem 1rem',
|
|
borderRadius: '999px',
|
|
fontSize: '0.85rem',
|
|
lineHeight: 1.4,
|
|
boxShadow: '0 10px 25px rgba(0,0,0,0.45)',
|
|
display: 'flex',
|
|
alignItems: 'center',
|
|
gap: '0.5rem',
|
|
}}
|
|
>
|
|
<span style={{ fontSize: '0.9rem' }}>✊</span>
|
|
<span style={{ flex: 1 }}>{statement.text}</span>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
|