feat(ui): improve table controls and analytics filters

This commit is contained in:
CaIon
2026-04-30 13:57:10 +08:00
parent 8bff691089
commit 8f3c41ae77
35 changed files with 858 additions and 472 deletions
@@ -14,6 +14,7 @@ import {
TableRow,
} from '@/components/ui/table'
import { CopyButton } from '@/components/copy-button'
import { GroupBadge } from '@/components/group-badge'
import { PublicLayout } from '@/components/layout'
import { DEFAULT_TOKEN_UNIT, QUOTA_TYPE_VALUES } from '../constants'
import { usePricingData } from '../hooks/use-pricing-data'
@@ -275,9 +276,7 @@ function AutoGroupChain(props: { model: PricingModel; autoGroups: string[] }) {
<span className='text-muted-foreground/40'></span>
{autoChain.map((g, idx) => (
<span key={g} className='flex items-center gap-1'>
<span className='bg-muted text-foreground rounded px-1.5 py-0.5 text-[11px] font-medium'>
{g}
</span>
<GroupBadge group={g} size='sm' />
{idx < autoChain.length - 1 && (
<span className='text-muted-foreground/40'></span>
)}
@@ -388,7 +387,9 @@ function GroupPricingSection(props: {
const ratio = groupRatio[group] || 1
return (
<TableRow key={group}>
<TableCell className='py-2.5 font-medium'>{group}</TableCell>
<TableCell className='py-2.5'>
<GroupBadge group={group} size='sm' />
</TableCell>
<TableCell className='text-muted-foreground py-2.5 font-mono text-xs'>
{ratio}x
</TableCell>
@@ -8,6 +8,7 @@ import {
TooltipTrigger,
} from '@/components/ui/tooltip'
import { DataTableColumnHeader } from '@/components/data-table/column-header'
import { GroupBadge } from '@/components/group-badge'
import { DEFAULT_TOKEN_UNIT, QUOTA_TYPE_VALUES } from '../constants'
import { parseTags } from '../lib/filters'
import { isTokenBasedModel } from '../lib/model-helpers'
@@ -49,6 +50,28 @@ function renderLimitedTags(
)
}
function renderLimitedGroupBadges(
groups: string[],
maxDisplay: number = 2
): React.ReactNode {
if (groups.length === 0)
return <span className='text-muted-foreground/50 text-xs'></span>
const displayed = groups.slice(0, maxDisplay)
const remaining = groups.length - maxDisplay
return (
<div className='flex max-w-full items-center gap-1 overflow-hidden'>
{displayed.map((group) => (
<GroupBadge key={group} group={group} size='sm' />
))}
{remaining > 0 && (
<span className='text-muted-foreground/50 text-xs'>+{remaining}</span>
)}
</div>
)
}
export function usePricingColumns(
options: PricingColumnsOptions = {}
): ColumnDef<PricingModel>[] {
@@ -312,11 +335,15 @@ export function usePricingColumns(
<TooltipProvider>
<Tooltip>
<TooltipTrigger asChild>
<div>{renderLimitedTags(groups, 2)}</div>
<div>{renderLimitedGroupBadges(groups, 2)}</div>
</TooltipTrigger>
{groups.length > 2 && (
<TooltipContent side='top' className='max-w-[280px] p-2'>
<span className='text-xs'>{groups.join(', ')}</span>
<div className='flex flex-wrap gap-1'>
{groups.map((group) => (
<GroupBadge key={group} group={group} size='sm' />
))}
</div>
</TooltipContent>
)}
</Tooltip>