TypeScript 61.9%
HTML 37.2%
SQL 0.7%
1import Link from 'next/link';2import type { VariantRow } from '@/lib/queries/assets';3import { fmtMoney, fmtNum, fmtRelative, cn, confidenceLabel } from '@/lib/format';4import { Table, th, td, tdNum, Badge } from '@/components/ui/primitives';56/**7 * Dense variant/grade matrix for md+ screens (phones use the chip selector): RIV with its band and8 * confidence, latest sale, sales and listings per variant. Rows link to the variant view.9 */10export function VariantTable({ variants, href, activeId, className }: { variants: VariantRow[]; href: (id: string | null) => string; activeId: string | null; className?: string }) {11 const rows = variants.slice(0, 8);12 if (rows.length < 2) return null;13 return (14 <div className={cn('card overflow-hidden', className)}>15 <div className="flex items-baseline justify-between border-b border-border px-3 py-2">16 <h2 className="text-[12px] font-semibold text-fg">By variant / grade</h2>17 <span className="text-[10px] text-subtle">{variants.length} tracked · click a row to focus</span>18 </div>19 <Table>20 <thead>21 <tr>22 <th className={th}>Variant</th>23 <th className={cn(th, 'text-right')}>RIV</th>24 <th className={cn(th, 'text-right')}>Range</th>25 <th className={th}>Confidence</th>26 <th className={cn(th, 'text-right')}>Latest sale</th>27 <th className={cn(th, 'text-right')}>Sales</th>28 <th className={cn(th, 'text-right')}>Listings</th>29 </tr>30 </thead>31 <tbody>32 {rows.map((v) => {33 const label = confidenceLabel(v.rivConfidence);34 return (35 <tr key={v.id} className={cn('hover:bg-sunken', activeId === v.id && 'bg-inset')}>36 <td className={cn(td, 'font-medium')}>37 <Link href={href(v.id)} scroll={false} className="hover:underline">38 {v.label}39 </Link>40 </td>41 <td className={cn(tdNum, 'font-semibold')}>{v.rivUsd === null ? <span className="text-subtle">—</span> : fmtMoney(v.rivUsd)}</td>42 <td className={cn(tdNum, 'text-muted')}>{v.rivLowUsd !== null && v.rivHighUsd !== null ? `${fmtMoney(v.rivLowUsd)} – ${fmtMoney(v.rivHighUsd)}` : <span className="text-subtle">—</span>}</td>43 <td className={td}>{v.rivUsd === null ? <span className="text-subtle">—</span> : <Badge tone={label === 'High' ? 'gain' : label === 'Medium' ? 'index' : label === 'Low' ? 'alert' : 'neutral'}>{label} · n={v.rivSampleSize}</Badge>}</td>44 <td className={tdNum}>45 {v.latestSaleUsd === null ? <span className="text-subtle">—</span> : fmtMoney(v.latestSaleUsd)}46 {v.latestSaleAt ? <span className="block text-[10px] text-subtle">{fmtRelative(v.latestSaleAt)}</span> : null}47 </td>48 <td className={tdNum}>{fmtNum(v.salesCount)}</td>49 <td className={tdNum}>{fmtNum(v.activeListings)}</td>50 </tr>51 );52 })}53 </tbody>54 </Table>55 </div>56 );57}58