shadimage
Awesome Cursor Rules
uibadgesource: ok · refreshed

Badge

Multi-variant React badge component for Tile UI.

npx shadcn add "https://react.tileui.zmorg.cn/r/badge.json"
free

No selection tags yet — empty means no evidence, not lack of support.

Dependencies

Bundle weight · light
ui-primitives@radix-ui/react-slot

Registry dependencies

@tile-ui/core@tile-ui/styles

Files3 · source cached 10/2/2026, 10:23:54 AM

packages/react/src/components/badge/badge.tsx
import React from 'react';
import { Slot } from '@radix-ui/react-slot';
import { getBadgeStyleKeys } from '../lib/core';
import type { BadgeBaseProps } from '../lib/core';
import styles from './badge.module.scss';

export interface BadgeProps extends React.HTMLAttributes<HTMLSpanElement>, BadgeBaseProps {}

const Badge = React.forwardRef<HTMLSpanElement, BadgeProps>(({ className = '', variant = 'default', asChild = false, children, ...props }, ref) => {
	const Comp = asChild ? Slot : 'span';
	const styleKeys = getBadgeStyleKeys(variant);

	const classes = [styles[styleKeys.base], styles[styleKeys.variant], className].filter(Boolean).join(' ');

	return (
		<Comp ref={ref} className={classes} {...props}>
			{children}
		</Comp>
	);
});

Badge.displayName = 'Badge';

export { Badge };
export default Badge;
packages/styles/scss/components/badge.module.scss
@use '../../../styles/variables/colors' as *;

.badge {
	display: inline-flex;
	width: fit-content;
	flex-shrink: 0;
	align-items: center;
	justify-content: center;
	gap: $spacing-1;
	overflow: hidden;
	border-radius: $radius-full;
	border: 1px solid transparent;
	padding: 0.125rem $spacing-2;
	font-size: $text-xs;
	font-weight: $font-medium;
	white-space: nowrap;
	transition:
		color $transition-fast,
		box-shadow $transition-fast;
	outline: none;

	&:focus-visible {
		border-color: $ring;
		box-shadow: 0 0 0 3px color-mix(in srgb, $ring 50%, transparent);
	}

	&[aria-invalid='true'] {
		border-color: $destructive;
		box-shadow: 0 0 0 3px color-mix(in srgb, $destructive 20%, transparent);
	}

	svg {
		pointer-events: none;
		width: 0.75rem;
		height: 0.75rem;
	}

	// 样式变体
	&.variantDefault {
		background-color: $primary;
		color: $primary-foreground;

		a:hover & {
			background-color: $primary-hover;
		}
	}

	&.variantSecondary {
		background-color: $secondary;
		color: $secondary-foreground;

		a:hover & {
			background-color: $secondary-hover;
		}
	}

	&.variantDestructive {
		background-color: $destructive;
		color: $destructive-foreground;

		a:hover & {
			background-color: $destructive-hover;
		}
	}

	&.variantOutline {
		border-color: $border;
		color: $foreground;

		a:hover & {
			background-color: $accent;
			color: $accent-foreground;
		}
	}

	&.variantGhost {
		a:hover & {
			background-color: $accent;
			color: $accent-foreground;
		}
	}

	&.variantLink {
		color: $primary;
		text-underline-offset: 4px;

		a:hover & {
			text-decoration: underline;
		}
	}
}
packages/react/src/components/badge/index.ts
export { Badge, type BadgeProps } from './badge';

More from Awesome Cursor Rules

Browse all components in this library →