spb/countryatlas
Public
TypeScript 57%
Python 38.6%
JavaScript 3.6%
CSS 0.6%
1import { CircleSlash2 } from 'lucide-react';2import type { ReactNode } from 'react';3import { t } from '@/i18n';4import { cn } from '@/lib/cn';56/** Explicit "No data" state — never a blank space. Optional list of the sources that were checked. */7export function EmptyState({ title, hint, sourcesChecked, action, className, compact }: { title?: ReactNode; hint?: ReactNode; sourcesChecked?: string[]; action?: ReactNode; className?: string; compact?: boolean }) {8 return (9 <div className={cn('flex items-start gap-3 border-t border-dashed border-rule-strong text-sm text-ink-2', compact ? 'py-3' : 'py-6', className)}>10 <CircleSlash2 size={18} aria-hidden className="mt-0.5 shrink-0 text-ink-3" />11 <div className="min-w-0">12 <p className="font-medium text-ink">{title ?? t('empty.generic')}</p>13 {hint ? <p className="mt-0.5 text-ink-2">{hint}</p> : null}14 {sourcesChecked && sourcesChecked.length ? <p className="mt-0.5 text-xs text-ink-3">{t('empty.sourcesChecked', { sources: sourcesChecked.join(', ') })}</p> : null}15 {action ? <div className="mt-2">{action}</div> : null}16 </div>17 </div>18 );19}2021/** Calm full-width state for a 503 (snapshot not built yet) or unreachable API. */22export function NotBuiltState({ className }: { className?: string }) {23 return (24 <div className={cn('mx-auto max-w-prose py-16 text-center', className)}>25 <div className="eyebrow">{t('site.name')}</div>26 <h2 className="display mt-2 text-2xl text-ink">{t('common.notBuilt')}</h2>27 <p className="mt-2 text-ink-2">{t('common.notBuiltHint')}</p>28 </div>29 );30}31