From 0377701a07f6ccde8b80b8a098fbc1323ccb741e Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Thu, 29 Jun 2023 11:23:56 +0200 Subject: [PATCH 1/8] WIP --- .../InteractionTag/useInteractionTag.tsx | 2 +- .../useInteractionTagStyles.styles.ts | 164 ++++++++++++++---- .../src/components/Tag/Tag.types.ts | 2 +- .../react-tags/src/components/Tag/useTag.tsx | 2 +- .../src/components/Tag/useTagStyles.styles.ts | 73 +++++++- .../InteractionTagAppearance.stories.tsx | 38 ++++ .../stories/InteractionTag/index.stories.tsx | 1 + .../stories/Tag/TagAppearance.stories.tsx | 38 ++++ .../react-tags/stories/Tag/index.stories.tsx | 1 + 9 files changed, 285 insertions(+), 36 deletions(-) create mode 100644 packages/react-components/react-tags/stories/InteractionTag/InteractionTagAppearance.stories.tsx create mode 100644 packages/react-components/react-tags/stories/Tag/TagAppearance.stories.tsx diff --git a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTag.tsx b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTag.tsx index 193b60e030285..4da27da00f3e4 100644 --- a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTag.tsx +++ b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTag.tsx @@ -36,7 +36,7 @@ export const useInteractionTag_unstable = ( const id = useId('fui-Tag', props.id); const { - appearance = 'filled-lighter', + appearance = 'filled', disabled = false, dismissible = contextDismissible, shape = 'rounded', diff --git a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts index b7dddee849adb..c8737c0210475 100644 --- a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts @@ -30,10 +30,19 @@ const useRootStyles = makeStyles({ alignItems: 'center', boxSizing: 'border-box', width: 'fit-content', + }, + filled: { backgroundColor: tokens.colorNeutralBackground3, color: tokens.colorNeutralForeground2, - ...shorthands.border(tokens.strokeWidthThin, 'solid', tokens.colorTransparentStroke), + }, + outline: { + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForeground2, + }, + brand: { + backgroundColor: tokens.colorBrandBackground2, + color: tokens.colorBrandForeground2, }, rounded: shorthands.borderRadius(tokens.borderRadiusMedium), @@ -50,6 +59,24 @@ const useRootStyles = makeStyles({ }, }); +const useRootDisabledStyles = makeStyles({ + filled: { + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + }, + outline: { + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorNeutralStrokeDisabled), + }, + brand: { + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + }, +}); + const useContentButtonStyles = makeStyles({ base: { // TODO use makeResetStyle when styles are settled @@ -71,27 +98,58 @@ const useContentButtonStyles = makeStyles({ "media secondary" `, + ...shorthands.border(tokens.strokeWidthThin, 'solid', tokens.colorTransparentStroke), + ...createCustomFocusIndicatorStyle( + { + ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), + zIndex: 1, + }, + { enableOutline: true }, + ), + }, + + filled: { ':hover': { cursor: 'pointer', + backgroundColor: tokens.colorNeutralBackground3Hover, + color: tokens.colorNeutralForeground2Hover, + }, + ':hover:active': { + backgroundColor: tokens.colorNeutralBackground3Pressed, + color: tokens.colorNeutralForeground2Pressed, }, + // TODO ':focus' - design have it filled }, - - rounded: createCustomFocusIndicatorStyle( - { - ...shorthands.borderRadius(tokens.borderRadiusMedium), - ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), - zIndex: 1, + outline: { + ...shorthands.borderColor(tokens.colorNeutralStroke1), + ':hover': { + cursor: 'pointer', + backgroundColor: tokens.colorSubtleBackgroundHover, + color: tokens.colorNeutralForeground2Hover, + }, + ':hover:active': { + backgroundColor: tokens.colorSubtleBackgroundPressed, + color: tokens.colorNeutralForeground2Pressed, }, - { enableOutline: true }, - ), - circular: createCustomFocusIndicatorStyle( - { - ...shorthands.borderRadius(tokens.borderRadiusCircular), - ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), - zIndex: 1, + }, + brand: { + ':hover': { + cursor: 'pointer', + backgroundColor: tokens.colorBrandBackground2Hover, + color: tokens.colorBrandForeground2Hover, }, - { enableOutline: true }, - ), + ':hover:active': { + backgroundColor: tokens.colorBrandBackground2Pressed, + color: tokens.colorBrandForeground2Pressed, + }, + }, + + disabled: { + cursor: 'not-allowed', + }, + + rounded: shorthands.borderRadius(tokens.borderRadiusMedium), + circular: shorthands.borderRadius(tokens.borderRadiusCircular), medium: { paddingRight: '7px', @@ -121,10 +179,15 @@ const useContentButtonWithoutMediaStyles = makeStyles({ * Styles for content slot when InteractionTag has dismiss button */ const useDismissibleContentButtonStyles = makeStyles({ - base: createCustomFocusIndicatorStyle({ + base: { borderTopRightRadius: tokens.borderRadiusNone, borderBottomRightRadius: tokens.borderRadiusNone, - }), + borderRightStyle: 'none', + ...createCustomFocusIndicatorStyle({ + borderTopRightRadius: tokens.borderRadiusNone, + borderBottomRightRadius: tokens.borderRadiusNone, + }), + }, medium: { paddingRight: tokens.spacingHorizontalS, }, @@ -151,30 +214,67 @@ const useDismissButtonStyles = makeStyles({ height: '100%', alignItems: 'center', + ...createCustomFocusIndicatorStyle(shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), { + enableOutline: true, + }), + + ...shorthands.border(tokens.strokeWidthThin, 'solid', tokens.colorTransparentStroke), + // divider: - ...shorthands.borderLeft(tokens.strokeWidthThin, 'solid', tokens.colorNeutralStroke1), + borderLeftColor: tokens.colorNeutralStroke1, borderTopLeftRadius: tokens.borderRadiusNone, borderBottomLeftRadius: tokens.borderRadiusNone, + }, + filled: { + ':hover': { + cursor: 'pointer', + backgroundColor: tokens.colorNeutralBackground3Hover, + color: tokens.colorNeutralForeground2BrandHover, + }, + ':hover:active': { + backgroundColor: tokens.colorNeutralBackground3Pressed, + color: tokens.colorNeutralForeground2BrandPressed, + }, + }, + outline: { + ...shorthands.borderColor(tokens.colorNeutralStroke1), + ':hover': { + cursor: 'pointer', + backgroundColor: tokens.colorSubtleBackgroundHover, + color: tokens.colorNeutralForeground2BrandHover, + }, + ':hover:active': { + backgroundColor: tokens.colorSubtleBackgroundPressed, + color: tokens.colorNeutralForeground2BrandPressed, + }, + }, + brand: { + borderLeftColor: tokens.colorBrandStroke2, ':hover': { cursor: 'pointer', + backgroundColor: tokens.colorBrandBackground2Hover, + color: tokens.colorBrandForeground2Hover, + }, + ':hover:active': { + backgroundColor: tokens.colorBrandBackground2Pressed, + color: tokens.colorBrandForeground2Pressed, }, }, - rounded: createCustomFocusIndicatorStyle({ - ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), - borderTopLeftRadius: tokens.borderRadiusNone, - borderBottomLeftRadius: tokens.borderRadiusNone, + disabled: { + cursor: 'not-allowed', + borderLeftColor: tokens.colorNeutralStrokeDisabled, + }, + + rounded: { borderTopRightRadius: tokens.borderRadiusMedium, borderBottomRightRadius: tokens.borderRadiusMedium, - }), - circular: createCustomFocusIndicatorStyle({ - ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), - borderTopLeftRadius: tokens.borderRadiusNone, - borderBottomLeftRadius: tokens.borderRadiusNone, + }, + circular: { borderTopRightRadius: tokens.borderRadiusCircular, borderBottomRightRadius: tokens.borderRadiusCircular, - }), + }, medium: { fontSize: mediumIconSize, @@ -198,6 +298,7 @@ const useDismissButtonStyles = makeStyles({ */ export const useInteractionTagStyles_unstable = (state: InteractionTagState): InteractionTagState => { const rootStyles = useRootStyles(); + const rootDisabledStyles = useRootDisabledStyles(); const contentButtonStyles = useContentButtonStyles(); const contentButtonWithoutMediaStyles = useContentButtonWithoutMediaStyles(); @@ -209,11 +310,12 @@ export const useInteractionTagStyles_unstable = (state: InteractionTagState): In const secondaryTextStyles = useSecondaryTextStyles(); const dismissButtonStyles = useDismissButtonStyles(); - const { shape, size } = state; + const { shape, size, appearance } = state; state.root.className = mergeClasses( interactionTagClassNames.root, rootStyles.base, + state.disabled ? rootDisabledStyles[appearance] : rootStyles[appearance], rootStyles[shape], rootStyles[size], state.root.className, @@ -224,6 +326,7 @@ export const useInteractionTagStyles_unstable = (state: InteractionTagState): In interactionTagClassNames.content, contentButtonStyles.base, + state.disabled ? contentButtonStyles.disabled : contentButtonStyles[appearance], contentButtonStyles[shape], contentButtonStyles[size], @@ -274,6 +377,7 @@ export const useInteractionTagStyles_unstable = (state: InteractionTagState): In state.dismissButton.className = mergeClasses( interactionTagClassNames.dismissButton, dismissButtonStyles.base, + state.disabled ? dismissButtonStyles.disabled : dismissButtonStyles[appearance], dismissButtonStyles[shape], dismissButtonStyles[size], state.dismissButton.className, diff --git a/packages/react-components/react-tags/src/components/Tag/Tag.types.ts b/packages/react-components/react-tags/src/components/Tag/Tag.types.ts index 2dd7710c60367..b5a32a318e1f0 100644 --- a/packages/react-components/react-tags/src/components/Tag/Tag.types.ts +++ b/packages/react-components/react-tags/src/components/Tag/Tag.types.ts @@ -37,7 +37,7 @@ export type TagSlots = { * Tag Props */ export type TagProps = ComponentProps> & { - appearance?: 'filled-darker' | 'filled-lighter' | 'tint' | 'outline'; + appearance?: 'filled' | 'outline' | 'brand'; disabled?: boolean; dismissible?: boolean; shape?: 'rounded' | 'circular'; diff --git a/packages/react-components/react-tags/src/components/Tag/useTag.tsx b/packages/react-components/react-tags/src/components/Tag/useTag.tsx index 57d7727b5b24c..3dd742de4d0c3 100644 --- a/packages/react-components/react-tags/src/components/Tag/useTag.tsx +++ b/packages/react-components/react-tags/src/components/Tag/useTag.tsx @@ -33,7 +33,7 @@ export const useTag_unstable = (props: TagProps, ref: React.Ref): T const id = useId('fui-Tag', props.id); const { - appearance = 'filled-lighter', + appearance = 'filled', disabled = false, dismissible = contextDismissible, shape = 'rounded', diff --git a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts index 66214279b8047..c7e727b71b93d 100644 --- a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts @@ -42,12 +42,54 @@ const useRootStyles = makeStyles({ `, boxSizing: 'border-box', width: 'fit-content', - backgroundColor: tokens.colorNeutralBackground3, - color: tokens.colorNeutralForeground2, + ...shorthands.border(tokens.strokeWidthThin, 'solid', tokens.colorTransparentStroke), + }, + filled: { + backgroundColor: tokens.colorNeutralBackground3, + color: tokens.colorNeutralForeground2, ':hover': { cursor: 'pointer', + [`& .${tagClassNames.dismissIcon}`]: { + color: tokens.colorNeutralForeground2BrandHover, // TODO + }, + }, + ':hover:active': { + [`& .${tagClassNames.dismissIcon}`]: { + color: tokens.colorNeutralForeground2BrandPressed, // TODO + }, + }, + }, + outline: { + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForeground2, + ...shorthands.borderColor(tokens.colorNeutralStroke1), + ':hover': { + cursor: 'pointer', + [`& .${tagClassNames.dismissIcon}`]: { + color: tokens.colorNeutralForeground2BrandHover, // TODO + }, + }, + ':hover:active': { + [`& .${tagClassNames.dismissIcon}`]: { + color: tokens.colorNeutralForeground2BrandPressed, // TODO + }, + }, + }, + brand: { + backgroundColor: tokens.colorBrandBackground2, + color: tokens.colorBrandForeground2, + ':hover': { + cursor: 'pointer', + [`& .${tagClassNames.dismissIcon}`]: { + color: tokens.colorNeutralForeground2BrandHover, // TODO + }, + }, + ':hover:active': { + [`& .${tagClassNames.dismissIcon}`]: { + color: tokens.colorNeutralForeground2BrandPressed, // TODO + }, }, }, @@ -82,6 +124,28 @@ const useRootStyles = makeStyles({ height: '20px', }, }); + +const useRootDisabledStyles = makeStyles({ + filled: { + cursor: 'not-allowed', + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + }, + outline: { + cursor: 'not-allowed', + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorNeutralStrokeDisabled), + }, + brand: { + cursor: 'not-allowed', + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + }, +}); + /** * Styles for root slot when Tag is without leading media/icon */ @@ -220,6 +284,7 @@ export const useSecondaryTextStyles = makeStyles({ */ export const useTagStyles_unstable = (state: TagState): TagState => { const rootStyles = useRootStyles(); + const rootDisabledStyles = useRootDisabledStyles(); const rootWithoutMediaStyles = useRootWithoutMediaStyles(); const rootWithoutDismissStyles = useRootWithoutDismissStyles(); @@ -229,12 +294,14 @@ export const useTagStyles_unstable = (state: TagState): TagState => { const primaryTextStyles = usePrimaryTextStyles(); const secondaryTextStyles = useSecondaryTextStyles(); - const { shape, size } = state; + const { shape, size, appearance } = state; state.root.className = mergeClasses( tagClassNames.root, rootStyles.base, + + state.disabled ? rootDisabledStyles[appearance] : rootStyles[appearance], rootStyles[shape], rootStyles[size], diff --git a/packages/react-components/react-tags/stories/InteractionTag/InteractionTagAppearance.stories.tsx b/packages/react-components/react-tags/stories/InteractionTag/InteractionTagAppearance.stories.tsx new file mode 100644 index 0000000000000..d8f2e6c05289c --- /dev/null +++ b/packages/react-components/react-tags/stories/InteractionTag/InteractionTagAppearance.stories.tsx @@ -0,0 +1,38 @@ +import * as React from 'react'; +import { makeStyles } from '@fluentui/react-components'; +import { InteractionTag } from '@fluentui/react-tags'; +import { bundleIcon, CalendarMonthFilled, CalendarMonthRegular } from '@fluentui/react-icons'; + +const CalendarMonth = bundleIcon(CalendarMonthFilled, CalendarMonthRegular); + +const useContainerStyles = makeStyles({ + container: { + columnGap: '10px', + display: 'flex', + }, +}); +export const Appearance = () => { + const styles = useContainerStyles(); + return ( +
+ } dismissible> + filled + + } dismissible> + outline + + } dismissible> + brand + +
+ ); +}; + +Appearance.storyName = 'Appearance'; +Appearance.parameters = { + docs: { + description: { + story: 'An InteractionTag can have a `filled`, `outline` or `brand` appearance. The default is `filled`.', + }, + }, +}; diff --git a/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx b/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx index a66cd8dbbf541..deaee8abc7cae 100644 --- a/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx +++ b/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx @@ -10,6 +10,7 @@ export { SecondaryText } from './InteractionTagSecondaryText.stories'; export { Dismiss } from './InteractionTagDismiss.stories'; export { Shape } from './InteractionTagShape.stories'; export { Size } from './InteractionTagSize.stories'; +export { Appearance } from './InteractionTagAppearance.stories'; export default { title: 'Preview Components/Tag/InteractionTag', diff --git a/packages/react-components/react-tags/stories/Tag/TagAppearance.stories.tsx b/packages/react-components/react-tags/stories/Tag/TagAppearance.stories.tsx new file mode 100644 index 0000000000000..6ef5d530f3e32 --- /dev/null +++ b/packages/react-components/react-tags/stories/Tag/TagAppearance.stories.tsx @@ -0,0 +1,38 @@ +import * as React from 'react'; +import { makeStyles } from '@fluentui/react-components'; +import { Tag } from '@fluentui/react-tags'; +import { bundleIcon, CalendarMonthFilled, CalendarMonthRegular } from '@fluentui/react-icons'; + +const CalendarMonth = bundleIcon(CalendarMonthFilled, CalendarMonthRegular); + +const useContainerStyles = makeStyles({ + container: { + columnGap: '10px', + display: 'flex', + }, +}); +export const Appearance = () => { + const styles = useContainerStyles(); + return ( +
+ } dismissible> + filled + + } dismissible> + outline + + } dismissible> + brand + +
+ ); +}; + +Appearance.storyName = 'Appearance'; +Appearance.parameters = { + docs: { + description: { + story: 'A tag can have a `filled`, `outline` or `brand` appearance. The default is `filled`.', + }, + }, +}; diff --git a/packages/react-components/react-tags/stories/Tag/index.stories.tsx b/packages/react-components/react-tags/stories/Tag/index.stories.tsx index b6b85183b5b5b..9ffe47d00814d 100644 --- a/packages/react-components/react-tags/stories/Tag/index.stories.tsx +++ b/packages/react-components/react-tags/stories/Tag/index.stories.tsx @@ -10,6 +10,7 @@ export { SecondaryText } from './TagSecondaryText.stories'; export { Dismiss } from './TagDismiss.stories'; export { Shape } from './TagShape.stories'; export { Size } from './TagSize.stories'; +export { Appearance } from './TagAppearance.stories'; export default { title: 'Preview Components/Tag/Tag', From 74f992e9c883fc771647444be8e122e7d8d3718c Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Thu, 29 Jun 2023 11:41:22 +0200 Subject: [PATCH 2/8] disabled --- .../useInteractionTagStyles.styles.ts | 108 ++++++++++-------- .../InteractionTagDisabled.stories.tsx | 44 +++++++ .../stories/InteractionTag/index.stories.tsx | 1 + .../stories/Tag/TagDisabled.stories.tsx | 38 ++++++ .../react-tags/stories/Tag/index.stories.tsx | 1 + 5 files changed, 146 insertions(+), 46 deletions(-) create mode 100644 packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx create mode 100644 packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx diff --git a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts index c8737c0210475..da5bae7efe007 100644 --- a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts @@ -32,19 +32,6 @@ const useRootStyles = makeStyles({ width: 'fit-content', }, - filled: { - backgroundColor: tokens.colorNeutralBackground3, - color: tokens.colorNeutralForeground2, - }, - outline: { - backgroundColor: tokens.colorSubtleBackground, - color: tokens.colorNeutralForeground2, - }, - brand: { - backgroundColor: tokens.colorBrandBackground2, - color: tokens.colorBrandForeground2, - }, - rounded: shorthands.borderRadius(tokens.borderRadiusMedium), circular: shorthands.borderRadius(tokens.borderRadiusCircular), @@ -59,24 +46,6 @@ const useRootStyles = makeStyles({ }, }); -const useRootDisabledStyles = makeStyles({ - filled: { - backgroundColor: tokens.colorNeutralBackgroundDisabled, - color: tokens.colorNeutralForegroundDisabled, - ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), - }, - outline: { - backgroundColor: tokens.colorSubtleBackground, - color: tokens.colorNeutralForegroundDisabled, - ...shorthands.borderColor(tokens.colorNeutralStrokeDisabled), - }, - brand: { - backgroundColor: tokens.colorNeutralBackgroundDisabled, - color: tokens.colorNeutralForegroundDisabled, - ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), - }, -}); - const useContentButtonStyles = makeStyles({ base: { // TODO use makeResetStyle when styles are settled @@ -109,6 +78,8 @@ const useContentButtonStyles = makeStyles({ }, filled: { + backgroundColor: tokens.colorNeutralBackground3, + color: tokens.colorNeutralForeground2, ':hover': { cursor: 'pointer', backgroundColor: tokens.colorNeutralBackground3Hover, @@ -121,6 +92,8 @@ const useContentButtonStyles = makeStyles({ // TODO ':focus' - design have it filled }, outline: { + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForeground2, ...shorthands.borderColor(tokens.colorNeutralStroke1), ':hover': { cursor: 'pointer', @@ -133,6 +106,8 @@ const useContentButtonStyles = makeStyles({ }, }, brand: { + backgroundColor: tokens.colorBrandBackground2, + color: tokens.colorBrandForeground2, ':hover': { cursor: 'pointer', backgroundColor: tokens.colorBrandBackground2Hover, @@ -144,10 +119,6 @@ const useContentButtonStyles = makeStyles({ }, }, - disabled: { - cursor: 'not-allowed', - }, - rounded: shorthands.borderRadius(tokens.borderRadiusMedium), circular: shorthands.borderRadius(tokens.borderRadiusCircular), @@ -161,6 +132,27 @@ const useContentButtonStyles = makeStyles({ paddingRight: '5px', }, }); +const useContentButtonDisabledStyles = makeStyles({ + filled: { + cursor: 'not-allowed', + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + }, + outline: { + cursor: 'not-allowed', + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorNeutralStrokeDisabled), + }, + brand: { + cursor: 'not-allowed', + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + }, +}); + /** * Styles for content slot when InteractionTag is without leading media/icon */ @@ -227,6 +219,8 @@ const useDismissButtonStyles = makeStyles({ }, filled: { + backgroundColor: tokens.colorNeutralBackground3, + color: tokens.colorNeutralForeground2, ':hover': { cursor: 'pointer', backgroundColor: tokens.colorNeutralBackground3Hover, @@ -238,6 +232,8 @@ const useDismissButtonStyles = makeStyles({ }, }, outline: { + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForeground2, ...shorthands.borderColor(tokens.colorNeutralStroke1), ':hover': { cursor: 'pointer', @@ -250,7 +246,9 @@ const useDismissButtonStyles = makeStyles({ }, }, brand: { - borderLeftColor: tokens.colorBrandStroke2, + backgroundColor: tokens.colorBrandBackground2, + color: tokens.colorBrandForeground2, + borderLeftColor: tokens.colorBrandStroke2, // divider ':hover': { cursor: 'pointer', backgroundColor: tokens.colorBrandBackground2Hover, @@ -262,11 +260,6 @@ const useDismissButtonStyles = makeStyles({ }, }, - disabled: { - cursor: 'not-allowed', - borderLeftColor: tokens.colorNeutralStrokeDisabled, - }, - rounded: { borderTopRightRadius: tokens.borderRadiusMedium, borderBottomRightRadius: tokens.borderRadiusMedium, @@ -292,30 +285,53 @@ const useDismissButtonStyles = makeStyles({ paddingRight: '5px', }, }); +const useDismissButtonDisabledStyles = makeStyles({ + filled: { + cursor: 'not-allowed', + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + borderLeftColor: tokens.colorNeutralStrokeDisabled, // divider + }, + outline: { + cursor: 'not-allowed', + backgroundColor: tokens.colorSubtleBackground, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorNeutralStrokeDisabled), + }, + brand: { + cursor: 'not-allowed', + backgroundColor: tokens.colorNeutralBackgroundDisabled, + color: tokens.colorNeutralForegroundDisabled, + ...shorthands.borderColor(tokens.colorTransparentStrokeDisabled), + borderLeftColor: tokens.colorNeutralStrokeDisabled, // divider + }, +}); /** * Apply styling to the InteractionTag slots based on the state */ export const useInteractionTagStyles_unstable = (state: InteractionTagState): InteractionTagState => { const rootStyles = useRootStyles(); - const rootDisabledStyles = useRootDisabledStyles(); const contentButtonStyles = useContentButtonStyles(); + const contentButtonDisabledStyles = useContentButtonDisabledStyles(); const contentButtonWithoutMediaStyles = useContentButtonWithoutMediaStyles(); const dismissibleContentButtonStyles = useDismissibleContentButtonStyles(); + const dismissButtonStyles = useDismissButtonStyles(); + const dismissButtonDisabledStyles = useDismissButtonDisabledStyles(); + const iconStyles = useIconStyles(); const mediaStyles = useMediaStyles(); const primaryTextStyles = usePrimaryTextStyles(); const secondaryTextStyles = useSecondaryTextStyles(); - const dismissButtonStyles = useDismissButtonStyles(); const { shape, size, appearance } = state; state.root.className = mergeClasses( interactionTagClassNames.root, rootStyles.base, - state.disabled ? rootDisabledStyles[appearance] : rootStyles[appearance], rootStyles[shape], rootStyles[size], state.root.className, @@ -326,7 +342,7 @@ export const useInteractionTagStyles_unstable = (state: InteractionTagState): In interactionTagClassNames.content, contentButtonStyles.base, - state.disabled ? contentButtonStyles.disabled : contentButtonStyles[appearance], + state.disabled ? contentButtonDisabledStyles[appearance] : contentButtonStyles[appearance], contentButtonStyles[shape], contentButtonStyles[size], @@ -377,7 +393,7 @@ export const useInteractionTagStyles_unstable = (state: InteractionTagState): In state.dismissButton.className = mergeClasses( interactionTagClassNames.dismissButton, dismissButtonStyles.base, - state.disabled ? dismissButtonStyles.disabled : dismissButtonStyles[appearance], + state.disabled ? dismissButtonDisabledStyles[appearance] : dismissButtonStyles[appearance], dismissButtonStyles[shape], dismissButtonStyles[size], state.dismissButton.className, diff --git a/packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx b/packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx new file mode 100644 index 0000000000000..168aeb9a41c25 --- /dev/null +++ b/packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx @@ -0,0 +1,44 @@ +import * as React from 'react'; +import { makeStyles } from '@fluentui/react-components'; +import { InteractionTag } from '@fluentui/react-tags'; +import { bundleIcon, CalendarMonthFilled, CalendarMonthRegular } from '@fluentui/react-icons'; + +const CalendarMonth = bundleIcon(CalendarMonthFilled, CalendarMonthRegular); + +const useContainerStyles = makeStyles({ + container: { + columnGap: '10px', + display: 'flex', + }, +}); +export const Disabled = () => { + const styles = useContainerStyles(); + return ( +
+ } dismissible> + disabled + + } + dismissible + > + disabled + + } dismissible> + disabled + +
+ ); +}; + +Disabled.storyName = 'Disabled'; +Disabled.parameters = { + docs: { + description: { + story: 'An InteractionTag can be `disabled`.', + }, + }, +}; diff --git a/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx b/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx index deaee8abc7cae..b253267a0812a 100644 --- a/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx +++ b/packages/react-components/react-tags/stories/InteractionTag/index.stories.tsx @@ -11,6 +11,7 @@ export { Dismiss } from './InteractionTagDismiss.stories'; export { Shape } from './InteractionTagShape.stories'; export { Size } from './InteractionTagSize.stories'; export { Appearance } from './InteractionTagAppearance.stories'; +export { Disabled } from './InteractionTagDisabled.stories'; export default { title: 'Preview Components/Tag/InteractionTag', diff --git a/packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx b/packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx new file mode 100644 index 0000000000000..e1380e52f6e7c --- /dev/null +++ b/packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx @@ -0,0 +1,38 @@ +import * as React from 'react'; +import { makeStyles } from '@fluentui/react-components'; +import { Tag } from '@fluentui/react-tags'; +import { bundleIcon, CalendarMonthFilled, CalendarMonthRegular } from '@fluentui/react-icons'; + +const CalendarMonth = bundleIcon(CalendarMonthFilled, CalendarMonthRegular); + +const useContainerStyles = makeStyles({ + container: { + columnGap: '10px', + display: 'flex', + }, +}); +export const Disabled = () => { + const styles = useContainerStyles(); + return ( +
+ } dismissible> + disabled + + } dismissible> + disabled + + } dismissible> + disabled + +
+ ); +}; + +Disabled.storyName = 'Disabled'; +Disabled.parameters = { + docs: { + description: { + story: 'A tag can be `disabled`.', + }, + }, +}; diff --git a/packages/react-components/react-tags/stories/Tag/index.stories.tsx b/packages/react-components/react-tags/stories/Tag/index.stories.tsx index 9ffe47d00814d..04fc2984760a3 100644 --- a/packages/react-components/react-tags/stories/Tag/index.stories.tsx +++ b/packages/react-components/react-tags/stories/Tag/index.stories.tsx @@ -11,6 +11,7 @@ export { Dismiss } from './TagDismiss.stories'; export { Shape } from './TagShape.stories'; export { Size } from './TagSize.stories'; export { Appearance } from './TagAppearance.stories'; +export { Disabled } from './TagDisabled.stories'; export default { title: 'Preview Components/Tag/Tag', From 684a193aec2a7e3c5b791818748de3c71ae9730e Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Thu, 29 Jun 2023 12:22:09 +0200 Subject: [PATCH 3/8] api --- packages/react-components/react-tags/etc/react-tags.api.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/react-components/react-tags/etc/react-tags.api.md b/packages/react-components/react-tags/etc/react-tags.api.md index 5aa9b3b037832..eb354f54bba38 100644 --- a/packages/react-components/react-tags/etc/react-tags.api.md +++ b/packages/react-components/react-tags/etc/react-tags.api.md @@ -74,7 +74,7 @@ export type TagGroupState = ComponentState & Requ // @public export type TagProps = ComponentProps> & { - appearance?: 'filled-darker' | 'filled-lighter' | 'tint' | 'outline'; + appearance?: 'filled' | 'outline' | 'brand'; disabled?: boolean; dismissible?: boolean; shape?: 'rounded' | 'circular'; From 677dfb990fc66ebaf13068b30f3ba12635dbd97b Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Thu, 29 Jun 2023 23:09:31 +0200 Subject: [PATCH 4/8] wip --- .../src/components/Tag/useTagStyles.styles.ts | 19 +++++++++++++------ 1 file changed, 13 insertions(+), 6 deletions(-) diff --git a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts index c7e727b71b93d..0bc6485b94e67 100644 --- a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts @@ -3,6 +3,7 @@ import type { TagSlots, TagState } from './Tag.types'; import type { SlotClassNames } from '@fluentui/react-utilities'; import { tokens, typographyStyles } from '@fluentui/react-theme'; import { createCustomFocusIndicatorStyle } from '@fluentui/react-tabster'; +import { iconFilledClassName, iconRegularClassName } from '@fluentui/react-icons'; export const tagClassNames: SlotClassNames = { root: 'fui-Tag', @@ -52,12 +53,12 @@ const useRootStyles = makeStyles({ ':hover': { cursor: 'pointer', [`& .${tagClassNames.dismissIcon}`]: { - color: tokens.colorNeutralForeground2BrandHover, // TODO + color: tokens.colorCompoundBrandForeground1Hover, }, }, ':hover:active': { [`& .${tagClassNames.dismissIcon}`]: { - color: tokens.colorNeutralForeground2BrandPressed, // TODO + color: tokens.colorCompoundBrandForeground1Pressed, }, }, }, @@ -67,13 +68,19 @@ const useRootStyles = makeStyles({ ...shorthands.borderColor(tokens.colorNeutralStroke1), ':hover': { cursor: 'pointer', + [`& .${iconFilledClassName}`]: { + display: 'inline', + }, + [`& .${iconRegularClassName}`]: { + display: 'none', + }, [`& .${tagClassNames.dismissIcon}`]: { - color: tokens.colorNeutralForeground2BrandHover, // TODO + color: tokens.colorCompoundBrandForeground1Hover, }, }, ':hover:active': { [`& .${tagClassNames.dismissIcon}`]: { - color: tokens.colorNeutralForeground2BrandPressed, // TODO + color: tokens.colorCompoundBrandForeground1Pressed, }, }, }, @@ -83,12 +90,12 @@ const useRootStyles = makeStyles({ ':hover': { cursor: 'pointer', [`& .${tagClassNames.dismissIcon}`]: { - color: tokens.colorNeutralForeground2BrandHover, // TODO + color: tokens.colorCompoundBrandForeground1Hover, }, }, ':hover:active': { [`& .${tagClassNames.dismissIcon}`]: { - color: tokens.colorNeutralForeground2BrandPressed, // TODO + color: tokens.colorCompoundBrandForeground1Pressed, }, }, }, From 4a7a94559f2403679e34d5d691e39431eb6c983e Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Mon, 10 Jul 2023 11:48:36 +0200 Subject: [PATCH 5/8] leave icon for later --- .../react-tags/src/components/Tag/useTagStyles.styles.ts | 7 ------- 1 file changed, 7 deletions(-) diff --git a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts index 0bc6485b94e67..39de36d5d3adc 100644 --- a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts @@ -3,7 +3,6 @@ import type { TagSlots, TagState } from './Tag.types'; import type { SlotClassNames } from '@fluentui/react-utilities'; import { tokens, typographyStyles } from '@fluentui/react-theme'; import { createCustomFocusIndicatorStyle } from '@fluentui/react-tabster'; -import { iconFilledClassName, iconRegularClassName } from '@fluentui/react-icons'; export const tagClassNames: SlotClassNames = { root: 'fui-Tag', @@ -68,12 +67,6 @@ const useRootStyles = makeStyles({ ...shorthands.borderColor(tokens.colorNeutralStroke1), ':hover': { cursor: 'pointer', - [`& .${iconFilledClassName}`]: { - display: 'inline', - }, - [`& .${iconRegularClassName}`]: { - display: 'none', - }, [`& .${tagClassNames.dismissIcon}`]: { color: tokens.colorCompoundBrandForeground1Hover, }, From 099e950605ddd88d6a76dcfd3de9330e22d3c703 Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Mon, 10 Jul 2023 11:53:55 +0200 Subject: [PATCH 6/8] clean --- .../components/InteractionTag/useInteractionTagStyles.styles.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts index da5bae7efe007..b05b8c3e07f9b 100644 --- a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts @@ -89,7 +89,6 @@ const useContentButtonStyles = makeStyles({ backgroundColor: tokens.colorNeutralBackground3Pressed, color: tokens.colorNeutralForeground2Pressed, }, - // TODO ':focus' - design have it filled }, outline: { backgroundColor: tokens.colorSubtleBackground, From 1ae1a59e50c9640254209a06eb44226fe43bd785 Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Mon, 10 Jul 2023 14:50:08 +0200 Subject: [PATCH 7/8] remove redundant description on disabled stories --- .../InteractionTag/InteractionTagDisabled.stories.tsx | 9 --------- .../react-tags/stories/Tag/TagDisabled.stories.tsx | 9 --------- 2 files changed, 18 deletions(-) diff --git a/packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx b/packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx index 168aeb9a41c25..64e4876efe91b 100644 --- a/packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx +++ b/packages/react-components/react-tags/stories/InteractionTag/InteractionTagDisabled.stories.tsx @@ -33,12 +33,3 @@ export const Disabled = () => { ); }; - -Disabled.storyName = 'Disabled'; -Disabled.parameters = { - docs: { - description: { - story: 'An InteractionTag can be `disabled`.', - }, - }, -}; diff --git a/packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx b/packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx index e1380e52f6e7c..f17b1446285f4 100644 --- a/packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx +++ b/packages/react-components/react-tags/stories/Tag/TagDisabled.stories.tsx @@ -27,12 +27,3 @@ export const Disabled = () => { ); }; - -Disabled.storyName = 'Disabled'; -Disabled.parameters = { - docs: { - description: { - story: 'A tag can be `disabled`.', - }, - }, -}; From b5d72b89fbeb024c2f9cef27bc3ae91e9f233657 Mon Sep 17 00:00:00 2001 From: YuanboXue-Amber Date: Mon, 10 Jul 2023 18:35:45 +0200 Subject: [PATCH 8/8] remove enableoutline --- .../useInteractionTagStyles.styles.ts | 15 +++++-------- .../src/components/Tag/useTagStyles.styles.ts | 22 +++++++------------ 2 files changed, 13 insertions(+), 24 deletions(-) diff --git a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts index b05b8c3e07f9b..e94380c6c120c 100644 --- a/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/InteractionTag/useInteractionTagStyles.styles.ts @@ -68,13 +68,10 @@ const useContentButtonStyles = makeStyles({ `, ...shorthands.border(tokens.strokeWidthThin, 'solid', tokens.colorTransparentStroke), - ...createCustomFocusIndicatorStyle( - { - ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), - zIndex: 1, - }, - { enableOutline: true }, - ), + ...createCustomFocusIndicatorStyle({ + ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), + zIndex: 1, + }), }, filled: { @@ -205,9 +202,7 @@ const useDismissButtonStyles = makeStyles({ height: '100%', alignItems: 'center', - ...createCustomFocusIndicatorStyle(shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), { - enableOutline: true, - }), + ...createCustomFocusIndicatorStyle(shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2)), ...shorthands.border(tokens.strokeWidthThin, 'solid', tokens.colorTransparentStroke), diff --git a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts index 39de36d5d3adc..90a276b7bfb01 100644 --- a/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts +++ b/packages/react-components/react-tags/src/components/Tag/useTagStyles.styles.ts @@ -95,23 +95,17 @@ const useRootStyles = makeStyles({ rounded: { ...shorthands.borderRadius(tokens.borderRadiusMedium), - ...createCustomFocusIndicatorStyle( - { - ...shorthands.borderRadius(tokens.borderRadiusMedium), - ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), - }, - { enableOutline: true }, - ), + ...createCustomFocusIndicatorStyle({ + ...shorthands.borderRadius(tokens.borderRadiusMedium), + ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), + }), }, circular: { ...shorthands.borderRadius(tokens.borderRadiusCircular), - ...createCustomFocusIndicatorStyle( - { - ...shorthands.borderRadius(tokens.borderRadiusCircular), - ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), - }, - { enableOutline: true }, - ), + ...createCustomFocusIndicatorStyle({ + ...shorthands.borderRadius(tokens.borderRadiusCircular), + ...shorthands.outline(tokens.strokeWidthThick, 'solid', tokens.colorStrokeFocus2), + }), }, medium: {