dify/web/app/components/base/tab-header/index.tsx
yyh af7d5e60b4
feat(ui): scaffold @langgenius/dify-ui and migrate design tokens (#35256)
Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com>
2026-04-15 13:11:20 +00:00

61 lines
1.6 KiB
TypeScript

'use client'
import type { FC } from 'react'
import { cn } from '@langgenius/dify-ui/cn'
import * as React from 'react'
type Item = {
id: string
name: string
isRight?: boolean
icon?: React.ReactNode
extra?: React.ReactNode
disabled?: boolean
}
export type ITabHeaderProps = {
items: Item[]
value: string
itemClassName?: string
itemWrapClassName?: string
activeItemClassName?: string
onChange: (value: string) => void
}
const TabHeader: FC<ITabHeaderProps> = ({
items,
value,
itemClassName,
itemWrapClassName,
activeItemClassName,
onChange,
}) => {
const renderItem = ({ id, name, icon, extra, disabled }: Item) => (
<div
key={id}
data-testid={`tab-header-item-${id}`}
className={cn(
'relative flex cursor-pointer items-center border-b-2 border-transparent pt-2.5 pb-2 system-md-semibold',
id === value ? cn('border-components-tab-active text-text-primary', activeItemClassName) : 'text-text-tertiary',
disabled && 'cursor-not-allowed opacity-30',
itemWrapClassName,
)}
onClick={() => !disabled && onChange(id)}
>
{icon || ''}
<div className={cn('ml-2', itemClassName)}>{name}</div>
{extra || ''}
</div>
)
return (
<div data-testid="tab-header" className="flex justify-between">
<div data-testid="tab-header-left" className="flex space-x-4">
{items.filter(item => !item.isRight).map(renderItem)}
</div>
<div data-testid="tab-header-right" className="flex space-x-4">
{items.filter(item => item.isRight).map(renderItem)}
</div>
</div>
)
}
export default React.memo(TabHeader)