diff --git a/apps/web/src/components/Layout/components/Header/styles.css.ts b/apps/web/src/components/Layout/components/Header/styles.css.ts index ece5219..3605ac1 100644 --- a/apps/web/src/components/Layout/components/Header/styles.css.ts +++ b/apps/web/src/components/Layout/components/Header/styles.css.ts @@ -5,7 +5,7 @@ import { style } from '@vanilla-extract/css'; export const header = style([ h1SemiBold, { - color: vars.color.archiveCoral, - backgroundColor: vars.color.archiveYellow, + color: vars.color.coral, + backgroundColor: vars.color.yellow, }, ]); diff --git a/packages/shared/components/src/Tag/index.tsx b/packages/shared/components/src/Tag/index.tsx new file mode 100644 index 0000000..00d8922 --- /dev/null +++ b/packages/shared/components/src/Tag/index.tsx @@ -0,0 +1,98 @@ +import { createContext, favolink, forwardRef } from '@favolink/system'; +import { classNames } from '@favolink/utils'; +import { type ComponentPropsWithoutRef } from 'react'; +import * as styles from './styles.css'; +import * as theme from './theme.css'; +import Icon, { type IconProps } from '../Icon'; + +const TAG_CLASSNAME = 'favolink-tag'; + +export type TagIconProps = IconProps; + +export const TagIcon = forwardRef( + function TagIcon(props, ref) { + const { children, ...restProps } = props; + + const { size } = useTagContext(); + + const iconSize: Record = { + small: { width: 14, height: 14 }, + medium: { width: 18, height: 18 }, + }; + + return ( + + {children} + + ); + }, +); + +export type TagLabelProps = ComponentPropsWithoutRef<'span'> & { + isAsIcon?: boolean; +}; + +export const TagLabel = forwardRef( + function TagText(props, ref) { + const { children, className, isAsIcon, ...restProps } = props; + + const { size } = useTagContext(); + + return ( + + {children} + + ); + }, +); + +type TagContextDefaultValue = { + size: styles.Size; +}; + +const [TagProvider, useTagContext] = createContext({ + size: 'small', +}); + +export type TagProps = ComponentPropsWithoutRef<'span'> & { + colorScheme?: styles.ColorScheme; + size?: styles.Size; +}; + +const Tag = forwardRef(function Tag(props, ref) { + const { + children, + className, + colorScheme = 'white', + size = 'small', + ...restProps + } = props; + + return ( + + {children} + + ); +}); + +export default Tag; diff --git a/packages/shared/components/src/Tag/styles.css.ts b/packages/shared/components/src/Tag/styles.css.ts new file mode 100644 index 0000000..52f8690 --- /dev/null +++ b/packages/shared/components/src/Tag/styles.css.ts @@ -0,0 +1,69 @@ +import { body3Medium, body4Medium } from '@favolink/styles/text.css'; +import { vars } from '@favolink/styles/theme.css'; +import { + type ComplexStyleRule, + style, + styleVariants, +} from '@vanilla-extract/css'; +import { type Color as TagColor, vars as tagVars } from './theme.css'; + +const border = style({ + borderRadius: 100, +}); + +const layout = style({ + display: 'inline-flex', + alignItems: 'center', + gap: 10, +}); + +export const base = style([border, layout]); + +export const size = styleVariants({ + small: [body4Medium, { padding: '4px 8px' }], + medium: [body3Medium, { padding: '8px 14px' }], +}); + +export type Size = keyof typeof size; + +export const colorScheme = styleVariants({ + black: createColorScheme('black'), + blue: createColorScheme('blue'), + brightGreen: createColorScheme('brightGreen'), + coral: createColorScheme('coral'), + mint: createColorScheme('mint'), + pink: createColorScheme('pink'), + purple: createColorScheme('purple'), + yellow: createColorScheme('yellow'), + white: { + ...createColorScheme('black'), + backgroundColor: 'white', + border: `1px solid ${vars.color.gray300}`, + }, +}); + +export type ColorScheme = keyof typeof colorScheme; + +const labelbase = style({ + display: 'flex', + justifyContent: 'center', + alignItems: 'center', +}); + +export const label = styleVariants({ + small: [labelbase, { minWidth: 14, minHeight: 14 }], + medium: [labelbase, { minWidth: 18, minHeight: 18 }], +}); + +export type Text = keyof typeof label; + +export const labelAsIcon = style({ + color: vars.color.gray400, +}); + +function createColorScheme(color: TagColor): ComplexStyleRule { + return { + color: tagVars.normal[color], + backgroundColor: tagVars.light[color], + }; +} diff --git a/packages/shared/components/src/Tag/theme.css.ts b/packages/shared/components/src/Tag/theme.css.ts new file mode 100644 index 0000000..9dce37b --- /dev/null +++ b/packages/shared/components/src/Tag/theme.css.ts @@ -0,0 +1,50 @@ +import { vars as globalVars } from '@favolink/styles/theme.css'; +import { createTheme, createThemeContract } from '@vanilla-extract/css'; + +export const vars = createThemeContract({ + normal: { + black: null, + blue: null, + brightGreen: null, + coral: null, + mint: null, + pink: null, + purple: null, + yellow: null, + }, + light: { + black: null, + blue: null, + brightGreen: null, + coral: null, + mint: null, + pink: null, + purple: null, + yellow: null, + }, +}); + +export type Color = keyof typeof vars.normal; + +export const color = createTheme(vars, { + normal: { + black: globalVars.color.gray700, + blue: '#2c84ec', + brightGreen: '#5db924', + coral: globalVars.color.coral, + mint: '#15c27a', + pink: '#ff4cbc', + purple: globalVars.color.purple, + yellow: '#ff8a35', + }, + light: { + black: '#aaacb615', + blue: '#6bafff20', + brightGreen: '#b4f78b40', + coral: '#f1766615', + mint: '#6af4ba30', + pink: '#ff8fb820', + purple: '#9570ff15', + yellow: '#ffe27940', + }, +}); diff --git a/packages/shared/components/src/index.ts b/packages/shared/components/src/index.ts index d8db8c9..14dc42c 100644 --- a/packages/shared/components/src/index.ts +++ b/packages/shared/components/src/index.ts @@ -25,5 +25,13 @@ export { } from './Modal'; export { default as Portal } from './Portal'; export { default as FavolinkProvider } from './Provider'; +export { + type TagProps, + default as Tag, + TagIcon, + type TagIconProps, + TagLabel, + type TagLabelProps, +} from './Tag'; export { default as Text, type TextProps } from './Text'; export { default as Toast } from './Toast'; diff --git a/packages/shared/styles/src/theme.css.ts b/packages/shared/styles/src/theme.css.ts index 99d3ca5..2abca3c 100644 --- a/packages/shared/styles/src/theme.css.ts +++ b/packages/shared/styles/src/theme.css.ts @@ -3,18 +3,20 @@ import { createGlobalThemeContract, } from '@vanilla-extract/css'; -const archiveColor = { - archiveBlack: '#aaacb6', - archiveBlue: '#9570ff', - archiveBrightGreen: '#b4f78b', - archiveCoral: '#f17666', - archiveYellow: '#ffe279', - archiveMint: '#6af4b4', - archivePink: '#ff8fb8', - archivePurple: '#9570ff', +export const archiveColor = { + black: '#aaacb6', + blue: '#9570ff', + brightGreen: '#b4f78b', + coral: '#f17666', + mint: '#6af4b4', + pink: '#ff8fb8', + purple: '#9570ff', + yellow: '#ffe279', }; -const grayColor = { +export type ArchiveColor = keyof typeof archiveColor; + +export const grayColor = { gray100: '#fafbfd', gray200: '#f4f6f9', gray300: '#edf0f4', @@ -28,24 +30,32 @@ const grayColor = { gray1100: '#1d2333', }; -const systemColor = { +export type GrayColor = keyof typeof grayColor; + +export const systemColor = { system100: '#ffd7d7', system200: '#ff8484', system300: '#ff4747', }; -const color = { ...archiveColor, ...grayColor, ...systemColor }; +export type SystemColor = keyof typeof systemColor; + +const color = { + ...archiveColor, + ...grayColor, + ...systemColor, +}; export const vars = createGlobalThemeContract({ color: { - archiveBlack: 'color-archive-black', - archiveBlue: 'color-archive-blue', - archiveBrightGreen: 'color-archive-bright-green', - archiveCoral: 'color-archive-coral', - archiveYellow: 'color-archive-yellow', - archiveMint: 'color-archive-mint', - archivePink: 'color-archive-pink', - archivePurple: 'color-archive-purple', + black: 'color-archive-black', + blue: 'color-archive-blue', + brightGreen: 'color-archive-bright-green', + coral: 'color-archive-coral', + yellow: 'color-archive-yellow', + mint: 'color-archive-mint', + pink: 'color-archive-pink', + purple: 'color-archive-purple', gray100: 'color-gray-100', gray200: 'color-gray-200', gray300: 'color-gray-300',