From 5f1c55055b148baca1f6a6fb2931313df511d60e Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 7 Oct 2022 12:16:17 +0200 Subject: [PATCH 01/49] [POC] Add `createMD3Theme` creator v2 --- docs/pages/experiments/md3/index.js | 81 ++++ .../mui-material-next/src/Button/Button.d.ts | 31 +- .../mui-material-next/src/Button/Button.js | 405 +++++++----------- .../src/Button/Button.test.js | 59 +-- .../mui-material-next/src/Button/Ripple.js | 96 ----- .../src/Button/Ripple.test.js | 128 ------ .../src/Button/TouchRipple.d.ts | 32 -- .../src/Button/TouchRipple.js | 333 -------------- .../src/Button/TouchRipple.test.js | 270 ------------ .../src/Button/touchRippleClasses.ts | 36 -- .../styles/experimental_createMD3Theme.d.ts | 13 + .../src/styles/experimental_createMD3Theme.js | 147 +++++++ .../styles/experimental_extendMD3Theme.d.ts | 13 + .../src/styles/experimental_extendMD3Theme.js | 359 ++++++++++++++++ packages/mui-material/src/styles/index.d.ts | 4 + packages/mui-material/src/styles/index.js | 4 + .../src/styles/md3/createDarkColorScheme.js | 35 ++ .../src/styles/md3/createLightColorScheme.js | 35 ++ .../src/styles/md3/createMd3Palette.js | 76 ++++ .../mui-material/src/styles/md3/palette.js | 98 +++++ .../mui-material/src/styles/md3/states.js | 16 + .../mui-material/src/styles/md3/typeface.js | 11 + .../mui-material/src/styles/md3/typescale.js | 74 ++++ 23 files changed, 1129 insertions(+), 1227 deletions(-) create mode 100644 docs/pages/experiments/md3/index.js delete mode 100644 packages/mui-material-next/src/Button/Ripple.js delete mode 100644 packages/mui-material-next/src/Button/Ripple.test.js delete mode 100644 packages/mui-material-next/src/Button/TouchRipple.d.ts delete mode 100644 packages/mui-material-next/src/Button/TouchRipple.js delete mode 100644 packages/mui-material-next/src/Button/TouchRipple.test.js delete mode 100644 packages/mui-material-next/src/Button/touchRippleClasses.ts create mode 100644 packages/mui-material/src/styles/experimental_createMD3Theme.d.ts create mode 100644 packages/mui-material/src/styles/experimental_createMD3Theme.js create mode 100644 packages/mui-material/src/styles/experimental_extendMD3Theme.d.ts create mode 100644 packages/mui-material/src/styles/experimental_extendMD3Theme.js create mode 100644 packages/mui-material/src/styles/md3/createDarkColorScheme.js create mode 100644 packages/mui-material/src/styles/md3/createLightColorScheme.js create mode 100644 packages/mui-material/src/styles/md3/createMd3Palette.js create mode 100644 packages/mui-material/src/styles/md3/palette.js create mode 100644 packages/mui-material/src/styles/md3/states.js create mode 100644 packages/mui-material/src/styles/md3/typeface.js create mode 100644 packages/mui-material/src/styles/md3/typescale.js diff --git a/docs/pages/experiments/md3/index.js b/docs/pages/experiments/md3/index.js new file mode 100644 index 00000000000000..a6a5f9022b9ac5 --- /dev/null +++ b/docs/pages/experiments/md3/index.js @@ -0,0 +1,81 @@ +import * as React from 'react'; +import { + experimental_extendMD3Theme as extendMD3Theme, + Experimental_CssVarsProvider as CssVarsProvider, + Tooltip, + IconButton, + experimental_createMD3Theme as createMD3Theme, + ThemeProvider, + useColorScheme, + Stack, +} from '@mui/material'; +import { unstable_capitalize as capitalize } from 'packages/mui-utils'; +import { Button } from '@mui/material-next'; +import DarkIcon from '@mui/icons-material/DarkModeOutlined'; +import LightIcon from '@mui/icons-material/LightModeOutlined'; + +const ModeSwitcher = ({ setMode: setModeProp }) => { + const { mode, setMode } = useColorScheme(); + const [mounted, setMounted] = React.useState(false); + + React.useEffect(() => { + setMounted(true); + }, []); + + if (!mounted) { + return null; + } + + return ( + + { + if (mode === 'light') { + setMode('dark'); + setModeProp('dark'); + } else { + setMode('light'); + setModeProp('light'); + } + }} + > + {mode === 'light' ? : } + + + ); +}; + +const variants = ['elevated', 'filled', 'filledTonal', 'outlined', 'text']; +const DemoComponents = () => { + return ( + + {variants.map((variant) => ( + + ))} + + ); +}; + +const cssVarsTheme = extendMD3Theme(); + +const lightTheme = createMD3Theme(); +const darkTheme = createMD3Theme({ palette: { mode: 'dark' } }); + +export default function App() { + const [mode, setMode] = React.useState('light'); + return ( + + + +

Css variables - Material You theme

+ +
+ +

Theme provider - Material You theme

+ +
+
+ ); +} diff --git a/packages/mui-material-next/src/Button/Button.d.ts b/packages/mui-material-next/src/Button/Button.d.ts index 525e4586cd40b0..8453de636930e6 100644 --- a/packages/mui-material-next/src/Button/Button.d.ts +++ b/packages/mui-material-next/src/Button/Button.d.ts @@ -8,7 +8,6 @@ import { } from '@mui/types'; import { SxProps } from '@mui/system'; import { Theme } from '@mui/material'; -import { TouchRippleProps } from './TouchRipple'; import { ButtonClasses } from './buttonClasses'; export interface ButtonPropsVariantOverrides {} @@ -28,12 +27,6 @@ export interface ButtonTypeMap

{ * It exposes the `focusVisible()` action. */ action?: React.Ref; - /** - * If `true`, the ripples are centered. - * They won't start at the cursor interaction position. - * @default false - */ - centerRipple?: boolean; /** * The content of the component. */ @@ -60,24 +53,6 @@ export interface ButtonTypeMap

{ * @default false */ disableElevation?: boolean; - /** - * If `true`, the keyboard focus ripple is disabled. - * @default false - */ - disableFocusRipple?: boolean; - /** - * If `true`, the ripple effect is disabled. - * - * ⚠️ Without a ripple there is no styling for :focus-visible by default. Be sure - * to highlight the element by applying separate styles with the `.Mui-focusVisible` class. - * @default false - */ - disableRipple?: boolean; - /** - * If `true`, the touch ripple effect is disabled. - * @default false - */ - disableTouchRipple?: boolean; /** * Element placed after the children. */ @@ -129,16 +104,12 @@ export interface ButtonTypeMap

{ * @default 0 */ tabIndex?: NonNullable['tabIndex']>; - /** - * Props applied to the `TouchRipple` element. - */ - TouchRippleProps?: Partial; /** * The variant to use. * @default 'text' */ variant?: OverridableStringUnion< - 'text' | 'outlined' | 'contained', + 'text' | 'outlined' | 'filled' | 'filledTonal' | 'elevated', ButtonPropsVariantOverrides >; }; diff --git a/packages/mui-material-next/src/Button/Button.js b/packages/mui-material-next/src/Button/Button.js index 548c275982f863..a5e1e76b7f6989 100644 --- a/packages/mui-material-next/src/Button/Button.js +++ b/packages/mui-material-next/src/Button/Button.js @@ -11,8 +11,6 @@ import { useButton } from '@mui/base/ButtonUnstyled'; import composeClasses from '@mui/base/composeClasses'; import { useThemeProps, alpha } from '@mui/system'; import styled, { rootShouldForwardProp } from '@mui/material/styles/styled'; -import useTouchRipple from '@mui/material/useTouchRipple'; -import TouchRipple from './TouchRipple'; import buttonClasses, { getButtonUtilityClass } from './buttonClasses'; const useUtilityClasses = (styleProps) => { @@ -92,194 +90,175 @@ export const ButtonRoot = styled('button', { ]; }, })(({ theme, ownerState }) => ({ - display: 'inline-flex', - alignItems: 'center', - justifyContent: 'center', - position: 'relative', - boxSizing: 'border-box', - WebkitTapHighlightColor: 'transparent', - backgroundColor: 'transparent', // Reset default value - // We disable the focus ring for mouse, touch and keyboard users. - outline: 0, - border: 0, - margin: 0, // Remove the margin in Safari - cursor: 'pointer', - userSelect: 'none', - verticalAlign: 'middle', - MozAppearance: 'none', // Reset - WebkitAppearance: 'none', // Reset - textDecoration: 'none', - // So we take precedent over the style of a native element. - color: 'inherit', - '&::-moz-focus-inner': { - borderStyle: 'none', // Remove Firefox dotted outline. - }, - [`&.${buttonClasses.disabled}`]: { - pointerEvents: 'none', // Disable link interactions - cursor: 'default', - }, - '@media print': { - colorAdjust: 'exact', - }, - ...theme.typography.button, - minWidth: 64, - padding: '6px 16px', - borderRadius: theme.shape.borderRadius, - transition: theme.transitions.create( - ['background-color', 'box-shadow', 'border-color', 'color'], - { duration: theme.transitions.duration.short }, - ), - '&:hover': { - textDecoration: 'none', - backgroundColor: alpha(theme.palette.text.primary, theme.palette.action.hoverOpacity), - // Reset on touch devices, it doesn't add specificity - '@media (hover: none)': { - backgroundColor: 'transparent', + border: 'none', + outline: 'none', + padding: '10px 24px', + fontFamily: (theme.vars || theme).typescale.label.large.family, + fontWeight: (theme.vars || theme).typescale.label.large.weight, + borderRadius: (theme.vars || theme).shape.borderRadius, + // Filled varaint + ...(ownerState.variant === 'filled' && { + backgroundColor: (theme.vars || theme).palette.md3.colors.primary, + color: (theme.vars || theme).palette.md3.colors.onPrimary, + '&:hover': { + boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.primaryChannel + } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + 1 - theme.state.hover.stateLayerOpacity, + ), + }), + }, + '&:active': { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.primaryChannel + } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + 1 - theme.state.pressed.stateLayerOpacity, + ), + }), + }, + [`&.${buttonClasses.focusVisible}`]: { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.primaryChannel + } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + 1 - theme.state.focus.stateLayerOpacity, + ), + }), }, - ...(ownerState.variant === 'text' && - ownerState.color !== 'inherit' && { - backgroundColor: alpha( - theme.palette[ownerState.color].main, - theme.palette.action.hoverOpacity, - ), - // Reset on touch devices, it doesn't add specificity - '@media (hover: none)': { - backgroundColor: 'transparent', - }, - }), - ...(ownerState.variant === 'outlined' && - ownerState.color !== 'inherit' && { - border: `1px solid ${theme.palette[ownerState.color].main}`, - backgroundColor: alpha( - theme.palette[ownerState.color].main, - theme.palette.action.hoverOpacity, - ), - // Reset on touch devices, it doesn't add specificity - '@media (hover: none)': { - backgroundColor: 'transparent', - }, - }), - ...(ownerState.variant === 'contained' && { - backgroundColor: theme.palette.grey.A100, - boxShadow: theme.shadows[4], - // Reset on touch devices, it doesn't add specificity - '@media (hover: none)': { - boxShadow: theme.shadows[2], - backgroundColor: theme.palette.grey[300], - }, - }), - ...(ownerState.variant === 'contained' && - ownerState.color !== 'inherit' && { - backgroundColor: theme.palette[ownerState.color].dark, - // Reset on touch devices, it doesn't add specificity - '@media (hover: none)': { - backgroundColor: theme.palette[ownerState.color].main, - }, - }), - }, - '&:active': { - ...(ownerState.variant === 'contained' && { - boxShadow: theme.shadows[8], - }), - }, - [`&.${buttonClasses.focusVisible}`]: { - ...(ownerState.variant === 'contained' && { - boxShadow: theme.shadows[6], - }), - }, - [`&.${buttonClasses.disabled}`]: { - color: theme.palette.action.disabled, - ...(ownerState.variant === 'outlined' && { - border: `1px solid ${theme.palette.action.disabledBackground}`, - }), - ...(ownerState.variant === 'outlined' && - ownerState.color === 'secondary' && { - border: `1px solid ${theme.palette.action.disabled}`, - }), - ...(ownerState.variant === 'contained' && { - color: theme.palette.action.disabled, - boxShadow: theme.shadows[0], - backgroundColor: theme.palette.action.disabledBackground, - }), - }, - ...(ownerState.variant === 'text' && { - padding: '6px 8px', }), - ...(ownerState.variant === 'text' && - ownerState.color !== 'inherit' && { - color: theme.palette[ownerState.color].main, - }), - ...(ownerState.variant === 'outlined' && { - padding: '5px 15px', - border: `1px solid ${ - theme.palette.mode === 'light' ? 'rgba(0, 0, 0, 0.23)' : 'rgba(255, 255, 255, 0.23)' - }`, + // Filled tonal varitant + ...(ownerState.variant === 'filledTonal' && { + backgroundColor: (theme.vars || theme).palette.md3.colors.secondaryContainer, + color: (theme.vars || theme).palette.md3.colors.onSecondaryContainer, + '&:hover': { + boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.secondaryContainerChannel + } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.state.hover.stateLayerOpacity, + ), + }), + }, + '&:active': { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.secondaryContainerChannel + } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.state.pressed.stateLayerOpacity, + ), + }), + }, + [`&.${buttonClasses.focusVisible}`]: { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.secondaryContainerChannel + } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.state.focus.stateLayerOpacity, + ), + }), + }, }), - ...(ownerState.variant === 'outlined' && - ownerState.color !== 'inherit' && { - color: theme.palette[ownerState.color].main, - border: `1px solid ${alpha(theme.palette[ownerState.color].main, 0.5)}`, - }), - ...(ownerState.variant === 'contained' && { - color: theme.palette.getContrastText(theme.palette.grey[300]), - backgroundColor: theme.palette.grey[300], - boxShadow: theme.shadows[2], + // Outlined varaiant + ...(ownerState.variant === 'outlined' && { + border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, + color: (theme.vars || theme).palette.md3.colors.primary, + background: 'transparent', }), - ...(ownerState.variant === 'contained' && - ownerState.color !== 'inherit' && { - color: theme.palette[ownerState.color].contrastText, - backgroundColor: theme.palette[ownerState.color].main, - }), - ...(ownerState.color === 'inherit' && { - color: 'inherit', - borderColor: 'currentColor', + // Elevated variant + ...(ownerState.variant === 'elevated' && { + background: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${ + (theme.vars || theme).palette.md3.colors.surface + }`, + color: (theme.vars || theme).palette.md3.colors.primary, + boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', // elevation.lightingColor.1 }), - ...(ownerState.size === 'small' && - ownerState.variant === 'text' && { - padding: '4px 5px', - fontSize: theme.typography.pxToRem(13), - }), - ...(ownerState.size === 'large' && - ownerState.variant === 'text' && { - padding: '8px 11px', - fontSize: theme.typography.pxToRem(15), - }), - ...(ownerState.size === 'small' && - ownerState.variant === 'outlined' && { - padding: '3px 9px', - fontSize: theme.typography.pxToRem(13), - }), - ...(ownerState.size === 'large' && - ownerState.variant === 'outlined' && { - padding: '7px 21px', - fontSize: theme.typography.pxToRem(15), - }), - ...(ownerState.size === 'small' && - ownerState.variant === 'contained' && { - padding: '4px 10px', - fontSize: theme.typography.pxToRem(13), - }), - ...(ownerState.size === 'large' && - ownerState.variant === 'contained' && { - padding: '8px 22px', - fontSize: theme.typography.pxToRem(15), - }), - ...(ownerState.fullWidth && { - width: '100%', + // Text variant + ...(ownerState.variant === 'text' && { + color: (theme.vars || theme).palette.md3.colors.primary, + background: 'transparent', }), - ...(ownerState.disableElevation && { - boxShadow: 'none', + // State styles for text, outlined, elevated variants + ...((ownerState.variant === 'text' || + ownerState.variant === 'outlined' || + ownerState.variant === 'elevated') && { '&:hover': { - boxShadow: 'none', - }, - [`&.${buttonClasses.focusVisible}`]: { - boxShadow: 'none', + ...(ownerState.variant === 'elevated' && { + boxShadow: theme.shadows[4], + }), + ...(theme.vars + ? { + backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.hover.stateLayerOpacity + })`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + theme.state.hover.stateLayerOpacity, + ), + }), }, '&:active': { - boxShadow: 'none', + ...(theme.vars + ? { + backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.pressed.stateLayerOpacity + })`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + theme.state.pressed.stateLayerOpacity, + ), + }), }, - [`&.${buttonClasses.disabled}`]: { - boxShadow: 'none', + [`&.${buttonClasses.focusVisible}`]: { + ...(theme.vars + ? { + backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.focus.stateLayerOpacity + })`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + theme.state.focus.stateLayerOpacity, + ), + }), }, }), })); @@ -331,9 +310,6 @@ const Button = React.forwardRef(function Button(inProps, ref) { component = 'button', disabled = false, disableElevation = false, - disableFocusRipple = false, - disableRipple = false, - disableTouchRipple = false, endIcon: endIconProp, focusVisibleClassName, fullWidth = false, @@ -355,7 +331,6 @@ const Button = React.forwardRef(function Button(inProps, ref) { size = 'medium', startIcon: startIconProp, tabIndex = 0, - TouchRippleProps, type, variant = 'text', ...other @@ -364,8 +339,6 @@ const Button = React.forwardRef(function Button(inProps, ref) { const buttonRef = React.useRef(null); const handleRef = useForkRef(buttonRef, ref); - const rippleRef = React.useRef(null); - let ComponentProp = component; if (ComponentProp === 'button' && (other.href || other.to)) { @@ -389,29 +362,6 @@ const Button = React.forwardRef(function Button(inProps, ref) { [setFocusVisible], ); - const { enableTouchRipple, getRippleHandlers } = useTouchRipple({ - disabled, - disableFocusRipple, - disableRipple, - disableTouchRipple, - focusVisible, - rippleRef, - }); - - if (process.env.NODE_ENV !== 'production') { - // eslint-disable-next-line react-hooks/rules-of-hooks - React.useEffect(() => { - if (enableTouchRipple && !rippleRef.current) { - console.error( - [ - 'MUI: The `component` prop provided to Button is invalid.', - 'Please make sure the children prop is rendered in this custom component.', - ].join('\n'), - ); - } - }, [enableTouchRipple]); - } - const ownerState = { ...props, centerRipple, @@ -419,9 +369,6 @@ const Button = React.forwardRef(function Button(inProps, ref) { component, disabled, disableElevation, - disableFocusRipple, - disableRipple, - disableTouchRipple, focusVisible, fullWidth, size, @@ -449,16 +396,12 @@ const Button = React.forwardRef(function Button(inProps, ref) { as={ComponentProp} className={clsx(classes.root, className)} ownerState={ownerState} - {...getRootProps(getRippleHandlers(props))} + {...getRootProps(props)} {...other} > {startIcon} {children} {endIcon} - {enableTouchRipple ? ( - /* TouchRipple is only needed client-side, x2 boost on the server. */ - - ) : null} ); }); @@ -473,12 +416,6 @@ Button.propTypes /* remove-proptypes */ = { * It exposes the `focusVisible()` action. */ action: refType, - /** - * If `true`, the ripples are centered. - * They won't start at the cursor interaction position. - * @default false - */ - centerRipple: PropTypes.bool, /** * The content of the component. */ @@ -514,24 +451,6 @@ Button.propTypes /* remove-proptypes */ = { * @default false */ disableElevation: PropTypes.bool, - /** - * If `true`, the keyboard focus ripple is disabled. - * @default false - */ - disableFocusRipple: PropTypes.bool, - /** - * If `true`, the ripple effect is disabled. - * - * ⚠️ Without a ripple there is no styling for :focus-visible by default. Be sure - * to highlight the element by applying separate styles with the `.Mui-focusVisible` class. - * @default false - */ - disableRipple: PropTypes.bool, - /** - * If `true`, the touch ripple effect is disabled. - * @default false - */ - disableTouchRipple: PropTypes.bool, /** * Element placed after the children. */ @@ -637,10 +556,6 @@ Button.propTypes /* remove-proptypes */ = { * @default 0 */ tabIndex: PropTypes.number, - /** - * Props applied to the `TouchRipple` element. - */ - TouchRippleProps: PropTypes.object, /** * @ignore */ diff --git a/packages/mui-material-next/src/Button/Button.test.js b/packages/mui-material-next/src/Button/Button.test.js index cfc5344335858a..fc3b6389b2a16d 100644 --- a/packages/mui-material-next/src/Button/Button.test.js +++ b/packages/mui-material-next/src/Button/Button.test.js @@ -1,6 +1,6 @@ import * as React from 'react'; import { expect } from 'chai'; -import { describeConformance, act, createRenderer, fireEvent } from 'test/utils'; +import { describeConformance, createRenderer } from 'test/utils'; import Button, { buttonClasses as classes } from '@mui/material/Button'; import ButtonBase from '@mui/material/ButtonBase'; @@ -280,26 +280,6 @@ describe(', - ); - const button = getByRole('button'); - - expect(button.querySelector('.touch-ripple')).not.to.equal(null); - }); - - it('can disable the ripple', () => { - const { getByRole } = render( - , - ); - const button = getByRole('button'); - - expect(button.querySelector('.touch-ripple')).to.equal(null); - }); - it('can disable the elevation', () => { const { getByRole } = render(); const button = getByRole('button'); @@ -307,41 +287,6 @@ describe(', - ); - const button = getByRole('button'); - - fireEvent.keyDown(document.body, { key: 'TAB' }); - act(() => { - button.focus(); - }); - - expect(button.querySelector('.pulsate-focus-visible')).not.to.equal(null); - }); - - it('can disable the focusRipple', () => { - const { getByRole } = render( - , - ); - const button = getByRole('button'); - - act(() => { - fireEvent.keyDown(document.body, { key: 'TAB' }); - button.focus(); - }); - - expect(button.querySelector('.pulsate-focus-visible')).to.equal(null); - }); - describe('server-side', () => { before(function beforeHook() { // Only run the test on node. @@ -366,7 +311,7 @@ describe(' - ))} + +

Enabled

+ + {variants.map((variant) => ( + + ))} + +

Disabled

+ + {variants.map((variant) => ( + + ))} + +

Colors

+ + {colors.map((color) => ( + + ))} + + + {colors.map((color) => ( + + ))} + + + {colors.map((color) => ( + + ))} + ); }; diff --git a/packages/mui-material-next/src/Button/Button.js b/packages/mui-material-next/src/Button/Button.js index a5e1e76b7f6989..7bf20ee80a4b89 100644 --- a/packages/mui-material-next/src/Button/Button.js +++ b/packages/mui-material-next/src/Button/Button.js @@ -89,179 +89,316 @@ export const ButtonRoot = styled('button', { ownerState.fullWidth && styles.fullWidth, ]; }, -})(({ theme, ownerState }) => ({ - border: 'none', - outline: 'none', - padding: '10px 24px', - fontFamily: (theme.vars || theme).typescale.label.large.family, - fontWeight: (theme.vars || theme).typescale.label.large.weight, - borderRadius: (theme.vars || theme).shape.borderRadius, - // Filled varaint - ...(ownerState.variant === 'filled' && { - backgroundColor: (theme.vars || theme).palette.md3.colors.primary, - color: (theme.vars || theme).palette.md3.colors.onPrimary, - '&:hover': { - boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.primaryChannel - } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - 1 - theme.state.hover.stateLayerOpacity, - ), - }), - }, - '&:active': { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.primaryChannel - } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - 1 - theme.state.pressed.stateLayerOpacity, - ), - }), - }, - [`&.${buttonClasses.focusVisible}`]: { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.primaryChannel - } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - 1 - theme.state.focus.stateLayerOpacity, - ), - }), - }, - }), - // Filled tonal varitant - ...(ownerState.variant === 'filledTonal' && { - backgroundColor: (theme.vars || theme).palette.md3.colors.secondaryContainer, - color: (theme.vars || theme).palette.md3.colors.onSecondaryContainer, - '&:hover': { - boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.secondaryContainerChannel - } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.state.hover.stateLayerOpacity, - ), - }), - }, - '&:active': { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.secondaryContainerChannel - } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.state.pressed.stateLayerOpacity, - ), - }), - }, - [`&.${buttonClasses.focusVisible}`]: { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.secondaryContainerChannel - } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.state.focus.stateLayerOpacity, - ), - }), - }, - }), - // Outlined varaiant - ...(ownerState.variant === 'outlined' && { - border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, - color: (theme.vars || theme).palette.md3.colors.primary, - background: 'transparent', - }), - // Elevated variant - ...(ownerState.variant === 'elevated' && { - background: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${ +})(({ theme, ownerState }) => { + const containerColor = { + elevated: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${ (theme.vars || theme).palette.md3.colors.surface }`, - color: (theme.vars || theme).palette.md3.colors.primary, - boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', // elevation.lightingColor.1 - }), - // Text variant - ...(ownerState.variant === 'text' && { - color: (theme.vars || theme).palette.md3.colors.primary, - background: 'transparent', - }), - // State styles for text, outlined, elevated variants - ...((ownerState.variant === 'text' || - ownerState.variant === 'outlined' || - ownerState.variant === 'elevated') && { - '&:hover': { - ...(ownerState.variant === 'elevated' && { - boxShadow: theme.shadows[4], + filled: (theme.vars || theme).palette.md3.colors[ownerState.color ?? 'primary'], + filledTonal: (theme.vars || theme).palette.md3.colors.secondaryContainer, + outlined: 'none', + text: 'none', + }; + + const labelTextColor = { + elevated: (theme.vars || theme).palette.md3.colors.primary, + filled: (theme.vars || theme).palette.md3.colors[ + `on${capitalize(ownerState.color ?? 'primary')}` + ], + filledTonal: (theme.vars || theme).palette.md3.colors.onSecondaryContainer, + outlined: (theme.vars || theme).palette.md3.colors[ownerState.color ?? 'primary'], + text: (theme.vars || theme).palette.md3.colors[ownerState.color ?? 'primary'], + }; + + const disabeldContainerColor = { + elevated: theme.vars + ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` + : alpha(theme.palette.md3.colors.onSurface, 0.12), + filled: theme.vars + ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` + : alpha(theme.palette.md3.colors.onSurface, 0.12), + filledTonal: theme.vars + ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` + : alpha(theme.palette.md3.colors.onSurface, 0.12), + outlined: 'none', + text: 'none', + }; + + const disabledLabelTextColor = theme.vars + ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.38)` + : alpha(theme.palette.md3.colors.onSurface, 0.38); + + return { + ...(theme.vars && { + // TODO: Define all button variables + // enabled + '--md-comp-button-container-color': containerColor[ownerState.variant], + '--md-comp-button-container-shadow-color': '', + '--md-comp-button-container-elevation': '', + '--md-comp-button-label-text-color': labelTextColor[ownerState.variant], + '--md-comp-button-label-text-font': (theme.vars || theme).typescale.label.large.family, + '--md-comp-button-label-text-line-height': '', + '--md-comp-button-label-text-size': '', + '--md-comp-button-label-text-tracking': '', + '--md-comp-button-label-text-weight': '', + '--md-comp-button-icon-color': '', + // disabled + '--md-comp-button-disabled-container-color': disabeldContainerColor[ownerState.variant], + '--md-comp-button-disabled-container-elevation': 'none', // Should be md.sys.elevation.level0 + // '--md-comp-button-disabled-container-opacity': '', contained in the container color + + '--md-comp-button-disabled-label-text-color': disabledLabelTextColor, + // '--md-comp-button-disabled-label-text-opacity': '', contained in the label text color + + '--md-comp-button-disabled-icon-color': '', + '--md-comp-button-disabled-icon-opacity': '', + // hovered + '--md-comp-button-hovered-container-state-layer-color': '', + '--md-comp-button-hovered-container-state-layer-opacity': '', + '--md-comp-button-hovered-container-elevation': '', + '--md-comp-button-hovered-label-text-color': '', + '--md-comp-button-hovered-icon-color': '', + // focused + '--md-comp-button-focused-container-state-layer-color': '', + '--md-comp-button-focused-container-state-layer-opacity': '', + '--md-comp-button-focused-container-elevation': '', + '--md-comp-button-focused-label-text-color': '', + '--md-comp-button-focused-icon-color': '', + // pressed + '--md-comp-button-pressed-container-state-layer-color': '', + '--md-comp-button-pressed-container-state-layer-opacity': '', + '--md-comp-button-pressed-container-elevation': '', + '--md-comp-button-pressed-label-text-color': '', + '--md-comp-button-pressed-icon-color': '', + }), + border: 'none', + outline: 'none', + padding: '10px 24px', + fontFamily: theme.vars + ? 'var(--md-comp-button-label-text-font)' + : theme.typescale.label.large.family, + fontWeight: (theme.vars || theme).typescale.label.large.weight, + borderRadius: (theme.vars || theme).shape.borderRadius, + background: theme.vars + ? 'var(--md-comp-button-container-color)' + : containerColor[ownerState.variant], + color: theme.vars + ? 'var(--md-comp-button-label-text-color)' + : labelTextColor[ownerState.variant], + // Filled varaint + ...(ownerState.variant === 'filled' && { + '&:hover': { + boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + 1 - theme.state.hover.stateLayerOpacity, + ), + }), + }, + '&:active': { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + 1 - theme.state.pressed.stateLayerOpacity, + ), + }), + }, + [`&.${buttonClasses.focusVisible}`]: { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + 1 - theme.state.focus.stateLayerOpacity, + ), + }), + }, + }), + // Filled tonal varitant + ...(ownerState.variant === 'filledTonal' && { + '&:hover': { + boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.secondaryContainerChannel + } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.state.hover.stateLayerOpacity, + ), + }), + }, + '&:active': { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.secondaryContainerChannel + } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.state.pressed.stateLayerOpacity, + ), + }), + }, + [`&.${buttonClasses.focusVisible}`]: { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors.secondaryContainerChannel + } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.state.focus.stateLayerOpacity, + ), + }), + }, + }), + // Outlined varaiant + ...(ownerState.variant === 'outlined' && { + border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, + }), + // Elevated variant + ...(ownerState.variant === 'elevated' && { + color: (theme.vars || theme).palette.md3.colors.primary, + boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', // elevation.lightingColor.1 + }), + ...(ownerState.variant === 'elevated' && { + '&:hover': { + ...(ownerState.variant === 'elevated' && { + boxShadow: theme.shadows[4], + }), + ...(theme.vars + ? { + backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.hover.stateLayerOpacity + })`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + theme.state.hover.stateLayerOpacity, + ), + }), + }, + '&:active': { + ...(theme.vars + ? { + backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.pressed.stateLayerOpacity + })`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + theme.state.pressed.stateLayerOpacity, + ), + }), + }, + [`&.${buttonClasses.focusVisible}`]: { + ...(theme.vars + ? { + backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.focus.stateLayerOpacity + })`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors.primary, + theme.state.focus.stateLayerOpacity, + ), + }), + }, + }), + // State styles for text, outlined, elevated variants + ...((ownerState.variant === 'text' || ownerState.variant === 'outlined') && { + '&:hover': { + ...(ownerState.variant === 'elevated' && { + boxShadow: theme.shadows[4], + }), + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.hover.stateLayerOpacity})`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.hover.stateLayerOpacity, + ), + }), + }, + '&:active': { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.pressed.stateLayerOpacity})`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.pressed.stateLayerOpacity, + ), + }), + }, + [`&.${buttonClasses.focusVisible}`]: { + ...(theme.vars + ? { + backgroundColor: `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.focus.stateLayerOpacity})`, + } + : { + backgroundColor: alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.focus.stateLayerOpacity, + ), + }), + }, + }), + [`&.${buttonClasses.disabled}`]: { + color: theme.vars + ? 'var(--md-comp-button-disabled-label-text-color)' + : disabledLabelTextColor, + background: theme.vars + ? 'var(--md-comp-button-disabled-container-color)' + : disabeldContainerColor[ownerState.variant], + boxShadow: theme.vars ? 'var(--md-comp-button-disabled-container-elevation)' : 'none', + ...(ownerState.variant === 'outlined' && { + border: `1px solid ${ + theme.vars + ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` + : alpha(theme.palette.md3.colors.onSurface, 0.12) + }`, }), - ...(theme.vars - ? { - backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.hover.stateLayerOpacity - })`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - theme.state.hover.stateLayerOpacity, - ), - }), - }, - '&:active': { - ...(theme.vars - ? { - backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.pressed.stateLayerOpacity - })`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - theme.state.pressed.stateLayerOpacity, - ), - }), }, - [`&.${buttonClasses.focusVisible}`]: { - ...(theme.vars - ? { - backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.focus.stateLayerOpacity - })`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - theme.state.focus.stateLayerOpacity, - ), - }), - }, - }), -})); + }; +}); const ButtonStartIcon = styled('span', { name: 'MuiButton', diff --git a/packages/mui-material/src/styles/experimental_extendMD3Theme.js b/packages/mui-material/src/styles/experimental_extendMD3Theme.js index d9e99df3576192..a860333e43accd 100644 --- a/packages/mui-material/src/styles/experimental_extendMD3Theme.js +++ b/packages/mui-material/src/styles/experimental_extendMD3Theme.js @@ -345,10 +345,16 @@ export default function extendTheme(options = {}, ...args) { if (useMaterialYou) { if (key === 'light') { palette.md3.colors.primaryChannel = colorChannel(palette.md3.primary['40']); + palette.md3.colors.secondaryChannel = colorChannel(palette.md3.secondary['40']); + palette.md3.colors.tertiaryChannel = colorChannel(palette.md3.tertiary['40']); palette.md3.colors.secondaryContainerChannel = colorChannel(palette.md3.secondary['90']); + palette.md3.colors.onSurfaceChannel = colorChannel(palette.md3.neutral['10']); } else { palette.md3.colors.primaryChannel = colorChannel(palette.md3.primary['80']); + palette.md3.colors.secondaryChannel = colorChannel(palette.md3.secondary['80']); + palette.md3.colors.tertiaryChannel = colorChannel(palette.md3.tertiary['80']); palette.md3.colors.secondaryContainerChannel = colorChannel(palette.md3.secondary['30']); + palette.md3.colors.onSurfaceChannel = colorChannel(palette.md3.neutral['90']); } } }); From 4be5c864a566a71925281d83f8dcc5077c70134a Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Tue, 18 Oct 2022 14:25:39 +0200 Subject: [PATCH 03/49] More progress --- docs/pages/experiments/md3/index.js | 23 + .../mui-material-next/src/Button/Button.d.ts | 5 + .../mui-material-next/src/Button/Button.js | 520 +++++++++--------- .../mui-material/src/styles/md3/typescale.js | 3 + 4 files changed, 294 insertions(+), 257 deletions(-) diff --git a/docs/pages/experiments/md3/index.js b/docs/pages/experiments/md3/index.js index 32902b9223a021..0655d208f98673 100644 --- a/docs/pages/experiments/md3/index.js +++ b/docs/pages/experiments/md3/index.js @@ -10,6 +10,8 @@ import { Stack, } from '@mui/material'; import { unstable_capitalize as capitalize } from 'packages/mui-utils'; +import DeleteIcon from '@mui/icons-material/Delete'; +import SendIcon from '@mui/icons-material/Send'; import { Button } from '@mui/material-next'; import DarkIcon from '@mui/icons-material/DarkModeOutlined'; import LightIcon from '@mui/icons-material/LightModeOutlined'; @@ -89,6 +91,27 @@ const DemoComponents = () => { ))} +

Extended buttons

+ + {colors.map((color) => ( + + ))} + + + + {colors.map((color) => ( + + ))} + + ); }; diff --git a/packages/mui-material-next/src/Button/Button.d.ts b/packages/mui-material-next/src/Button/Button.d.ts index 8453de636930e6..689ecceda57e6b 100644 --- a/packages/mui-material-next/src/Button/Button.d.ts +++ b/packages/mui-material-next/src/Button/Button.d.ts @@ -57,6 +57,11 @@ export interface ButtonTypeMap

{ * Element placed after the children. */ endIcon?: React.ReactNode; + /** + * If `true`, allows a disabled button to receive focus. + * @default false + */ + focusableWhenDisabled?: boolean; /** * This prop can help identify which element has keyboard focus. * The class name will be applied when the element gains the focus through keyboard interaction. diff --git a/packages/mui-material-next/src/Button/Button.js b/packages/mui-material-next/src/Button/Button.js index 7bf20ee80a4b89..11ce90cab21a30 100644 --- a/packages/mui-material-next/src/Button/Button.js +++ b/packages/mui-material-next/src/Button/Button.js @@ -54,6 +54,7 @@ const useUtilityClasses = (styleProps) => { }; const commonIconStyles = ({ size }) => ({ + color: 'var(--md-comp-button-icon-color)', ...(size === 'small' && { '& > *:nth-of-type(1)': { fontSize: 18, @@ -124,271 +125,264 @@ export const ButtonRoot = styled('button', { text: 'none', }; + const hoveredContainerColor = { + elevated: theme.vars + ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.hover.stateLayerOpacity + })` + : alpha(theme.palette.md3.colors.primary, theme.state.hover.stateLayerOpacity), + filled: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + 1 - theme.state.hover.stateLayerOpacity, + ), + filledTonal: theme.vars + ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ + (theme.vars || theme).state.hover.stateLayerOpacity + }))` + : alpha(theme.palette.md3.colors.secondaryContainer, 1 - theme.state.hover.stateLayerOpacity), + outlined: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.hover.stateLayerOpacity})` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.hover.stateLayerOpacity, + ), + text: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.hover.stateLayerOpacity})` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.hover.stateLayerOpacity, + ), + }; + + const hoveredContainerElevation = { + elevated: theme.shadows[4], // not the correct value, need to be validated + filled: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', + filledTonal: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', + outlined: 'none', + text: 'none', + }; + + const pressedContainerColor = { + elevated: theme.vars + ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.pressed.stateLayerOpacity + })` + : alpha(theme.palette.md3.colors.primary, theme.state.pressed.stateLayerOpacity), + filled: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + 1 - theme.state.pressed.stateLayerOpacity, + ), + filledTonal: theme.vars + ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ + (theme.vars || theme).state.pressed.stateLayerOpacity + }))` + : alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.state.pressed.stateLayerOpacity, + ), + outlined: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.pressed.stateLayerOpacity})` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.pressed.stateLayerOpacity, + ), + text: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.pressed.stateLayerOpacity})` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.pressed.stateLayerOpacity, + ), + }; + + const focusedContainerColor = { + elevated: theme.vars + ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ + (theme.vars || theme).state.focus.stateLayerOpacity + })` + : alpha(theme.palette.md3.colors.primary, theme.state.focus.stateLayerOpacity), + filled: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + 1 - theme.state.focus.stateLayerOpacity, + ), + filledTonal: theme.vars + ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ + (theme.vars || theme).state.focus.stateLayerOpacity + }))` + : alpha(theme.palette.md3.colors.secondaryContainer, 1 - theme.state.focus.stateLayerOpacity), + outlined: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.focus.stateLayerOpacity})` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.focus.stateLayerOpacity, + ), + text: theme.vars + ? `rgba(${ + (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).state.focus.stateLayerOpacity})` + : alpha( + theme.palette.md3.colors[ownerState.color ?? 'primary'], + theme.state.focus.stateLayerOpacity, + ), + }; + + const containerElevation = { + elevated: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', + filled: 'none', // md.sys.elevation.level0 + filledTonal: 'none', // md.sys.elevation.level0 + outlined: 'none', // md.sys.elevation.level0 + text: 'none', // md.sys.elevation.level0 + }; const disabledLabelTextColor = theme.vars ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.38)` : alpha(theme.palette.md3.colors.onSurface, 0.38); + const letterSpacing = `${ + theme.typescale.label.large.tracking / theme.typescale.label.large.size + }rem`; + return { - ...(theme.vars && { - // TODO: Define all button variables - // enabled - '--md-comp-button-container-color': containerColor[ownerState.variant], - '--md-comp-button-container-shadow-color': '', - '--md-comp-button-container-elevation': '', - '--md-comp-button-label-text-color': labelTextColor[ownerState.variant], - '--md-comp-button-label-text-font': (theme.vars || theme).typescale.label.large.family, - '--md-comp-button-label-text-line-height': '', - '--md-comp-button-label-text-size': '', - '--md-comp-button-label-text-tracking': '', - '--md-comp-button-label-text-weight': '', - '--md-comp-button-icon-color': '', - // disabled - '--md-comp-button-disabled-container-color': disabeldContainerColor[ownerState.variant], - '--md-comp-button-disabled-container-elevation': 'none', // Should be md.sys.elevation.level0 - // '--md-comp-button-disabled-container-opacity': '', contained in the container color - - '--md-comp-button-disabled-label-text-color': disabledLabelTextColor, - // '--md-comp-button-disabled-label-text-opacity': '', contained in the label text color - - '--md-comp-button-disabled-icon-color': '', - '--md-comp-button-disabled-icon-opacity': '', - // hovered - '--md-comp-button-hovered-container-state-layer-color': '', - '--md-comp-button-hovered-container-state-layer-opacity': '', - '--md-comp-button-hovered-container-elevation': '', - '--md-comp-button-hovered-label-text-color': '', - '--md-comp-button-hovered-icon-color': '', - // focused - '--md-comp-button-focused-container-state-layer-color': '', - '--md-comp-button-focused-container-state-layer-opacity': '', - '--md-comp-button-focused-container-elevation': '', - '--md-comp-button-focused-label-text-color': '', - '--md-comp-button-focused-icon-color': '', - // pressed - '--md-comp-button-pressed-container-state-layer-color': '', - '--md-comp-button-pressed-container-state-layer-opacity': '', - '--md-comp-button-pressed-container-elevation': '', - '--md-comp-button-pressed-label-text-color': '', - '--md-comp-button-pressed-icon-color': '', - }), - border: 'none', - outline: 'none', + // What's missing: + // 1. The container state opacities are calculated in the background color for now + // '--md-comp-button-disabled-container-opacity': '', + // '--md-comp-button-disabled-label-text-opacity': '', + // '--md-comp-button-disabled-icon-opacity': '', + // '--md-comp-button-hovered-container-state-layer-opacity': '', + // '--md-comp-button-focused-container-state-layer-opacity': '', + // '--md-comp-button-pressed-container-state-layer-opacity': '', + // 2. The elevations are not correctly implemented, as I still couldn't find an actual specification around their values + // '--md-comp-button-container-shadow-color': '', + // '--md-comp-button-focused-container-elevation': '', + // '--md-comp-button-pressed-container-elevation': '', + // 3. Not sure how to make the tracking work with the CSS variables as there is a calculation needed + // '--md-comp-button-label-text-tracking': (theme.vars || theme).typescale.label.large.tracking, + // Icon variables default values + '--md-comp-button-icon-color': labelTextColor[ownerState.variant], + '--md-comp-button-hovered-icon-color': labelTextColor[ownerState.variant], // same as default + '--md-comp-button-pressed-icon-color': labelTextColor[ownerState.variant], // same as default + '--md-comp-button-focused-icon-color': labelTextColor[ownerState.variant], // same as default + '--md-comp-button-disabled-icon-color': disabledLabelTextColor, + // Dynamic variables + '--md-comp-button-label-text-line-height': `calc(${ + (theme.vars || theme).typescale.label.large.lineHeight + } / ${theme.typescale.label.large.size})`, + // Noramlized styles for buttons + display: 'inline-flex', + alignItems: 'center', + justifyContent: 'center', + position: 'relative', + boxSizing: 'border-box', + WebkitTapHighlightColor: 'transparent', + backgroundColor: 'transparent', // Reset default value + // We disable the focus ring for mouse, touch and keyboard users. + outline: 0, + border: 0, + margin: 0, // Remove the margin in Safari + cursor: 'pointer', + userSelect: 'none', + verticalAlign: 'middle', + MozAppearance: 'none', // Reset + WebkitAppearance: 'none', // Reset + textDecoration: 'none', + // So we take precedent over the style of a native element. + color: 'inherit', + '&::-moz-focus-inner': { + borderStyle: 'none', // Remove Firefox dotted outline. + }, + '@media print': { + colorAdjust: 'exact', + }, padding: '10px 24px', - fontFamily: theme.vars - ? 'var(--md-comp-button-label-text-font)' - : theme.typescale.label.large.family, - fontWeight: (theme.vars || theme).typescale.label.large.weight, - borderRadius: (theme.vars || theme).shape.borderRadius, - background: theme.vars - ? 'var(--md-comp-button-container-color)' - : containerColor[ownerState.variant], - color: theme.vars - ? 'var(--md-comp-button-label-text-color)' - : labelTextColor[ownerState.variant], - // Filled varaint - ...(ownerState.variant === 'filled' && { - '&:hover': { - boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.state.hover.stateLayerOpacity, - ), - }), - }, - '&:active': { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.state.pressed.stateLayerOpacity, - ), - }), - }, - [`&.${buttonClasses.focusVisible}`]: { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.state.focus.stateLayerOpacity, - ), - }), + minWidth: 64, + // Taken from MD2, haven't really found a spec on transitions + transition: theme.transitions.create( + ['background-color', 'box-shadow', 'border-color', 'color'], + { + duration: theme.transitions.duration.short, }, - }), - // Filled tonal varitant - ...(ownerState.variant === 'filledTonal' && { - '&:hover': { - boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.secondaryContainerChannel - } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.state.hover.stateLayerOpacity, - ), - }), - }, - '&:active': { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.secondaryContainerChannel - } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.state.pressed.stateLayerOpacity, - ), - }), - }, - [`&.${buttonClasses.focusVisible}`]: { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors.secondaryContainerChannel - } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.state.focus.stateLayerOpacity, - ), - }), - }, - }), + ), + fontFamily: `var(--md-comp-button-label-text-font, ${ + (theme.vars || theme).typescale.label.large.family + })`, + fontWeight: `var(--md-comp-button-label-text-weight, ${ + (theme.vars || theme).typescale.label.large.weight + })`, + fontSize: `var(--md-comp-button-label-text-size, ${ + (theme.vars || theme).typescale.label.large.size + }${theme.vars ? '' : 'px'})`, + lineHeight: 'var(--md-comp-button-label-text-line-height)', + letterSpacing: letterSpacing, + borderRadius: (theme.vars || theme).shape.borderRadius, + background: `var(--md-comp-button-container-color, ${containerColor[ownerState.variant]})`, + color: `var(--md-comp-button-label-text-color, ${labelTextColor[ownerState.variant]})`, + boxShadow: `var(--md-comp-button-container-elevation, ${ + containerElevation[ownerState.variant] + })`, // Outlined varaiant ...(ownerState.variant === 'outlined' && { border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, }), - // Elevated variant - ...(ownerState.variant === 'elevated' && { - color: (theme.vars || theme).palette.md3.colors.primary, - boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.3), 0px 1px 3px 1px rgba(0, 0, 0, 0.15)', // elevation.lightingColor.1 - }), - ...(ownerState.variant === 'elevated' && { - '&:hover': { - ...(ownerState.variant === 'elevated' && { - boxShadow: theme.shadows[4], - }), - ...(theme.vars - ? { - backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.hover.stateLayerOpacity - })`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - theme.state.hover.stateLayerOpacity, - ), - }), - }, - '&:active': { - ...(theme.vars - ? { - backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.pressed.stateLayerOpacity - })`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - theme.state.pressed.stateLayerOpacity, - ), - }), - }, - [`&.${buttonClasses.focusVisible}`]: { - ...(theme.vars - ? { - backgroundColor: `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.focus.stateLayerOpacity - })`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors.primary, - theme.state.focus.stateLayerOpacity, - ), - }), - }, - }), - // State styles for text, outlined, elevated variants - ...((ownerState.variant === 'text' || ownerState.variant === 'outlined') && { - '&:hover': { - ...(ownerState.variant === 'elevated' && { - boxShadow: theme.shadows[4], - }), - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.hover.stateLayerOpacity})`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.hover.stateLayerOpacity, - ), - }), - }, - '&:active': { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.pressed.stateLayerOpacity})`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.pressed.stateLayerOpacity, - ), - }), - }, - [`&.${buttonClasses.focusVisible}`]: { - ...(theme.vars - ? { - backgroundColor: `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.focus.stateLayerOpacity})`, - } - : { - backgroundColor: alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.focus.stateLayerOpacity, - ), - }), - }, - }), + '&:hover': { + '--md-comp-button-icon-color': '--md-comp-button-hovered-icon-color', + color: `var(--md-comp-button-hovered-label-text-color, ${ + labelTextColor[ownerState.variant] + })`, + backgroundColor: `var(--md-comp-button-hovered-container-state-layer-color, ${ + hoveredContainerColor[ownerState.variant] + })`, + boxShadow: `var(--md-comp-button-hovered-container-elevation, ${ + hoveredContainerElevation[ownerState.variant] + })`, + }, + '&:active': { + '--md-comp-button-icon-color': '--md-comp-button-pressed-icon-color', + color: `var(--md-comp-button-pressed-label-text-color, ${ + labelTextColor[ownerState.variant] + })`, + backgroundColor: `var(--md-comp-button-pressed-container-state-layer-color, ${ + pressedContainerColor[ownerState.variant] + })`, + }, + [`&.${buttonClasses.focusVisible}`]: { + '--md-comp-button-icon-color': '--md-comp-button-focused-icon-color', + color: `var(--md-comp-button-focused-label-text-color, ${ + labelTextColor[ownerState.variant] + })`, + backgroundColor: `var(--md-comp-button-focused-container-state-layer-color, ${ + focusedContainerColor[ownerState.variant] + })`, + }, [`&.${buttonClasses.disabled}`]: { - color: theme.vars - ? 'var(--md-comp-button-disabled-label-text-color)' - : disabledLabelTextColor, - background: theme.vars - ? 'var(--md-comp-button-disabled-container-color)' - : disabeldContainerColor[ownerState.variant], - boxShadow: theme.vars ? 'var(--md-comp-button-disabled-container-elevation)' : 'none', + // Allows deverloper to specify the disabled icon color var + '--md-comp-button-icon-color': '--md-comp-button-disabled-icon-color', + pointerEvents: 'none', // Disable link interactions + cursor: 'default', + color: `var(--md-comp-button-disabled-label-text-color, ${disabledLabelTextColor})`, + background: `var(--md-comp-button-disabled-container-color, ${ + disabeldContainerColor[ownerState.variant] + })`, + boxShadow: 'var(--md-comp-button-disabled-container-elevation, none)', // Should be md.sys.elevation.level0 ...(ownerState.variant === 'outlined' && { border: `1px solid ${ theme.vars @@ -411,7 +405,7 @@ const ButtonStartIcon = styled('span', { })(({ ownerState }) => ({ display: 'inherit', marginRight: 8, - marginLeft: -4, + marginLeft: -8, ...(ownerState.size === 'small' && { marginLeft: -2, }), @@ -428,7 +422,7 @@ const ButtonEndIcon = styled('span', { }, })(({ ownerState }) => ({ display: 'inherit', - marginRight: -4, + marginRight: -8, marginLeft: 8, ...(ownerState.size === 'small' && { marginRight: -2, @@ -446,6 +440,7 @@ const Button = React.forwardRef(function Button(inProps, ref) { color = 'primary', component = 'button', disabled = false, + focusableWhenDisabled = false, disableElevation = false, endIcon: endIconProp, focusVisibleClassName, @@ -483,7 +478,13 @@ const Button = React.forwardRef(function Button(inProps, ref) { } const { focusVisible, setFocusVisible, getRootProps } = useButton({ - ...props, + disabled, + focusableWhenDisabled, + href: props.href, + onFocusVisible, + tabIndex, + to: props.to, + type, component: ComponentProp, ref: handleRef, }); @@ -592,6 +593,11 @@ Button.propTypes /* remove-proptypes */ = { * Element placed after the children. */ endIcon: PropTypes.node, + /** + * If `true`, allows a disabled button to receive focus. + * @default false + */ + focusableWhenDisabled: PropTypes.bool, /** * @ignore */ @@ -702,7 +708,7 @@ Button.propTypes /* remove-proptypes */ = { * @default 'text' */ variant: PropTypes /* @typescript-to-proptypes-ignore */.oneOfType([ - PropTypes.oneOf(['contained', 'outlined', 'text']), + PropTypes.oneOf(['text', 'outlined', 'filled', 'filledTonal', 'elevated']), PropTypes.string, ]), }; diff --git a/packages/mui-material/src/styles/md3/typescale.js b/packages/mui-material/src/styles/md3/typescale.js index 2da3afcb85ddf5..7a834239faa11a 100644 --- a/packages/mui-material/src/styles/md3/typescale.js +++ b/packages/mui-material/src/styles/md3/typescale.js @@ -11,6 +11,9 @@ const mdSysTypescale = { large: { family: 'Roboto', weight: '500', + lineHeight: 20, + size: 14, + tracking: 0.1, }, }, body: { From 9be7ed057212c3436371a5cfb20efd6dbed77be7 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Tue, 18 Oct 2022 15:18:17 +0200 Subject: [PATCH 04/49] vars fixes --- packages/mui-material-next/src/Button/Button.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.js b/packages/mui-material-next/src/Button/Button.js index 11ce90cab21a30..919072dbdffdd6 100644 --- a/packages/mui-material-next/src/Button/Button.js +++ b/packages/mui-material-next/src/Button/Button.js @@ -344,7 +344,7 @@ export const ButtonRoot = styled('button', { border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, }), '&:hover': { - '--md-comp-button-icon-color': '--md-comp-button-hovered-icon-color', + '--md-comp-button-icon-color': 'var(--md-comp-button-hovered-icon-color)', color: `var(--md-comp-button-hovered-label-text-color, ${ labelTextColor[ownerState.variant] })`, @@ -356,7 +356,7 @@ export const ButtonRoot = styled('button', { })`, }, '&:active': { - '--md-comp-button-icon-color': '--md-comp-button-pressed-icon-color', + '--md-comp-button-icon-color': 'var(--md-comp-button-pressed-icon-color)', color: `var(--md-comp-button-pressed-label-text-color, ${ labelTextColor[ownerState.variant] })`, @@ -365,7 +365,7 @@ export const ButtonRoot = styled('button', { })`, }, [`&.${buttonClasses.focusVisible}`]: { - '--md-comp-button-icon-color': '--md-comp-button-focused-icon-color', + '--md-comp-button-icon-color': 'var(--md-comp-button-focused-icon-color)', color: `var(--md-comp-button-focused-label-text-color, ${ labelTextColor[ownerState.variant] })`, @@ -375,7 +375,7 @@ export const ButtonRoot = styled('button', { }, [`&.${buttonClasses.disabled}`]: { // Allows deverloper to specify the disabled icon color var - '--md-comp-button-icon-color': '--md-comp-button-disabled-icon-color', + '--md-comp-button-icon-color': 'var(--md-comp-button-disabled-icon-color)', pointerEvents: 'none', // Disable link interactions cursor: 'default', color: `var(--md-comp-button-disabled-label-text-color, ${disabledLabelTextColor})`, From eb7148767ebcc6ca97d5cdd8f506ace0ec165664 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Tue, 18 Oct 2022 15:51:52 +0200 Subject: [PATCH 05/49] Make sizes work --- docs/pages/experiments/md3/index.js | 16 ++++++++++++ .../mui-material-next/src/Button/Button.d.ts | 2 +- .../mui-material-next/src/Button/Button.js | 25 ++++++++++++++++--- 3 files changed, 39 insertions(+), 4 deletions(-) diff --git a/docs/pages/experiments/md3/index.js b/docs/pages/experiments/md3/index.js index 0655d208f98673..e859d6f2672ecf 100644 --- a/docs/pages/experiments/md3/index.js +++ b/docs/pages/experiments/md3/index.js @@ -49,6 +49,7 @@ const ModeSwitcher = ({ setMode: setModeProp }) => { const variants = ['elevated', 'filled', 'filledTonal', 'outlined', 'text']; const colors = ['primary', 'secondary', 'tertiary']; +const sizes = ['small', 'medium', 'large']; const DemoComponents = () => { return ( @@ -112,6 +113,21 @@ const DemoComponents = () => { Delete +

Sizes

+ + {sizes.map((size) => ( + + ))} + + + {sizes.map((size) => ( + + ))} + ); }; diff --git a/packages/mui-material-next/src/Button/Button.d.ts b/packages/mui-material-next/src/Button/Button.d.ts index 689ecceda57e6b..a193c2b0729cc3 100644 --- a/packages/mui-material-next/src/Button/Button.d.ts +++ b/packages/mui-material-next/src/Button/Button.d.ts @@ -61,7 +61,7 @@ export interface ButtonTypeMap

{ * If `true`, allows a disabled button to receive focus. * @default false */ - focusableWhenDisabled?: boolean; + focusableWhenDisabled?: boolean; /** * This prop can help identify which element has keyboard focus. * The class name will be applied when the element gains the focus through keyboard interaction. diff --git a/packages/mui-material-next/src/Button/Button.js b/packages/mui-material-next/src/Button/Button.js index 919072dbdffdd6..53886a89ebd379 100644 --- a/packages/mui-material-next/src/Button/Button.js +++ b/packages/mui-material-next/src/Button/Button.js @@ -329,10 +329,9 @@ export const ButtonRoot = styled('button', { (theme.vars || theme).typescale.label.large.weight })`, fontSize: `var(--md-comp-button-label-text-size, ${ - (theme.vars || theme).typescale.label.large.size - }${theme.vars ? '' : 'px'})`, + theme.typography.pxToRem(theme.typescale.label.large.size) // the pxToRem should be moved to typescale in the future + })`, lineHeight: 'var(--md-comp-button-label-text-line-height)', - letterSpacing: letterSpacing, borderRadius: (theme.vars || theme).shape.borderRadius, background: `var(--md-comp-button-container-color, ${containerColor[ownerState.variant]})`, color: `var(--md-comp-button-label-text-color, ${labelTextColor[ownerState.variant]})`, @@ -342,6 +341,26 @@ export const ButtonRoot = styled('button', { // Outlined varaiant ...(ownerState.variant === 'outlined' && { border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, + padding: '9px 23px', + }), + // Sizes are not specified in Material You, this need to be revised + ...(ownerState.size === 'small' && { + fontSize: `var(--md-comp-button-label-text-size, ${ + theme.typography.pxToRem(theme.typescale.label.large.size - 1) // the pxToRem should be moved to typescale in the future + })`, + padding: '8px 20px', + ...(ownerState.variant === 'outlined' && { + padding: '7px 19px', + }), + }), + ...(ownerState.size === 'large' && { + fontSize: `var(--md-comp-button-label-text-size, ${ + theme.typography.pxToRem(theme.typescale.label.large.size + 1) // the pxToRem should be moved to typescale in the future + })`, + padding: '12px 26px', + ...(ownerState.variant === 'outlined' && { + padding: '11px 25px', + }), }), '&:hover': { '--md-comp-button-icon-color': 'var(--md-comp-button-hovered-icon-color)', From 995e5c05762bb43a5fdfc8ff0eba4e72f54815aa Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 19 Oct 2022 16:12:54 +0200 Subject: [PATCH 06/49] Convert component to ts --- .../src/Button/{Button.js => Button.tsx} | 82 ++++++----- .../Button/{Button.d.ts => Button.types.ts} | 110 ++++++-------- .../mui-material-next/src/styles/index.ts | 137 ++++++++++++++++++ .../src/MaterialYouModuleAugmentation.ts | 87 +++++++++++ 4 files changed, 313 insertions(+), 103 deletions(-) rename packages/mui-material-next/src/Button/{Button.js => Button.tsx} (90%) rename packages/mui-material-next/src/Button/{Button.d.ts => Button.types.ts} (74%) create mode 100644 packages/mui-material-next/src/styles/index.ts create mode 100644 packages/mui-material/src/MaterialYouModuleAugmentation.ts diff --git a/packages/mui-material-next/src/Button/Button.js b/packages/mui-material-next/src/Button/Button.tsx similarity index 90% rename from packages/mui-material-next/src/Button/Button.js rename to packages/mui-material-next/src/Button/Button.tsx index 53886a89ebd379..c4340f76f5feb6 100644 --- a/packages/mui-material-next/src/Button/Button.js +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -7,13 +7,15 @@ import { unstable_capitalize as capitalize, unstable_useForkRef as useForkRef, } from '@mui/utils'; -import { useButton } from '@mui/base/ButtonUnstyled'; +import { MD3ColorSchemeTokens, Theme } from '../styles'; +import { useButton, UseButtonRootSlotOwnProps } from '@mui/base/ButtonUnstyled'; import composeClasses from '@mui/base/composeClasses'; import { useThemeProps, alpha } from '@mui/system'; import styled, { rootShouldForwardProp } from '@mui/material/styles/styled'; import buttonClasses, { getButtonUtilityClass } from './buttonClasses'; +import { ButtonProps, ExtendButton, ButtonTypeMap, ButtonOwnerState } from './Button.types'; -const useUtilityClasses = (styleProps) => { +const useUtilityClasses = (styleProps: ButtonOwnerState) => { const { classes, color, @@ -32,16 +34,15 @@ const useUtilityClasses = (styleProps) => { disabled && 'disabled', focusVisible && 'focusVisible', variant, - `${variant}${capitalize(color)}`, - `size${capitalize(size)}`, - `${variant}Size${capitalize(size)}`, - color === 'inherit' && 'colorInherit', + `${variant}${capitalize(color ?? '')}`, + `size${capitalize(size ?? '')}`, + `${variant}Size${capitalize(size ?? '')}`, disableElevation && 'disableElevation', fullWidth && 'fullWidth', ], label: ['label'], - startIcon: ['startIcon', `iconSize${capitalize(size)}`], - endIcon: ['endIcon', `iconSize${capitalize(size)}`], + startIcon: ['startIcon', `iconSize${capitalize(size ?? '')}`], + endIcon: ['endIcon', `iconSize${capitalize(size ?? '')}`], }; const composedClasses = composeClasses(slots, getButtonUtilityClass, classes); @@ -53,7 +54,7 @@ const useUtilityClasses = (styleProps) => { return composedClasses; }; -const commonIconStyles = ({ size }) => ({ +const commonIconStyles = ({ size }: ButtonOwnerState) => ({ color: 'var(--md-comp-button-icon-color)', ...(size === 'small' && { '& > *:nth-of-type(1)': { @@ -73,7 +74,7 @@ const commonIconStyles = ({ size }) => ({ }); export const ButtonRoot = styled('button', { - shouldForwardProp: (prop) => rootShouldForwardProp(prop) || prop === 'classes', + shouldForwardProp: (prop) => rootShouldForwardProp(prop as string) || prop === 'classes', name: 'MuiButton', slot: 'Root', overridesResolver: (props, styles) => { @@ -90,7 +91,7 @@ export const ButtonRoot = styled('button', { ownerState.fullWidth && styles.fullWidth, ]; }, -})(({ theme, ownerState }) => { +})<{ ownerState: ButtonOwnerState; theme?: Theme }>(({ ownerState, theme }) => { const containerColor = { elevated: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${ (theme.vars || theme).palette.md3.colors.surface @@ -104,7 +105,7 @@ export const ButtonRoot = styled('button', { const labelTextColor = { elevated: (theme.vars || theme).palette.md3.colors.primary, filled: (theme.vars || theme).palette.md3.colors[ - `on${capitalize(ownerState.color ?? 'primary')}` + `on${capitalize(ownerState.color ?? 'primary')}` as keyof MD3ColorSchemeTokens ], filledTonal: (theme.vars || theme).palette.md3.colors.onSecondaryContainer, outlined: (theme.vars || theme).palette.md3.colors[ownerState.color ?? 'primary'], @@ -278,10 +279,10 @@ export const ButtonRoot = styled('button', { // 3. Not sure how to make the tracking work with the CSS variables as there is a calculation needed // '--md-comp-button-label-text-tracking': (theme.vars || theme).typescale.label.large.tracking, // Icon variables default values - '--md-comp-button-icon-color': labelTextColor[ownerState.variant], - '--md-comp-button-hovered-icon-color': labelTextColor[ownerState.variant], // same as default - '--md-comp-button-pressed-icon-color': labelTextColor[ownerState.variant], // same as default - '--md-comp-button-focused-icon-color': labelTextColor[ownerState.variant], // same as default + '--md-comp-button-icon-color': labelTextColor[ownerState.variant ?? 'text'], + '--md-comp-button-hovered-icon-color': labelTextColor[ownerState.variant ?? 'text'], // same as default + '--md-comp-button-pressed-icon-color': labelTextColor[ownerState.variant ?? 'text'], // same as default + '--md-comp-button-focused-icon-color': labelTextColor[ownerState.variant ?? 'text'], // same as default '--md-comp-button-disabled-icon-color': disabledLabelTextColor, // Dynamic variables '--md-comp-button-label-text-line-height': `calc(${ @@ -305,8 +306,6 @@ export const ButtonRoot = styled('button', { MozAppearance: 'none', // Reset WebkitAppearance: 'none', // Reset textDecoration: 'none', - // So we take precedent over the style of a native element. - color: 'inherit', '&::-moz-focus-inner': { borderStyle: 'none', // Remove Firefox dotted outline. }, @@ -315,6 +314,7 @@ export const ButtonRoot = styled('button', { }, padding: '10px 24px', minWidth: 64, + letterSpacing, // Taken from MD2, haven't really found a spec on transitions transition: theme.transitions.create( ['background-color', 'box-shadow', 'border-color', 'color'], @@ -333,10 +333,14 @@ export const ButtonRoot = styled('button', { })`, lineHeight: 'var(--md-comp-button-label-text-line-height)', borderRadius: (theme.vars || theme).shape.borderRadius, - background: `var(--md-comp-button-container-color, ${containerColor[ownerState.variant]})`, - color: `var(--md-comp-button-label-text-color, ${labelTextColor[ownerState.variant]})`, + background: `var(--md-comp-button-container-color, ${ + containerColor[ownerState.variant ?? 'text'] + })`, + color: `var(--md-comp-button-label-text-color, ${ + labelTextColor[ownerState.variant ?? 'text'] + })`, boxShadow: `var(--md-comp-button-container-elevation, ${ - containerElevation[ownerState.variant] + containerElevation[ownerState.variant ?? 'text'] })`, // Outlined varaiant ...(ownerState.variant === 'outlined' && { @@ -365,31 +369,31 @@ export const ButtonRoot = styled('button', { '&:hover': { '--md-comp-button-icon-color': 'var(--md-comp-button-hovered-icon-color)', color: `var(--md-comp-button-hovered-label-text-color, ${ - labelTextColor[ownerState.variant] + labelTextColor[ownerState.variant ?? 'text'] })`, backgroundColor: `var(--md-comp-button-hovered-container-state-layer-color, ${ - hoveredContainerColor[ownerState.variant] + hoveredContainerColor[ownerState.variant ?? 'text'] })`, boxShadow: `var(--md-comp-button-hovered-container-elevation, ${ - hoveredContainerElevation[ownerState.variant] + hoveredContainerElevation[ownerState.variant ?? 'text'] })`, }, '&:active': { '--md-comp-button-icon-color': 'var(--md-comp-button-pressed-icon-color)', color: `var(--md-comp-button-pressed-label-text-color, ${ - labelTextColor[ownerState.variant] + labelTextColor[ownerState.variant ?? 'text'] })`, backgroundColor: `var(--md-comp-button-pressed-container-state-layer-color, ${ - pressedContainerColor[ownerState.variant] + pressedContainerColor[ownerState.variant ?? 'text'] })`, }, [`&.${buttonClasses.focusVisible}`]: { '--md-comp-button-icon-color': 'var(--md-comp-button-focused-icon-color)', color: `var(--md-comp-button-focused-label-text-color, ${ - labelTextColor[ownerState.variant] + labelTextColor[ownerState.variant ?? 'text'] })`, backgroundColor: `var(--md-comp-button-focused-container-state-layer-color, ${ - focusedContainerColor[ownerState.variant] + focusedContainerColor[ownerState.variant ?? 'text'] })`, }, [`&.${buttonClasses.disabled}`]: { @@ -399,7 +403,7 @@ export const ButtonRoot = styled('button', { cursor: 'default', color: `var(--md-comp-button-disabled-label-text-color, ${disabledLabelTextColor})`, background: `var(--md-comp-button-disabled-container-color, ${ - disabeldContainerColor[ownerState.variant] + disabeldContainerColor[ownerState.variant ?? 'text'] })`, boxShadow: 'var(--md-comp-button-disabled-container-elevation, none)', // Should be md.sys.elevation.level0 ...(ownerState.variant === 'outlined' && { @@ -421,7 +425,7 @@ const ButtonStartIcon = styled('span', { return [styles.startIcon, styles[`iconSize${capitalize(ownerState.size)}`]]; }, -})(({ ownerState }) => ({ +})<{ ownerState: ButtonOwnerState }>(({ ownerState }) => ({ display: 'inherit', marginRight: 8, marginLeft: -8, @@ -439,7 +443,7 @@ const ButtonEndIcon = styled('span', { return [styles.endIcon, styles[`iconSize${capitalize(ownerState.size)}`]]; }, -})(({ ownerState }) => ({ +})<{ ownerState: ButtonOwnerState }>(({ ownerState }) => ({ display: 'inherit', marginRight: -8, marginLeft: 8, @@ -449,11 +453,12 @@ const ButtonEndIcon = styled('span', { ...commonIconStyles(ownerState), })); -const Button = React.forwardRef(function Button(inProps, ref) { +const Button = React.forwardRef(function Button< + BaseComponentType extends React.ElementType = ButtonTypeMap['defaultComponent'], +>(inProps: ButtonProps, ref: React.ForwardedRef) { const props = useThemeProps({ props: inProps, name: 'MuiButton' }); const { action, - centerRipple = false, children, className, color = 'primary', @@ -487,7 +492,7 @@ const Button = React.forwardRef(function Button(inProps, ref) { ...other } = props; - const buttonRef = React.useRef(null); + const buttonRef = React.useRef(null); const handleRef = useForkRef(buttonRef, ref); let ComponentProp = component; @@ -502,9 +507,9 @@ const Button = React.forwardRef(function Button(inProps, ref) { href: props.href, onFocusVisible, tabIndex, + // @ts-ignore to: props.to, type, - component: ComponentProp, ref: handleRef, }); @@ -513,7 +518,7 @@ const Button = React.forwardRef(function Button(inProps, ref) { () => ({ focusVisible: () => { setFocusVisible(true); - buttonRef.current.focus(); + buttonRef.current!.focus(); }, }), [setFocusVisible], @@ -521,7 +526,6 @@ const Button = React.forwardRef(function Button(inProps, ref) { const ownerState = { ...props, - centerRipple, color, component, disabled, @@ -553,7 +557,7 @@ const Button = React.forwardRef(function Button(inProps, ref) { as={ComponentProp} className={clsx(classes.root, className)} ownerState={ownerState} - {...getRootProps(props)} + {...(getRootProps(props) as UseButtonRootSlotOwnProps)} {...other} > {startIcon} @@ -561,7 +565,7 @@ const Button = React.forwardRef(function Button(inProps, ref) { {endIcon} ); -}); +}) as ExtendButton; Button.propTypes /* remove-proptypes */ = { // ----------------------------- Warning -------------------------------- diff --git a/packages/mui-material-next/src/Button/Button.d.ts b/packages/mui-material-next/src/Button/Button.types.ts similarity index 74% rename from packages/mui-material-next/src/Button/Button.d.ts rename to packages/mui-material-next/src/Button/Button.types.ts index a193c2b0729cc3..46d81c3eafc0d9 100644 --- a/packages/mui-material-next/src/Button/Button.d.ts +++ b/packages/mui-material-next/src/Button/Button.types.ts @@ -1,13 +1,8 @@ import * as React from 'react'; -import { - DistributiveOmit, - OverridableComponent, - OverridableStringUnion, - OverridableTypeMap, - OverrideProps, -} from '@mui/types'; +import { OverridableStringUnion } from '@mui/types'; import { SxProps } from '@mui/system'; -import { Theme } from '@mui/material'; +import { Theme } from '../styles'; +import { OverrideProps, OverridableComponent, OverridableTypeMap } from '@mui/types'; import { ButtonClasses } from './buttonClasses'; export interface ButtonPropsVariantOverrides {} @@ -20,13 +15,36 @@ export interface ButtonActions { focusVisible(): void; } -export interface ButtonTypeMap

{ +export type ButtonTypeMap

= { props: P & { /** * A ref for imperative actions. - * It exposes the `focusVisible()` action. + * It currently only supports `focusVisible()` action. */ action?: React.Ref; + /** + * This prop can help identify which element has keyboard focus. + * The class name will be applied when the element gains the focus through keyboard interaction. + * It's a polyfill for the [CSS :focus-visible selector](https://drafts.csswg.org/selectors-4/#the-focus-visible-pseudo). + * The rationale for using this feature [is explained here](https://github.com/WICG/focus-visible/blob/HEAD/explainer.md). + * A [polyfill can be used](https://github.com/WICG/focus-visible) to apply a `focus-visible` class to other components + * if needed. + */ + focusVisibleClassName?: string; + /** + * The component used to render a link when the `href` prop is provided. + * @default 'a' + */ + LinkComponent?: React.ElementType; + /** + * Callback fired when the component is focused with a keyboard. + * We trigger a `onFocus` callback too. + */ + onFocusVisible?: React.FocusEventHandler; + /** + * @default 0 + */ + tabIndex?: NonNullable['tabIndex']>; /** * The content of the component. */ @@ -36,13 +54,12 @@ export interface ButtonTypeMap

{ */ classes?: Partial; /** - * The color of the component. It supports those theme colors that make sense for this component. + * The color of the component. + * It supports both default and custom theme colors, which can be added as shown in the + * [palette customization guide](https://mui.com/material-ui/customization/palette/#adding-new-colors). * @default 'primary' */ - color?: OverridableStringUnion< - 'inherit' | 'primary' | 'secondary' | 'success' | 'error' | 'info' | 'warning', - ButtonPropsColorOverrides - >; + color?: OverridableStringUnion<'primary' | 'secondary' | 'tertiary', ButtonPropsColorOverrides>; /** * If `true`, the component is disabled. * @default false @@ -54,23 +71,14 @@ export interface ButtonTypeMap

{ */ disableElevation?: boolean; /** - * Element placed after the children. - */ - endIcon?: React.ReactNode; - /** - * If `true`, allows a disabled button to receive focus. + * If `true`, the keyboard focus ripple is disabled. * @default false */ - focusableWhenDisabled?: boolean; + disableFocusRipple?: boolean; /** - * This prop can help identify which element has keyboard focus. - * The class name will be applied when the element gains the focus through keyboard interaction. - * It's a polyfill for the [CSS :focus-visible selector](https://drafts.csswg.org/selectors-4/#the-focus-visible-pseudo). - * The rationale for using this feature [is explained here](https://github.com/WICG/focus-visible/blob/HEAD/explainer.md). - * A [polyfill can be used](https://github.com/WICG/focus-visible) to apply a `focus-visible` class to other components - * if needed. + * Element placed after the children. */ - focusVisibleClassName?: string; + endIcon?: React.ReactNode; /** * If `true`, the button will take up the full width of its container. * @default false @@ -81,16 +89,6 @@ export interface ButtonTypeMap

{ * If defined, an `a` element will be used as the root node. */ href?: string; - /** - * The component used to render a link when the `href` prop is provided. - * @default 'a' - */ - LinkComponent?: React.ElementType; - /** - * Callback fired when the component is focused with a keyboard. - * We trigger a `onFocus` callback too. - */ - onFocusVisible?: React.FocusEventHandler; /** * The size of the component. * `small` is equivalent to the dense button styling. @@ -105,10 +103,6 @@ export interface ButtonTypeMap

{ * The system prop that allows defining system overrides as well as additional CSS styles. */ sx?: SxProps; - /** - * @default 0 - */ - tabIndex?: NonNullable['tabIndex']>; /** * The variant to use. * @default 'text' @@ -119,43 +113,31 @@ export interface ButtonTypeMap

{ >; }; defaultComponent: D; +}; + +export interface ButtonOwnerState extends ButtonProps { + /** + * If `true`, the button's focus is visible. + */ + focusVisible?: boolean; } /** - * utility to create component types that inherit props from Button. + * utility to create component types that inherit props from ButtonBase. * This component has an additional overload if the `href` prop is set which * can make extension quite tricky */ export interface ExtendButtonTypeMap { - props: M['props'] & - (M['props'] extends { classes?: Record } - ? DistributiveOmit - : ButtonTypeMap['props']); + props: M['props'] & ButtonTypeMap['props']; defaultComponent: M['defaultComponent']; } export type ExtendButton = (( props: { href: string } & OverrideProps, 'a'>, ) => JSX.Element) & - OverridableComponent>; - -/** - * - * Demos: - * - * - [Button group](https://mui.com/material-ui/react-button-group/) - * - [Button](https://mui.com/material-ui/react-button/) - * - * API: - * - * - [Button API](https://mui.com/api/button/) - * - inherits [ButtonBase API](https://mui.com/api/button-base/) - */ -declare const Button: ExtendButton; + OverridableComponent> & { propTypes?: any }; export type ButtonProps< D extends React.ElementType = ButtonTypeMap['defaultComponent'], P = {}, > = OverrideProps, D>; - -export default Button; diff --git a/packages/mui-material-next/src/styles/index.ts b/packages/mui-material-next/src/styles/index.ts new file mode 100644 index 00000000000000..9f3ee8494288a9 --- /dev/null +++ b/packages/mui-material-next/src/styles/index.ts @@ -0,0 +1,137 @@ +// Needs to be keep in sync with @mui/material/MaterialYouModuleAugmentation +import { Theme as MD2Theme } from '@mui/material/styles'; + +interface MD3Tones { + 0: string; + 10: string; + 20: string; + 30: string; + 40: string; + 50: string; + 60: string; + 70: string; + 80: string; + 90: string; + 95: string; + 99: string; + 100: string; +} +export interface MD3Palettes { + primary: MD3Tones; + secondary: MD3Tones; + tertiary: MD3Tones; + neutral: MD3Tones; + neutralVariant: MD3Tones; + error: MD3Tones; + common: { + black: string; + white: string; + }; +} + +export interface MD3PalettesOptions extends Partial {} + +export interface MD3ColorSchemeTokens { + primary: string; + onPrimary: string; + primaryContainer: string; + onPrimaryContainer: string; + + secondary: string; + onSecondary: string; + secondaryContainer: string; + onSecondaryContainer: string; + + tertiary: string; + onTertiary: string; + tertiaryContainer: string; + onTertiaryContainer: string; + + error: string; + onError: string; + errorContainer: string; + onErrorContainer: string; + + background: string; + onBackground: string; + + surface: string; + onSurface: string; + surfaceVariant: string; + onSurfaceVariant: string; + + inverseSurface: string; + inverseOnSurface: string; + inversePrimary: string; + surfaceTint?: string; + + outline: string; + shadow: string; + + // channels + primaryChannel: string; + secondaryChannel: string; + tertiaryChannel: string; + onSurfaceChannel: string; + secondaryContainerChannel: string; +} + +export interface MD3ColorSchemeTokensOptions extends Partial {} + +export interface MD3States { + hover: { + stateLayerOpacity: number; + }; + focus: { + stateLayerOpacity: number; + }; + pressed: { + stateLayerOpacity: number; + }; + dragged: { + stateLayerOpacity: number; + }; +} + +export interface TypescaleValue { + small: { + family: string; + weight: string; + }; + medium: { + family: string; + weight: string; + }; + large: { + family: string; + weight: string; + lineHeight: number; + size: number; + tracking: number; + }; +} + +export interface MD3Typescale { + label: TypescaleValue; + body: TypescaleValue; + headline: TypescaleValue; + display: TypescaleValue; +} + +export interface Shapes { + borderRadius: number; +} + +export interface Theme extends MD2Theme { + useMaterialYou?: boolean; + palette: MD2Theme['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; + state: MD3States; + typescale: MD3Typescale; + shape: Shapes; + vars?: { + palette: MD2Theme['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; + state: MD3States; + typescale: MD3Typescale; + shape: Shapes; + }; +} diff --git a/packages/mui-material/src/MaterialYouModuleAugmentation.ts b/packages/mui-material/src/MaterialYouModuleAugmentation.ts new file mode 100644 index 00000000000000..b807b7862c3859 --- /dev/null +++ b/packages/mui-material/src/MaterialYouModuleAugmentation.ts @@ -0,0 +1,87 @@ +interface MD3Tones { + 0: string; + 10: string; + 20: string; + 30: string; + 40: string; + 50: string; + 60: string; + 70: string; + 80: string; + 90: string; + 95: string; + 99: string; + 100: string; +} +export interface MD3Palettes { + primary: MD3Tones; + secondary: MD3Tones; + tertiary: MD3Tones; + neutral: MD3Tones; + neutralVariant: MD3Tones; + error: MD3Tones; + common: { + black: string; + white: string; + }; +} + +export interface MD3PalettesOptions extends Partial {} + +export interface MD3ColorSchemeTokens { + primary: string; + onPrimary: string; + primaryContainer: string; + onPrimaryContainer: string; + + secondary: string; + onSecondary: string; + secondaryContainer: string; + onSecondaryContainer: string; + + tertiary: string; + onTertiary: string; + tertiaryContainer: string; + onTertiaryContainer: string; + + error: string; + onError: string; + errorContainer: string; + onErrorContainer: string; + + background: string; + onBackground: string; + + surface: string; + onSurface: string; + surfaceVariant: string; + onSurfaceVariant: string; + + inverseSurface: string; + inverseOnSurface: string; + inversePrimary: string; + surfaceTint?: string; + + outline: string; + shadow: string; +} + +export interface MD3ColorSchemeTokensOptions extends Partial {} + +declare module '@mui/material/styles' { + interface Theme { + useMaterialYou?: boolean; + } + + interface ThemeOptions { + useMaterialYou?: boolean; + } + + interface Palette { + md3: MD3Palettes & { colors: MD3ColorSchemeTokens }; + } + + interface PaletteOptions { + md3?: MD3PalettesOptions & { colors?: MD3ColorSchemeTokensOptions }; + } +} From dca1c6051a797e8eb73ce317255885f5e0fb7a93 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 19 Oct 2022 16:44:13 +0200 Subject: [PATCH 07/49] fix import --- docs/pages/experiments/md3/index.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/pages/experiments/md3/index.js b/docs/pages/experiments/md3/index.js index e859d6f2672ecf..39340635da438e 100644 --- a/docs/pages/experiments/md3/index.js +++ b/docs/pages/experiments/md3/index.js @@ -9,7 +9,7 @@ import { useColorScheme, Stack, } from '@mui/material'; -import { unstable_capitalize as capitalize } from 'packages/mui-utils'; +import { unstable_capitalize as capitalize } from '@mui/utils'; import DeleteIcon from '@mui/icons-material/Delete'; import SendIcon from '@mui/icons-material/Send'; import { Button } from '@mui/material-next'; From 61ebd28954370a047111bac553dbafbfcb443aec Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 19 Oct 2022 17:00:23 +0200 Subject: [PATCH 08/49] Fix lint & prettier --- .../mui-material-next/src/Button/Button.tsx | 32 +++++-------------- .../src/Button/Button.types.ts | 8 +++-- 2 files changed, 14 insertions(+), 26 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index c4340f76f5feb6..a591e21d7d7ca7 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -7,11 +7,11 @@ import { unstable_capitalize as capitalize, unstable_useForkRef as useForkRef, } from '@mui/utils'; -import { MD3ColorSchemeTokens, Theme } from '../styles'; import { useButton, UseButtonRootSlotOwnProps } from '@mui/base/ButtonUnstyled'; import composeClasses from '@mui/base/composeClasses'; import { useThemeProps, alpha } from '@mui/system'; -import styled, { rootShouldForwardProp } from '@mui/material/styles/styled'; +import { styled } from '@mui/material/styles'; +import { MD3ColorSchemeTokens, Theme } from '../styles'; import buttonClasses, { getButtonUtilityClass } from './buttonClasses'; import { ButtonProps, ExtendButton, ButtonTypeMap, ButtonOwnerState } from './Button.types'; @@ -74,7 +74,6 @@ const commonIconStyles = ({ size }: ButtonOwnerState) => ({ }); export const ButtonRoot = styled('button', { - shouldForwardProp: (prop) => rootShouldForwardProp(prop as string) || prop === 'classes', name: 'MuiButton', slot: 'Root', overridesResolver: (props, styles) => { @@ -570,27 +569,25 @@ const Button = React.forwardRef(function Button< Button.propTypes /* remove-proptypes */ = { // ----------------------------- Warning -------------------------------- // | These PropTypes are generated from the TypeScript type definitions | - // | To update them edit the d.ts file and run "yarn proptypes" | + // | To update them edit TypeScript types and run "yarn proptypes" | // ---------------------------------------------------------------------- /** * A ref for imperative actions. - * It exposes the `focusVisible()` action. + * It currently only supports `focusVisible()` action. */ action: refType, /** * The content of the component. */ children: PropTypes.node, - /** - * Override or extend the styles applied to the component. - */ - classes: PropTypes.object, /** * @ignore */ className: PropTypes.string, /** - * The color of the component. It supports those theme colors that make sense for this component. + * The color of the component. + * It supports both default and custom theme colors, which can be added as shown in the + * [palette customization guide](https://mui.com/material-ui/customization/palette/#adding-new-colors). * @default 'primary' */ color: PropTypes /* @typescript-to-proptypes-ignore */.oneOfType([ @@ -616,11 +613,6 @@ Button.propTypes /* remove-proptypes */ = { * Element placed after the children. */ endIcon: PropTypes.node, - /** - * If `true`, allows a disabled button to receive focus. - * @default false - */ - focusableWhenDisabled: PropTypes.bool, /** * @ignore */ @@ -710,14 +702,6 @@ Button.propTypes /* remove-proptypes */ = { * Element placed before the children. */ startIcon: PropTypes.node, - /** - * The system prop that allows defining system overrides as well as additional CSS styles. - */ - sx: PropTypes.oneOfType([ - PropTypes.arrayOf(PropTypes.oneOfType([PropTypes.func, PropTypes.object, PropTypes.bool])), - PropTypes.func, - PropTypes.object, - ]), /** * @default 0 */ @@ -734,6 +718,6 @@ Button.propTypes /* remove-proptypes */ = { PropTypes.oneOf(['text', 'outlined', 'filled', 'filledTonal', 'elevated']), PropTypes.string, ]), -}; +} as any; export default Button; diff --git a/packages/mui-material-next/src/Button/Button.types.ts b/packages/mui-material-next/src/Button/Button.types.ts index 46d81c3eafc0d9..592f220d7f3bdb 100644 --- a/packages/mui-material-next/src/Button/Button.types.ts +++ b/packages/mui-material-next/src/Button/Button.types.ts @@ -1,8 +1,12 @@ import * as React from 'react'; -import { OverridableStringUnion } from '@mui/types'; +import { + OverridableStringUnion, + OverrideProps, + OverridableComponent, + OverridableTypeMap, +} from '@mui/types'; import { SxProps } from '@mui/system'; import { Theme } from '../styles'; -import { OverrideProps, OverridableComponent, OverridableTypeMap } from '@mui/types'; import { ButtonClasses } from './buttonClasses'; export interface ButtonPropsVariantOverrides {} From e81a363a2c73feca3ad134987b0a66bbeee47be2 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 11:02:11 +0200 Subject: [PATCH 09/49] Fix tsx issues --- packages/mui-material-next/src/Button/Button.spec.tsx | 4 ++-- packages/mui-material-next/src/Button/index.ts | 2 ++ 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.spec.tsx b/packages/mui-material-next/src/Button/Button.spec.tsx index ccc8462fb891a4..f8b4b519a98a4a 100644 --- a/packages/mui-material-next/src/Button/Button.spec.tsx +++ b/packages/mui-material-next/src/Button/Button.spec.tsx @@ -14,11 +14,11 @@ const FakeIcon =

Icon
; const ButtonTest = () => (
- + - + diff --git a/packages/mui-material-next/src/Button/index.ts b/packages/mui-material-next/src/Button/index.ts index 8946132d8d8701..176aaa81470666 100644 --- a/packages/mui-material-next/src/Button/index.ts +++ b/packages/mui-material-next/src/Button/index.ts @@ -1,5 +1,7 @@ export { default } from './Button'; export * from './Button'; +export * from './Button.types'; + export { default as buttonClasses } from './buttonClasses'; export * from './buttonClasses'; From 545b6469309dae8886308b30e23d956420d7285a Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 12:34:16 +0200 Subject: [PATCH 10/49] Fix regression tests --- .../fixtures/ButtonNext/IconLabelButtonsNext.js | 10 +++++----- .../fixtures/ButtonNext/MultilineButtonNext.js | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js b/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js index dc7748b6c95ec3..5bf13d5f356586 100644 --- a/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js +++ b/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js @@ -6,19 +6,19 @@ import SendIcon from '@mui/icons-material/Send'; export default function IconLabelButtonsNext() { return (
- - - - -
diff --git a/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js b/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js index 43a827747edf0b..546607ecc4db32 100644 --- a/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js +++ b/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js @@ -3,7 +3,7 @@ import Button from '@mui/material-next/Button'; export default function MultilineButtonNext() { return ( - ))} @@ -66,7 +70,7 @@ const DemoComponents = () => { {variants.map((variant) => ( ))} @@ -74,21 +78,21 @@ const DemoComponents = () => { {colors.map((color) => ( ))} {colors.map((color) => ( ))} {colors.map((color) => ( ))} @@ -117,14 +121,14 @@ const DemoComponents = () => { {sizes.map((size) => ( ))} {sizes.map((size) => ( ))} @@ -132,24 +136,17 @@ const DemoComponents = () => { ); }; -const cssVarsTheme = extendMD3Theme(); - -const lightTheme = createMD3Theme(); -const darkTheme = createMD3Theme({ palette: { mode: 'dark' } }); +// default MD3 theme +const cssVarsTheme = extendTheme(); export default function App() { - const [mode, setMode] = React.useState('light'); + const [_, setMode] = React.useState('light'); return ( -

Css variables - Material You theme

- -

Theme provider - Material You theme

- -
); } diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index a591e21d7d7ca7..aadf4c5312741b 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -10,8 +10,7 @@ import { import { useButton, UseButtonRootSlotOwnProps } from '@mui/base/ButtonUnstyled'; import composeClasses from '@mui/base/composeClasses'; import { useThemeProps, alpha } from '@mui/system'; -import { styled } from '@mui/material/styles'; -import { MD3ColorSchemeTokens, Theme } from '../styles'; +import { MD3ColorSchemeTokens, styled } from '../styles'; import buttonClasses, { getButtonUtilityClass } from './buttonClasses'; import { ButtonProps, ExtendButton, ButtonTypeMap, ButtonOwnerState } from './Button.types'; @@ -90,7 +89,7 @@ export const ButtonRoot = styled('button', { ownerState.fullWidth && styles.fullWidth, ]; }, -})<{ ownerState: ButtonOwnerState; theme?: Theme }>(({ ownerState, theme }) => { +})<{ ownerState: ButtonOwnerState }>(({ ownerState, theme }) => { const containerColor = { elevated: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${ (theme.vars || theme).palette.md3.colors.surface @@ -556,7 +555,7 @@ const Button = React.forwardRef(function Button< as={ComponentProp} className={clsx(classes.root, className)} ownerState={ownerState} - {...(getRootProps(props) as UseButtonRootSlotOwnProps)} + {...getRootProps()} {...other} > {startIcon} diff --git a/packages/mui-material-next/src/styles/Theme.types.ts b/packages/mui-material-next/src/styles/Theme.types.ts new file mode 100644 index 00000000000000..4ea7e882dcec6f --- /dev/null +++ b/packages/mui-material-next/src/styles/Theme.types.ts @@ -0,0 +1,155 @@ +// Needs to be keep in sync with @mui/material/MaterialYouModuleAugmentation +import { + CssVarsTheme as MD2Theme, + SupportedColorScheme, + ColorSystemOptions as MD2ColorSystemOptions, + CssVarsThemeOptions as MD2CssVarsThemeOptions, +} from '@mui/material/styles'; + +export interface ColorSystemOptions extends Omit { + palette?: MD2ColorSystemOptions['palette'] & { + md3?: MD3Palettes & { colors: MD3ColorSchemeTokens }; + }; +} + +export interface CssVarsThemeOptions extends Omit { + /** + * Color schemes configuration + */ + colorSchemes?: Partial>; +} + +interface MD3Tones { + 0: string; + 10: string; + 20: string; + 30: string; + 40: string; + 50: string; + 60: string; + 70: string; + 80: string; + 90: string; + 95: string; + 99: string; + 100: string; +} +export interface MD3Palettes { + primary: MD3Tones; + secondary: MD3Tones; + tertiary: MD3Tones; + neutral: MD3Tones; + neutralVariant: MD3Tones; + error: MD3Tones; + common: { + black: string; + white: string; + }; +} + +export interface MD3PalettesOptions extends Partial {} + +export interface MD3ColorSchemeTokens { + primary: string; + onPrimary: string; + primaryContainer: string; + onPrimaryContainer: string; + + secondary: string; + onSecondary: string; + secondaryContainer: string; + onSecondaryContainer: string; + + tertiary: string; + onTertiary: string; + tertiaryContainer: string; + onTertiaryContainer: string; + + error: string; + onError: string; + errorContainer: string; + onErrorContainer: string; + + background: string; + onBackground: string; + + surface: string; + onSurface: string; + surfaceVariant: string; + onSurfaceVariant: string; + + inverseSurface: string; + inverseOnSurface: string; + inversePrimary: string; + surfaceTint?: string; + + outline: string; + shadow: string; + + // channels + primaryChannel: string; + secondaryChannel: string; + tertiaryChannel: string; + onSurfaceChannel: string; + secondaryContainerChannel: string; +} + +export interface MD3ColorSchemeTokensOptions extends Partial {} + +export interface MD3States { + hover: { + stateLayerOpacity: number; + }; + focus: { + stateLayerOpacity: number; + }; + pressed: { + stateLayerOpacity: number; + }; + dragged: { + stateLayerOpacity: number; + }; +} + +export interface TypescaleValue { + small: { + family: string; + weight: string; + }; + medium: { + family: string; + weight: string; + }; + large: { + family: string; + weight: string; + lineHeight: number; + size: number; + tracking: number; + }; +} + +export interface MD3Typescale { + label: TypescaleValue; + body: TypescaleValue; + headline: TypescaleValue; + display: TypescaleValue; +} + +export interface Shapes { + borderRadius: number; +} + +export interface Theme extends Omit { + useMaterialYou?: boolean; + palette: MD2Theme['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; + state: MD3States; + typescale: MD3Typescale; + shape: Shapes; + vars: MD2Theme['vars'] & { + palette: MD2Theme['vars']['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; + state: MD3States; + typescale: MD3Typescale; + shape: Shapes; + }; +} diff --git a/packages/mui-material-next/src/styles/createDarkColorScheme.js b/packages/mui-material-next/src/styles/createDarkColorScheme.js new file mode 100644 index 00000000000000..4ea01f9757375d --- /dev/null +++ b/packages/mui-material-next/src/styles/createDarkColorScheme.js @@ -0,0 +1,35 @@ +// convert all these values to CSS vars +const createDarkColorScheme = (getCssVar, palette) => ({ + colors: { + surfaceTint: getCssVar('palette-md3-primary-40', palette.primary[40]), + onErrorContainer: getCssVar('palette-md3-error-80', palette.error[80]), + onError: getCssVar('palette-md3-error-20', palette.error[20]), + errorContainer: getCssVar('palette-md3-error-30', palette.error[30]), + onTertiaryContainer: getCssVar('palette-md3-tertiary-90', palette.tertiary[90]), + onTertiary: getCssVar('palette-md3-tertiary-20', palette.tertiary[20]), + tertiaryContainer: getCssVar('palette-md3-tertiary-30', palette.tertiary[30]), + tertiary: getCssVar('palette-md3-tertiary-80', palette.tertiary[80]), + shadow: getCssVar('palette-md3-common-black', palette.common.black), + error: getCssVar('palette-md3-error-80', palette.error[80]), + outline: getCssVar('palette-md3-neutralVariant-60', palette.neutralVariant[60]), + onBackground: getCssVar('palette-md3-neutral-90', palette.neutral[90]), + background: getCssVar('palette-md3-neutral-10', palette.neutral[10]), + inverseOnSurface: getCssVar('palette-md3-neutral-20', palette.neutral[20]), + inverseSurface: getCssVar('palette-md3-neutral-90', palette.neutral[90]), + onSurfaceVariant: getCssVar('palette-md3-neutralVariant-80', palette.neutralVariant[80]), + onSurface: getCssVar('palette-md3-neutral-90', palette.neutral[90]), + surfaceVariant: getCssVar('palette-md3-neutralVariant-30', palette.neutralVariant[30]), + surface: getCssVar('palette-md3-neutral-10', palette.neutral[10]), + onSecondaryContainer: getCssVar('palette-md3-secondary-90', palette.secondary[90]), + onSecondary: getCssVar('palette-md3-secondary-20', palette.secondary[20]), + secondaryContainer: getCssVar('palette-md3-secondary-30', palette.secondary[30]), + secondary: getCssVar('palette-md3-secondary-80', palette.secondary[80]), + inversePrimary: getCssVar('palette-md3-primary-40', palette.primary[40]), + onPrimaryContainer: getCssVar('palette-md3-primary-90', palette.primary[90]), + onPrimary: getCssVar('palette-md3-primary-20', palette.primary[20]), + primaryContainer: getCssVar('palette-md3-primary-30', palette.primary[30]), + primary: getCssVar('palette-md3-primary-80', palette.primary[80]), + }, +}); + +export default createDarkColorScheme; diff --git a/packages/mui-material-next/src/styles/createLightColorScheme.js b/packages/mui-material-next/src/styles/createLightColorScheme.js new file mode 100644 index 00000000000000..9d3de968cf7218 --- /dev/null +++ b/packages/mui-material-next/src/styles/createLightColorScheme.js @@ -0,0 +1,35 @@ +// convert all these values to CSS vars +const createLightColorScheme = (getCssVar, palette) => ({ + colors: { + surfaceTint: getCssVar('palette-md3-primary-40', palette.primary[40]), + onErrorContainer: getCssVar('palette-md3-error-10', palette.error[10]), + onError: getCssVar('palette-md3-error-100', palette.error[100]), + errorContainer: getCssVar('palette-md3-error-90', palette.error[90]), + onTertiaryContainer: getCssVar('palette-md3-tertiary-10', palette.tertiary[10]), + onTertiary: getCssVar('palette-md3-tertiary-100', palette.tertiary[100]), + tertiaryContainer: getCssVar('palette-md3-tertiary-90', palette.tertiary[90]), + tertiary: getCssVar('palette-md3-tertiary-40', palette.tertiary[40]), + shadow: getCssVar('palette-md3-common-black', palette.common.black), + error: getCssVar('palette-md3-error-40', palette.error[40]), + outline: getCssVar('palette-md3-neutralVariant-50', palette.neutralVariant[50]), + onBackground: getCssVar('palette-md3-neutral-10', palette.neutral[10]), + background: getCssVar('palette-md3-neutral-99', palette.neutral[99]), + inverseOnSurface: getCssVar('palette-md3-neutral-95', palette.neutral[95]), + inverseSurface: getCssVar('palette-md3-neutral-20', palette.neutral[20]), + onSurfaceVariant: getCssVar('palette-md3-neutralVariant-30', palette.neutralVariant[30]), + onSurface: getCssVar('palette-md3-neutral-10', palette.neutral[10]), + surfaceVariant: getCssVar('palette-md3-neutralVariant-90', palette.neutralVariant[90]), + surface: getCssVar('palette-md3-neutral-99', palette.neutral[99]), + onSecondaryContainer: getCssVar('palette-md3-secondary-10', palette.secondary[10]), + onSecondary: getCssVar('palette-md3-secondary-100', palette.secondary[100]), + secondaryContainer: getCssVar('palette-md3-secondary-90', palette.secondary[90]), + secondary: getCssVar('palette-md3-secondary-40', palette.secondary[40]), + inversePrimary: getCssVar('palette-md3-primary-80', palette.primary[80]), + onPrimaryContainer: getCssVar('palette-md3-primary-10', palette.primary[10]), + onPrimary: getCssVar('palette-md3-primary-100', palette.primary[100]), + primaryContainer: getCssVar('palette-md3-primary-90', palette.primary[90]), + primary: getCssVar('palette-md3-primary-40', palette.primary[40]), + }, +}); + +export default createLightColorScheme; diff --git a/packages/mui-material/src/styles/md3/createMd3Palette.js b/packages/mui-material-next/src/styles/createMd3Palette.js similarity index 100% rename from packages/mui-material/src/styles/md3/createMd3Palette.js rename to packages/mui-material-next/src/styles/createMd3Palette.js diff --git a/packages/mui-material-next/src/styles/defaultTheme.ts b/packages/mui-material-next/src/styles/defaultTheme.ts new file mode 100644 index 00000000000000..eac9d73ffe7249 --- /dev/null +++ b/packages/mui-material-next/src/styles/defaultTheme.ts @@ -0,0 +1,53 @@ +import { deepmerge } from '@mui/utils'; +import extendTheme from './extendTheme'; +import type { Theme, CssVarsThemeOptions, ColorSystemOptions } from './Theme.types'; + +export const getThemeWithVars = ( + themeInput?: Omit & ColorSystemOptions, +) => { + const { + colorSchemes, + opacity, + overlays, + shape, + state, + typescale, + palette: paletteInput, + ...restTheme + } = extendTheme(themeInput); + const colorSchemePalette = deepmerge( + colorSchemes[paletteInput?.colorScheme || 'light'].palette, + paletteInput, + ); + const { mode = 'light', colorScheme = 'light', ...palette } = colorSchemePalette; + + return { + opacity, + overlays, + shape, + state, + typescale, + ...restTheme, + colorSchemes: { + ...colorSchemes, + [colorScheme]: palette, + }, + palette: { + ...palette, + mode, + colorScheme, + }, + vars: { + opacity, + overlays, + shape, + state, + typescale, + palette, + }, + } as unknown as Theme; +}; + +const defaultTheme = getThemeWithVars(); + +export default defaultTheme; diff --git a/packages/mui-material/src/styles/experimental_extendMD3Theme.js b/packages/mui-material-next/src/styles/extendTheme.ts similarity index 88% rename from packages/mui-material/src/styles/experimental_extendMD3Theme.js rename to packages/mui-material-next/src/styles/extendTheme.ts index a860333e43accd..11d98134ce1ca7 100644 --- a/packages/mui-material/src/styles/experimental_extendMD3Theme.js +++ b/packages/mui-material-next/src/styles/extendTheme.ts @@ -7,24 +7,31 @@ import { emphasize, unstable_createGetCssVar as systemCreateGetCssVar, } from '@mui/system'; -import createThemeWithoutVars from './createTheme'; -import { getOverlayAlpha } from '../Paper/Paper'; -import md3CommonPalette from './md3/palette'; -import createMd3LightColorScheme from './md3/createLightColorScheme'; -import createMd3DarkColorScheme from './md3/createDarkColorScheme'; -import md3Typescale from './md3/typescale'; -import md3Typeface from './md3/typeface'; -import md3State from './md3/states'; +import { + createTheme as createThemeWithoutVars, + getOverlayAlpha, + SupportedColorScheme, + ColorSystem as MD2ColorSystem, + Overlays, +} from '@mui/material/styles'; +import { Theme, MD3Palettes, MD3ColorSchemeTokens, CssVarsThemeOptions } from './Theme.types'; +import md3CommonPalette from './palette'; +import createMd3LightColorScheme from './createLightColorScheme'; +import createMd3DarkColorScheme from './createDarkColorScheme'; +import md3Typescale from './typescale'; +import md3Typeface from './typeface'; +import md3State from './states'; -const defaultDarkOverlays = [...Array(25)].map((_, index) => { +const defaultLightOverlays: Overlays = [...Array(25)].map(() => undefined) as Overlays; +const defaultDarkOverlays: Overlays = [...Array(25)].map((_, index) => { if (index === 0) { return undefined; } const overlay = getOverlayAlpha(index); return `linear-gradient(rgba(255 255 255 / ${overlay}), rgba(255 255 255 / ${overlay}))`; -}); +}) as Overlays; -function assignNode(obj, keys) { +function assignNode(obj: any, keys: string[]) { keys.forEach((k) => { if (!obj[k]) { obj[k] = {}; @@ -32,13 +39,16 @@ function assignNode(obj, keys) { }); } -function setColor(obj, key, defaultValue) { +function setColor(obj: any, key: string, defaultValue: any) { obj[key] = obj[key] || defaultValue; } export const createGetCssVar = (cssVarPrefix = 'mui') => systemCreateGetCssVar(cssVarPrefix); -export default function extendTheme(options = {}, ...args) { +export default function extendTheme( + options: CssVarsThemeOptions & { useMaterialYou?: boolean } = {}, + ...args: any[] +) { const { colorSchemes: colorSchemesInput = {}, cssVarPrefix = 'mui', @@ -49,19 +59,19 @@ export default function extendTheme(options = {}, ...args) { const md3LightPalette = { ...md3CommonPalette, - ...createMd3LightColorScheme(getCssVar), + ...createMd3LightColorScheme(getCssVar, md3CommonPalette), }; const md3DarkPalette = { ...md3CommonPalette, - ...createMd3DarkColorScheme(getCssVar), + ...createMd3DarkColorScheme(getCssVar, md3CommonPalette), }; + // @ts-ignore - it's fine, everything that is not supported will be spread const { palette: lightPalette, ...muiTheme } = createThemeWithoutVars({ ...input, ...(useMaterialYou && { useMaterialYou: true, - palette: { md3: md3LightPalette }, typescale: md3Typescale, typeface: md3Typeface, state: md3State, @@ -70,17 +80,15 @@ export default function extendTheme(options = {}, ...args) { ...input?.shape, }, }), - ...(colorSchemesInput.light && { - palette: { - ...colorSchemesInput.light?.palette, - ...(useMaterialYou && { - md3: { - ...md3LightPalette, - ...colorSchemesInput.light?.palette?.md3, - }, - }), - }, - }), + palette: { + ...(colorSchemesInput.light && colorSchemesInput.light?.palette), + ...(useMaterialYou && { + md3: { + ...md3LightPalette, + ...colorSchemesInput.light?.palette?.md3, + }, + }), + }, }); const { palette: darkPalette } = createThemeWithoutVars({ palette: { @@ -95,7 +103,7 @@ export default function extendTheme(options = {}, ...args) { }, }); - let theme = { + let theme: Theme = { ...muiTheme, cssVarPrefix, getCssVar, @@ -103,6 +111,7 @@ export default function extendTheme(options = {}, ...args) { ...colorSchemesInput, light: { ...colorSchemesInput.light, + // @ts-ignore they are added below palette: lightPalette, opacity: { inputPlaceholder: 0.42, @@ -111,10 +120,11 @@ export default function extendTheme(options = {}, ...args) { switchTrack: 0.38, ...colorSchemesInput.light?.opacity, }, - overlays: colorSchemesInput.light?.overlays || [], + overlays: colorSchemesInput.light?.overlays || defaultLightOverlays, }, dark: { ...colorSchemesInput.dark, + // @ts-ignore they are added below palette: darkPalette, opacity: { inputPlaceholder: 0.5, @@ -129,7 +139,10 @@ export default function extendTheme(options = {}, ...args) { }; Object.keys(theme.colorSchemes).forEach((key) => { - const palette = theme.colorSchemes[key].palette; + const palette = theme.colorSchemes[key as SupportedColorScheme] + .palette as MD2ColorSystem['palette'] & { + md3: MD3Palettes & { colors: MD3ColorSchemeTokens }; + }; // attach black & white channels to common node if (key === 'light') { @@ -307,36 +320,45 @@ export default function extendTheme(options = {}, ...args) { palette.dividerChannel = colorChannel(palette.divider); - Object.keys(palette).forEach((color) => { - const colors = palette[color]; + Object.keys(palette).forEach((c) => { + const color = c as keyof MD2ColorSystem['palette']; + const colors: any = palette[color]; // Color palettes: primary, secondary, error, info, success, and warning if (colors.main) { + // @ts-ignore palette[color].mainChannel = colorChannel(colors.main); } if (colors.light) { + // @ts-ignore palette[color].lightChannel = colorChannel(colors.light); } if (colors.dark) { + // @ts-ignore palette[color].darkChannel = colorChannel(colors.dark); } if (colors.contrastText) { + // @ts-ignore palette[color].contrastTextChannel = colorChannel(colors.contrastText); } // Text colors: text.primary, text.secondary if (colors.primary && typeof colors.primary === 'string') { + // @ts-ignore palette[color].primaryChannel = colorChannel(colors.primary); } if (colors.secondary && typeof colors.primary === 'string') { + // @ts-ignore palette[color].secondaryChannel = colorChannel(colors.secondary); } // Action colors: action.active, action.selected if (colors.active) { + // @ts-ignore palette[color].activeChannel = colorChannel(colors.active); } if (colors.selected) { + // @ts-ignore palette[color].selectedChannel = colorChannel(colors.selected); } }); diff --git a/packages/mui-material-next/src/styles/index.ts b/packages/mui-material-next/src/styles/index.ts index 9f3ee8494288a9..026e1621625149 100644 --- a/packages/mui-material-next/src/styles/index.ts +++ b/packages/mui-material-next/src/styles/index.ts @@ -1,137 +1,5 @@ -// Needs to be keep in sync with @mui/material/MaterialYouModuleAugmentation -import { Theme as MD2Theme } from '@mui/material/styles'; - -interface MD3Tones { - 0: string; - 10: string; - 20: string; - 30: string; - 40: string; - 50: string; - 60: string; - 70: string; - 80: string; - 90: string; - 95: string; - 99: string; - 100: string; -} -export interface MD3Palettes { - primary: MD3Tones; - secondary: MD3Tones; - tertiary: MD3Tones; - neutral: MD3Tones; - neutralVariant: MD3Tones; - error: MD3Tones; - common: { - black: string; - white: string; - }; -} - -export interface MD3PalettesOptions extends Partial {} - -export interface MD3ColorSchemeTokens { - primary: string; - onPrimary: string; - primaryContainer: string; - onPrimaryContainer: string; - - secondary: string; - onSecondary: string; - secondaryContainer: string; - onSecondaryContainer: string; - - tertiary: string; - onTertiary: string; - tertiaryContainer: string; - onTertiaryContainer: string; - - error: string; - onError: string; - errorContainer: string; - onErrorContainer: string; - - background: string; - onBackground: string; - - surface: string; - onSurface: string; - surfaceVariant: string; - onSurfaceVariant: string; - - inverseSurface: string; - inverseOnSurface: string; - inversePrimary: string; - surfaceTint?: string; - - outline: string; - shadow: string; - - // channels - primaryChannel: string; - secondaryChannel: string; - tertiaryChannel: string; - onSurfaceChannel: string; - secondaryContainerChannel: string; -} - -export interface MD3ColorSchemeTokensOptions extends Partial {} - -export interface MD3States { - hover: { - stateLayerOpacity: number; - }; - focus: { - stateLayerOpacity: number; - }; - pressed: { - stateLayerOpacity: number; - }; - dragged: { - stateLayerOpacity: number; - }; -} - -export interface TypescaleValue { - small: { - family: string; - weight: string; - }; - medium: { - family: string; - weight: string; - }; - large: { - family: string; - weight: string; - lineHeight: number; - size: number; - tracking: number; - }; -} - -export interface MD3Typescale { - label: TypescaleValue; - body: TypescaleValue; - headline: TypescaleValue; - display: TypescaleValue; -} - -export interface Shapes { - borderRadius: number; -} - -export interface Theme extends MD2Theme { - useMaterialYou?: boolean; - palette: MD2Theme['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; - state: MD3States; - typescale: MD3Typescale; - shape: Shapes; - vars?: { - palette: MD2Theme['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; - state: MD3States; - typescale: MD3Typescale; - shape: Shapes; - }; -} +export * from './Theme.types'; +export * from './extendTheme'; +export { default as extendTheme } from './extendTheme'; +export { default as styled } from './styled'; +export { default as defaultTheme } from './defaultTheme'; diff --git a/packages/mui-material/src/styles/md3/palette.js b/packages/mui-material-next/src/styles/palette.js similarity index 100% rename from packages/mui-material/src/styles/md3/palette.js rename to packages/mui-material-next/src/styles/palette.js diff --git a/packages/mui-material/src/styles/md3/states.js b/packages/mui-material-next/src/styles/states.js similarity index 100% rename from packages/mui-material/src/styles/md3/states.js rename to packages/mui-material-next/src/styles/states.js diff --git a/packages/mui-material-next/src/styles/styled.ts b/packages/mui-material-next/src/styles/styled.ts new file mode 100644 index 00000000000000..ffb0f1ddf7cf3d --- /dev/null +++ b/packages/mui-material-next/src/styles/styled.ts @@ -0,0 +1,9 @@ +import { createStyled } from '@mui/system'; +import { Theme } from './Theme.types'; +import defaultTheme from './defaultTheme'; +// TODO: custom styleFunctionSx will be required +// import styleFunctionSx from './styleFunctionSx'; + +const styled = createStyled({ defaultTheme /* styleFunctionSx */ }); + +export default styled; diff --git a/packages/mui-material/src/styles/md3/typeface.js b/packages/mui-material-next/src/styles/typeface.js similarity index 100% rename from packages/mui-material/src/styles/md3/typeface.js rename to packages/mui-material-next/src/styles/typeface.js diff --git a/packages/mui-material/src/styles/md3/typescale.js b/packages/mui-material-next/src/styles/typescale.js similarity index 100% rename from packages/mui-material/src/styles/md3/typescale.js rename to packages/mui-material-next/src/styles/typescale.js diff --git a/packages/mui-material/src/MaterialYouModuleAugmentation.ts b/packages/mui-material/src/MaterialYouModuleAugmentation.ts deleted file mode 100644 index b807b7862c3859..00000000000000 --- a/packages/mui-material/src/MaterialYouModuleAugmentation.ts +++ /dev/null @@ -1,87 +0,0 @@ -interface MD3Tones { - 0: string; - 10: string; - 20: string; - 30: string; - 40: string; - 50: string; - 60: string; - 70: string; - 80: string; - 90: string; - 95: string; - 99: string; - 100: string; -} -export interface MD3Palettes { - primary: MD3Tones; - secondary: MD3Tones; - tertiary: MD3Tones; - neutral: MD3Tones; - neutralVariant: MD3Tones; - error: MD3Tones; - common: { - black: string; - white: string; - }; -} - -export interface MD3PalettesOptions extends Partial {} - -export interface MD3ColorSchemeTokens { - primary: string; - onPrimary: string; - primaryContainer: string; - onPrimaryContainer: string; - - secondary: string; - onSecondary: string; - secondaryContainer: string; - onSecondaryContainer: string; - - tertiary: string; - onTertiary: string; - tertiaryContainer: string; - onTertiaryContainer: string; - - error: string; - onError: string; - errorContainer: string; - onErrorContainer: string; - - background: string; - onBackground: string; - - surface: string; - onSurface: string; - surfaceVariant: string; - onSurfaceVariant: string; - - inverseSurface: string; - inverseOnSurface: string; - inversePrimary: string; - surfaceTint?: string; - - outline: string; - shadow: string; -} - -export interface MD3ColorSchemeTokensOptions extends Partial {} - -declare module '@mui/material/styles' { - interface Theme { - useMaterialYou?: boolean; - } - - interface ThemeOptions { - useMaterialYou?: boolean; - } - - interface Palette { - md3: MD3Palettes & { colors: MD3ColorSchemeTokens }; - } - - interface PaletteOptions { - md3?: MD3PalettesOptions & { colors?: MD3ColorSchemeTokensOptions }; - } -} diff --git a/packages/mui-material/src/Paper/Paper.js b/packages/mui-material/src/Paper/Paper.js index deab7b6fa7cb80..515f641d02bdcf 100644 --- a/packages/mui-material/src/Paper/Paper.js +++ b/packages/mui-material/src/Paper/Paper.js @@ -5,21 +5,11 @@ import { chainPropTypes, integerPropType } from '@mui/utils'; import { unstable_composeClasses as composeClasses } from '@mui/base'; import { alpha } from '@mui/system'; import styled from '../styles/styled'; +import getOverlayAlpha from '../styles/getOverlayAlpha'; import useThemeProps from '../styles/useThemeProps'; import useTheme from '../styles/useTheme'; import { getPaperUtilityClass } from './paperClasses'; -// Inspired by https://github.com/material-components/material-components-ios/blob/bca36107405594d5b7b16265a5b0ed698f85a5ee/components/Elevation/src/UIColor%2BMaterialElevation.m#L61 -export const getOverlayAlpha = (elevation) => { - let alphaValue; - if (elevation < 1) { - alphaValue = 5.11916 * elevation ** 2; - } else { - alphaValue = 4.5 * Math.log(elevation + 1) + 2; - } - return (alphaValue / 100).toFixed(2); -}; - const useUtilityClasses = (ownerState) => { const { square, elevation, variant, classes } = ownerState; diff --git a/packages/mui-material/src/styles/experimental_createMD3Theme.d.ts b/packages/mui-material/src/styles/experimental_createMD3Theme.d.ts deleted file mode 100644 index bbd4a027325d61..00000000000000 --- a/packages/mui-material/src/styles/experimental_createMD3Theme.d.ts +++ /dev/null @@ -1,13 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -import { ThemeOptions, Theme } from './createTheme'; - -/** - * Generate a Material Design 3 theme based on the options received. - * @param options Takes an incomplete theme object and adds the missing parts. - * @param args Deep merge the arguments with the about to be returned theme. - * @returns A complete, ready-to-use theme object. - */ -export default function experimental_createMD3Theme( - options?: ThemeOptions, - ...args: object[] -): Theme; diff --git a/packages/mui-material/src/styles/experimental_createMD3Theme.js b/packages/mui-material/src/styles/experimental_createMD3Theme.js deleted file mode 100644 index 44436429d35d8f..00000000000000 --- a/packages/mui-material/src/styles/experimental_createMD3Theme.js +++ /dev/null @@ -1,147 +0,0 @@ -import { deepmerge } from '@mui/utils'; -import { generateUtilityClass } from '@mui/base'; -import { createTheme as systemCreateTheme } from '@mui/system'; -import MuiError from '@mui/utils/macros/MuiError.macro'; -import createMixins from './createMixins'; -import createPalette from './createPalette'; -import createTypography from './createTypography'; -import shadows from './shadows'; -import createTransitions from './createTransitions'; -import zIndex from './zIndex'; -import createMd3Palette from './md3/createMd3Palette'; -import md3Typescale from './md3/typescale'; -import md3Typeface from './md3/typeface'; -import md3State from './md3/states'; - -function createTheme(options = {}, ...args) { - const { - breakpoints: breakpointsInput, - mixins: mixinsInput = {}, - spacing: spacingInput, - palette: paletteInput = {}, - transitions: transitionsInput = {}, - typography: typographyInput = {}, - shape: shapeInput, - useMaterialYou = true, - ...other - } = options; - - if (options.vars) { - throw new MuiError( - 'MUI: `vars` is a private field used for CSS variables support.\n' + - 'Please use another name.', - ); - } - - const palette = createPalette(paletteInput); - if (useMaterialYou) { - palette.md3 = createMd3Palette(palette.md3, paletteInput.mode); - } - const systemTheme = systemCreateTheme(options); - - let muiTheme = deepmerge(systemTheme, { - mixins: createMixins(systemTheme.breakpoints, mixinsInput), - palette, - // Don't use [...shadows] until you've verified its transpiled code is not invoking the iterator protocol. - shadows: shadows.slice(), - typography: createTypography(palette, typographyInput), - transitions: createTransitions(transitionsInput), - zIndex: { ...zIndex }, - ...(useMaterialYou && { - useMaterialYou: true, - state: md3State, - typescale: md3Typescale, - typeface: md3Typeface, - shape: { - borderRadius: 100, - ...shapeInput, - }, - }), - }); - - muiTheme = deepmerge(muiTheme, other); - muiTheme = args.reduce((acc, argument) => deepmerge(acc, argument), muiTheme); - - if (process.env.NODE_ENV !== 'production') { - const stateClasses = [ - 'active', - 'checked', - 'completed', - 'disabled', - 'error', - 'expanded', - 'focused', - 'focusVisible', - 'required', - 'selected', - ]; - - const traverse = (node, component) => { - let key; - - // eslint-disable-next-line guard-for-in, no-restricted-syntax - for (key in node) { - const child = node[key]; - if (stateClasses.indexOf(key) !== -1 && Object.keys(child).length > 0) { - if (process.env.NODE_ENV !== 'production') { - const stateClass = generateUtilityClass('', key); - console.error( - [ - `MUI: The \`${component}\` component increases ` + - `the CSS specificity of the \`${key}\` internal state.`, - 'You can not override it like this: ', - JSON.stringify(node, null, 2), - '', - `Instead, you need to use the '&.${stateClass}' syntax:`, - JSON.stringify( - { - root: { - [`&.${stateClass}`]: child, - }, - }, - null, - 2, - ), - '', - 'https://mui.com/r/state-classes-guide', - ].join('\n'), - ); - } - // Remove the style to prevent global conflicts. - node[key] = {}; - } - } - }; - - Object.keys(muiTheme.components).forEach((component) => { - const styleOverrides = muiTheme.components[component].styleOverrides; - - if (styleOverrides && component.indexOf('Mui') === 0) { - traverse(styleOverrides, component); - } - }); - } - - return muiTheme; -} - -let warnedOnce = false; - -export function createMuiTheme(...args) { - if (process.env.NODE_ENV !== 'production') { - if (!warnedOnce) { - warnedOnce = true; - console.error( - [ - 'MUI: the createMuiTheme function was renamed to createTheme.', - '', - "You should use `import { createTheme } from '@mui/material/styles'`", - ].join('\n'), - ); - } - } - - return createTheme(...args); -} - -export default createTheme; diff --git a/packages/mui-material/src/styles/experimental_extendMD3Theme.d.ts b/packages/mui-material/src/styles/experimental_extendMD3Theme.d.ts deleted file mode 100644 index 4961af35245182..00000000000000 --- a/packages/mui-material/src/styles/experimental_extendMD3Theme.d.ts +++ /dev/null @@ -1,13 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -import { Theme } from './createTheme'; -import { CssVarsThemeOptions, CssVarsTheme } from './experimental_extendTheme'; -/** - * Generate a theme based on the options received. - * @param options Takes an incomplete theme object and adds the missing parts. - * @param args Deep merge the arguments with the about to be returned theme. - * @returns A complete, ready-to-use theme object. - */ -export default function experimental_extendMD3Theme( - options?: CssVarsThemeOptions, - ...args: object[] -): Omit & CssVarsTheme; diff --git a/packages/mui-material/src/styles/experimental_extendTheme.d.ts b/packages/mui-material/src/styles/experimental_extendTheme.d.ts index 5ae0ea1cda08e7..5df2204de37c64 100644 --- a/packages/mui-material/src/styles/experimental_extendTheme.d.ts +++ b/packages/mui-material/src/styles/experimental_extendTheme.d.ts @@ -34,6 +34,8 @@ export type SupportedColorScheme = DefaultColorScheme | ExtendedColorScheme; export interface Opacity { inputPlaceholder: number; inputUnderline: number; + switchTrackDisabled: number; + switchTrack: number; } export type Overlays = [ @@ -383,6 +385,16 @@ export interface CssVarsTheme extends ColorSystem { vars: ThemeVars; getCssVar: (field: ThemeCssVar, ...vars: ThemeCssVar[]) => string; getColorSchemeSelector: (colorScheme: SupportedColorScheme) => string; + + // Default theme tokens + spacing: Theme['spacing']; + breakpints: Theme['breakpoints']; + shape: Theme['shape']; + typography: Theme['typography']; + transitions: Theme['transitions']; + shadows: Theme['shadows']; + mixins: Theme['mixins']; + zIndex: Theme['zIndex']; } /** diff --git a/packages/mui-material/src/styles/experimental_extendTheme.js b/packages/mui-material/src/styles/experimental_extendTheme.js index 2628a52a6f450a..ea7b52876c063b 100644 --- a/packages/mui-material/src/styles/experimental_extendTheme.js +++ b/packages/mui-material/src/styles/experimental_extendTheme.js @@ -8,7 +8,7 @@ import { unstable_createGetCssVar as systemCreateGetCssVar, } from '@mui/system'; import createThemeWithoutVars from './createTheme'; -import { getOverlayAlpha } from '../Paper/Paper'; +import getOverlayAlpha from './getOverlayAlpha'; const defaultDarkOverlays = [...Array(25)].map((_, index) => { if (index === 0) { diff --git a/packages/mui-material/src/styles/getOverlayAlpha.ts b/packages/mui-material/src/styles/getOverlayAlpha.ts new file mode 100644 index 00000000000000..c528a101adfe16 --- /dev/null +++ b/packages/mui-material/src/styles/getOverlayAlpha.ts @@ -0,0 +1,12 @@ +// Inspired by https://github.com/material-components/material-components-ios/blob/bca36107405594d5b7b16265a5b0ed698f85a5ee/components/Elevation/src/UIColor%2BMaterialElevation.m#L61 +const getOverlayAlpha = (elevation: number) => { + let alphaValue; + if (elevation < 1) { + alphaValue = 5.11916 * elevation ** 2; + } else { + alphaValue = 4.5 * Math.log(elevation + 1) + 2; + } + return (alphaValue / 100).toFixed(2); +}; + +export default getOverlayAlpha; diff --git a/packages/mui-material/src/styles/index.d.ts b/packages/mui-material/src/styles/index.d.ts index 0760de6d974298..b6870d47403eb0 100644 --- a/packages/mui-material/src/styles/index.d.ts +++ b/packages/mui-material/src/styles/index.d.ts @@ -128,8 +128,6 @@ export type { ThemeVars, ThemeCssVar, ThemeCssVarOverrides, + ColorSystemOptions, } from './experimental_extendTheme'; - -// MD3 -export { default as experimental_createMD3Theme } from './experimental_createMD3Theme'; -export { default as experimental_extendMD3Theme } from './experimental_extendMD3Theme'; +export { default as getOverlayAlpha } from './getOverlayAlpha'; diff --git a/packages/mui-material/src/styles/index.js b/packages/mui-material/src/styles/index.js index 123d96cf686f3c..8c01c3314e37f3 100644 --- a/packages/mui-material/src/styles/index.js +++ b/packages/mui-material/src/styles/index.js @@ -35,7 +35,4 @@ export { default as withTheme } from './withTheme'; export * from './CssVarsProvider'; export { default as experimental_extendTheme } from './experimental_extendTheme'; - -// MD3 -export { default as experimental_createMD3Theme } from './experimental_createMD3Theme'; -export { default as experimental_extendMD3Theme } from './experimental_extendMD3Theme'; +export { default as getOverlayAlpha } from './getOverlayAlpha'; diff --git a/packages/mui-material/src/styles/md3/createDarkColorScheme.js b/packages/mui-material/src/styles/md3/createDarkColorScheme.js deleted file mode 100644 index 003bb33048fa64..00000000000000 --- a/packages/mui-material/src/styles/md3/createDarkColorScheme.js +++ /dev/null @@ -1,35 +0,0 @@ -// convert all these values to CSS vars -const createDarkColorScheme = (getCssVar) => ({ - colors: { - surfaceTint: getCssVar('palette-md3-primary-40'), - onErrorContainer: getCssVar('palette-md3-error-80'), - onError: getCssVar('palette-md3-error-20'), - errorContainer: getCssVar('palette-md3-error-30'), - onTertiaryContainer: getCssVar('palette-md3-tertiary-90'), - onTertiary: getCssVar('palette-md3-tertiary-20'), - tertiaryContainer: getCssVar('palette-md3-tertiary-30'), - tertiary: getCssVar('palette-md3-tertiary-80'), - shadow: getCssVar('palette-md3-common-black'), - error: getCssVar('palette-md3-error-80'), - outline: getCssVar('palette-md3-neutralVariant-60'), - onBackground: getCssVar('palette-md3-neutral-90'), - background: getCssVar('palette-md3-neutral-10'), - inverseOnSurface: getCssVar('palette-md3-neutral-20'), - inverseSurface: getCssVar('palette-md3-neutral-90'), - onSurfaceVariant: getCssVar('palette-md3-neutralVariant-80'), - onSurface: getCssVar('palette-md3-neutral-90'), - surfaceVariant: getCssVar('palette-md3-neutralVariant-30'), - surface: getCssVar('palette-md3-neutral-10'), - onSecondaryContainer: getCssVar('palette-md3-secondary-90'), - onSecondary: getCssVar('palette-md3-secondary-20'), - secondaryContainer: getCssVar('palette-md3-secondary-30'), - secondary: getCssVar('palette-md3-secondary-80'), - inversePrimary: getCssVar('palette-md3-primary-40'), - onPrimaryContainer: getCssVar('palette-md3-primary-90'), - onPrimary: getCssVar('palette-md3-primary-20'), - primaryContainer: getCssVar('palette-md3-primary-30'), - primary: getCssVar('palette-md3-primary-80'), - }, -}); - -export default createDarkColorScheme; diff --git a/packages/mui-material/src/styles/md3/createLightColorScheme.js b/packages/mui-material/src/styles/md3/createLightColorScheme.js deleted file mode 100644 index 597cd5ea925b86..00000000000000 --- a/packages/mui-material/src/styles/md3/createLightColorScheme.js +++ /dev/null @@ -1,35 +0,0 @@ -// convert all these values to CSS vars -const createLightColorScheme = (getCssVar) => ({ - colors: { - surfaceTint: getCssVar('palette-md3-primary-40'), - onErrorContainer: getCssVar('palette-md3-error-10'), - onError: getCssVar('palette-md3-error-100'), - errorContainer: getCssVar('palette-md3-error-90'), - onTertiaryContainer: getCssVar('palette-md3-tertiary-10'), - onTertiary: getCssVar('palette-md3-tertiary-100'), - tertiaryContainer: getCssVar('palette-md3-tertiary-90'), - tertiary: getCssVar('palette-md3-tertiary-40'), - shadow: getCssVar('palette-md3-common-black'), - error: getCssVar('palette-md3-error-40'), - outline: getCssVar('palette-md3-neutralVariant-50'), - onBackground: getCssVar('palette-md3-neutral-10'), - background: getCssVar('palette-md3-neutral-99'), - inverseOnSurface: getCssVar('palette-md3-neutral-95'), - inverseSurface: getCssVar('palette-md3-neutral-20'), - onSurfaceVariant: getCssVar('palette-md3-neutralVariant-30'), - onSurface: getCssVar('palette-md3-neutral-10'), - surfaceVariant: getCssVar('palette-md3-neutralVariant-90'), - surface: getCssVar('palette-md3-neutral-99'), - onSecondaryContainer: getCssVar('palette-md3-secondary-10'), - onSecondary: getCssVar('palette-md3-secondary-100'), - secondaryContainer: getCssVar('palette-md3-secondary-90'), - secondary: getCssVar('palette-md3-secondary-40'), - inversePrimary: getCssVar('palette-md3-primary-80'), - onPrimaryContainer: getCssVar('palette-md3-primary-10'), - onPrimary: getCssVar('palette-md3-primary-100'), - primaryContainer: getCssVar('palette-md3-primary-90'), - primary: getCssVar('palette-md3-primary-40'), - }, -}); - -export default createLightColorScheme; From 9fd9092c5e41820f9f0d69ea6574ce698f5d8956 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 14:48:04 +0200 Subject: [PATCH 12/49] Fix some CI issues --- docs/pages/experiments/md3/index.tsx | 3 +- .../mui-material-next/src/Button/Button.tsx | 2 +- .../ButtonNext/IconLabelButtonsNext.js | 40 +++++++++++-------- .../ButtonNext/MultilineButtonNext.js | 20 ++++++---- 4 files changed, 39 insertions(+), 26 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index f51282b5f54879..43239355821c8f 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -140,7 +140,8 @@ const DemoComponents = () => { const cssVarsTheme = extendTheme(); export default function App() { - const [_, setMode] = React.useState('light'); + // eslint-disable-next-line @typescript-eslint/no-unused-vars + const [mode, setMode] = React.useState('light'); return ( diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index aadf4c5312741b..08eb9d2fc35832 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -7,7 +7,7 @@ import { unstable_capitalize as capitalize, unstable_useForkRef as useForkRef, } from '@mui/utils'; -import { useButton, UseButtonRootSlotOwnProps } from '@mui/base/ButtonUnstyled'; +import { useButton } from '@mui/base/ButtonUnstyled'; import composeClasses from '@mui/base/composeClasses'; import { useThemeProps, alpha } from '@mui/system'; import { MD3ColorSchemeTokens, styled } from '../styles'; diff --git a/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js b/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js index 5bf13d5f356586..018ce75fda3ed1 100644 --- a/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js +++ b/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js @@ -2,25 +2,31 @@ import * as React from 'react'; import Button from '@mui/material-next/Button'; import Icon from '@mui/material/Icon'; import SendIcon from '@mui/icons-material/Send'; +import { extendTheme } from '@mui/material-next/styles'; +import { Experimental_CssVarsProvider as CssVarsProvider } from '@mui/material/styles'; + +const theme = extendTheme(); export default function IconLabelButtonsNext() { return ( -
- - - - - -
+ +
+ + + + + +
+
); } diff --git a/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js b/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js index 546607ecc4db32..2d80b028f194d3 100644 --- a/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js +++ b/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js @@ -1,14 +1,20 @@ import * as React from 'react'; import Button from '@mui/material-next/Button'; +import { extendTheme } from '@mui/material-next/styles'; +import { Experimental_CssVarsProvider as CssVarsProvider } from '@mui/material/styles'; + +const theme = extendTheme(); export default function MultilineButtonNext() { return ( - + + + ); } From c70d8dc42e9fd0b96486b837fe0f4a40e4612dd6 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 15:06:39 +0200 Subject: [PATCH 13/49] Fix build --- packages/mui-material-next/src/styles/Theme.types.ts | 10 +++++++--- ...eateDarkColorScheme.js => createDarkColorScheme.ts} | 6 +++++- ...teLightColorScheme.js => createLightColorScheme.ts} | 8 ++++++-- .../{createMd3Palette.js => createMd3Palette.ts} | 5 +++-- .../src/styles/{palette.js => palette.ts} | 0 .../src/styles/{states.js => states.ts} | 0 .../src/styles/{typeface.js => typeface.ts} | 0 .../src/styles/{typescale.js => typescale.ts} | 0 8 files changed, 21 insertions(+), 8 deletions(-) rename packages/mui-material-next/src/styles/{createDarkColorScheme.js => createDarkColorScheme.ts} (93%) rename packages/mui-material-next/src/styles/{createLightColorScheme.js => createLightColorScheme.ts} (92%) rename packages/mui-material-next/src/styles/{createMd3Palette.js => createMd3Palette.ts} (95%) rename packages/mui-material-next/src/styles/{palette.js => palette.ts} (100%) rename packages/mui-material-next/src/styles/{states.js => states.ts} (100%) rename packages/mui-material-next/src/styles/{typeface.js => typeface.ts} (100%) rename packages/mui-material-next/src/styles/{typescale.js => typescale.ts} (100%) diff --git a/packages/mui-material-next/src/styles/Theme.types.ts b/packages/mui-material-next/src/styles/Theme.types.ts index 4ea7e882dcec6f..0126830505de53 100644 --- a/packages/mui-material-next/src/styles/Theme.types.ts +++ b/packages/mui-material-next/src/styles/Theme.types.ts @@ -19,7 +19,7 @@ export interface CssVarsThemeOptions extends Omit>; } -interface MD3Tones { +export interface MD3Tones { 0: string; 10: string; 20: string; @@ -140,14 +140,18 @@ export interface Shapes { borderRadius: number; } +export interface MD3PaletteWithTokens extends MD3Palettes { + colors: MD3ColorSchemeTokens; +} + export interface Theme extends Omit { useMaterialYou?: boolean; - palette: MD2Theme['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; + palette: MD2Theme['palette'] & { md3: MD3PaletteWithTokens }; state: MD3States; typescale: MD3Typescale; shape: Shapes; vars: MD2Theme['vars'] & { - palette: MD2Theme['vars']['palette'] & { md3: MD3Palettes & { colors: MD3ColorSchemeTokens } }; + palette: MD2Theme['vars']['palette'] & { md3: MD3PaletteWithTokens }; state: MD3States; typescale: MD3Typescale; shape: Shapes; diff --git a/packages/mui-material-next/src/styles/createDarkColorScheme.js b/packages/mui-material-next/src/styles/createDarkColorScheme.ts similarity index 93% rename from packages/mui-material-next/src/styles/createDarkColorScheme.js rename to packages/mui-material-next/src/styles/createDarkColorScheme.ts index 4ea01f9757375d..6b8f17ab1c62cb 100644 --- a/packages/mui-material-next/src/styles/createDarkColorScheme.js +++ b/packages/mui-material-next/src/styles/createDarkColorScheme.ts @@ -1,5 +1,9 @@ +import { MD3Palettes } from './Theme.types'; // convert all these values to CSS vars -const createDarkColorScheme = (getCssVar, palette) => ({ +const createDarkColorScheme = ( + getCssVar: (cssVar: string, defaultVal: string) => string, + palette: MD3Palettes, +) => ({ colors: { surfaceTint: getCssVar('palette-md3-primary-40', palette.primary[40]), onErrorContainer: getCssVar('palette-md3-error-80', palette.error[80]), diff --git a/packages/mui-material-next/src/styles/createLightColorScheme.js b/packages/mui-material-next/src/styles/createLightColorScheme.ts similarity index 92% rename from packages/mui-material-next/src/styles/createLightColorScheme.js rename to packages/mui-material-next/src/styles/createLightColorScheme.ts index 9d3de968cf7218..2498953855df5a 100644 --- a/packages/mui-material-next/src/styles/createLightColorScheme.js +++ b/packages/mui-material-next/src/styles/createLightColorScheme.ts @@ -1,5 +1,9 @@ -// convert all these values to CSS vars -const createLightColorScheme = (getCssVar, palette) => ({ +import { MD3Palettes } from './Theme.types'; + +const createLightColorScheme = ( + getCssVar: (cssVar: string, defaultVal: string) => string, + palette: MD3Palettes, +) => ({ colors: { surfaceTint: getCssVar('palette-md3-primary-40', palette.primary[40]), onErrorContainer: getCssVar('palette-md3-error-10', palette.error[10]), diff --git a/packages/mui-material-next/src/styles/createMd3Palette.js b/packages/mui-material-next/src/styles/createMd3Palette.ts similarity index 95% rename from packages/mui-material-next/src/styles/createMd3Palette.js rename to packages/mui-material-next/src/styles/createMd3Palette.ts index de98fd01f75966..3a08f2a242c1d6 100644 --- a/packages/mui-material-next/src/styles/createMd3Palette.js +++ b/packages/mui-material-next/src/styles/createMd3Palette.ts @@ -1,8 +1,9 @@ import { deepmerge } from '@mui/utils'; +import { MD3PaletteWithTokens } from './Theme.types'; import globalPalette from './palette'; -const createMd3Palette = (palette, mode = 'light') => { - const resolvedGlobalPalette = deepmerge(globalPalette, palette); +const createMd3Palette = (palette: MD3PaletteWithTokens, mode = 'light'): MD3PaletteWithTokens => { + const resolvedGlobalPalette = deepmerge(globalPalette, palette) as MD3PaletteWithTokens; return { ...resolvedGlobalPalette, diff --git a/packages/mui-material-next/src/styles/palette.js b/packages/mui-material-next/src/styles/palette.ts similarity index 100% rename from packages/mui-material-next/src/styles/palette.js rename to packages/mui-material-next/src/styles/palette.ts diff --git a/packages/mui-material-next/src/styles/states.js b/packages/mui-material-next/src/styles/states.ts similarity index 100% rename from packages/mui-material-next/src/styles/states.js rename to packages/mui-material-next/src/styles/states.ts diff --git a/packages/mui-material-next/src/styles/typeface.js b/packages/mui-material-next/src/styles/typeface.ts similarity index 100% rename from packages/mui-material-next/src/styles/typeface.js rename to packages/mui-material-next/src/styles/typeface.ts diff --git a/packages/mui-material-next/src/styles/typescale.js b/packages/mui-material-next/src/styles/typescale.ts similarity index 100% rename from packages/mui-material-next/src/styles/typescale.js rename to packages/mui-material-next/src/styles/typescale.ts From 72b737538ff267fabce68aed2c7ad678499aefa1 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 15:18:52 +0200 Subject: [PATCH 14/49] Cleanup docs experiments page --- docs/pages/experiments/md3/index.tsx | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index 43239355821c8f..0a7e7fc76dfb38 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -14,7 +14,7 @@ import { extendTheme } from '@mui/material-next/styles'; import DarkIcon from '@mui/icons-material/DarkModeOutlined'; import LightIcon from '@mui/icons-material/LightModeOutlined'; -const ModeSwitcher = ({ setMode: setModeProp }: { setMode: (arg: string) => void }) => { +const ModeSwitcher = () => { const { mode, setMode } = useColorScheme(); const [mounted, setMounted] = React.useState(false); @@ -32,10 +32,8 @@ const ModeSwitcher = ({ setMode: setModeProp }: { setMode: (arg: string) => void onClick={() => { if (mode === 'light') { setMode('dark'); - setModeProp('dark'); } else { setMode('light'); - setModeProp('light'); } }} > @@ -140,12 +138,10 @@ const DemoComponents = () => { const cssVarsTheme = extendTheme(); export default function App() { - // eslint-disable-next-line @typescript-eslint/no-unused-vars - const [mode, setMode] = React.useState('light'); return ( - + From 1ea8e955802756c4e82ade67da1051dc7cc9c071 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 16:48:47 +0200 Subject: [PATCH 15/49] Make it able to coexist with MD2 --- docs/pages/experiments/md3/index.tsx | 26 ++++++ .../mui-material-next/src/Button/Button.tsx | 84 ++++++++++--------- .../src/styles/Theme.types.ts | 18 ++-- .../src/styles/extendTheme.ts | 14 ++-- .../ButtonNext/IconLabelButtonsNext.js | 40 ++++----- .../ButtonNext/MultilineButtonNext.js | 20 ++--- 6 files changed, 115 insertions(+), 87 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index 0a7e7fc76dfb38..25562983bfdc01 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -6,6 +6,7 @@ import { useColorScheme, Stack, } from '@mui/material'; +import MD2Button, { ButtonProps as MD2ButtonProps } from '@mui/material/Button'; import { unstable_capitalize as capitalize } from '@mui/utils'; import DeleteIcon from '@mui/icons-material/Delete'; import SendIcon from '@mui/icons-material/Send'; @@ -53,6 +54,16 @@ const variants: ButtonProps['variant'][] = [ const colors: ButtonProps['color'][] = ['primary', 'secondary', 'tertiary']; const sizes: ButtonProps['size'][] = ['small', 'medium', 'large']; +const md2Variants: MD2ButtonProps['variant'][] = ['contained', 'outlined', 'text']; +const md2Colors: MD2ButtonProps['color'][] = [ + 'primary', + 'secondary', + 'success', + 'error', + 'info', + 'warning', +]; + const DemoComponents = () => { return ( @@ -130,6 +141,21 @@ const DemoComponents = () => { ))} +

Material Design 2 Buttons

+ + {md2Variants.map((variant) => ( + + {capitalize(variant as string)} + + ))} + + + {md2Colors.map((color) => ( + + {capitalize(color as string)} + + ))} + ); }; diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 08eb9d2fc35832..95ceaf4c24dc93 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -127,37 +127,40 @@ export const ButtonRoot = styled('button', { const hoveredContainerColor = { elevated: theme.vars ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.hover.stateLayerOpacity + (theme.vars || theme).md3.state.hover.stateLayerOpacity })` - : alpha(theme.palette.md3.colors.primary, theme.state.hover.stateLayerOpacity), + : alpha(theme.palette.md3.colors.primary, theme.md3.state.hover.stateLayerOpacity), filled: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).state.hover.stateLayerOpacity}))` + } / calc(1 - ${(theme.vars || theme).md3.state.hover.stateLayerOpacity}))` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.state.hover.stateLayerOpacity, + 1 - theme.md3.state.hover.stateLayerOpacity, ), filledTonal: theme.vars ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).state.hover.stateLayerOpacity + (theme.vars || theme).md3.state.hover.stateLayerOpacity }))` - : alpha(theme.palette.md3.colors.secondaryContainer, 1 - theme.state.hover.stateLayerOpacity), + : alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.md3.state.hover.stateLayerOpacity, + ), outlined: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.hover.stateLayerOpacity})` + } / ${(theme.vars || theme).md3.state.hover.stateLayerOpacity})` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.hover.stateLayerOpacity, + theme.md3.state.hover.stateLayerOpacity, ), text: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.hover.stateLayerOpacity})` + } / ${(theme.vars || theme).md3.state.hover.stateLayerOpacity})` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.hover.stateLayerOpacity, + theme.md3.state.hover.stateLayerOpacity, ), }; @@ -172,77 +175,80 @@ export const ButtonRoot = styled('button', { const pressedContainerColor = { elevated: theme.vars ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.pressed.stateLayerOpacity + (theme.vars || theme).md3.state.pressed.stateLayerOpacity })` - : alpha(theme.palette.md3.colors.primary, theme.state.pressed.stateLayerOpacity), + : alpha(theme.palette.md3.colors.primary, theme.md3.state.pressed.stateLayerOpacity), filled: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).state.pressed.stateLayerOpacity}))` + } / calc(1 - ${(theme.vars || theme).md3.state.pressed.stateLayerOpacity}))` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.state.pressed.stateLayerOpacity, + 1 - theme.md3.state.pressed.stateLayerOpacity, ), filledTonal: theme.vars ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).state.pressed.stateLayerOpacity + (theme.vars || theme).md3.state.pressed.stateLayerOpacity }))` : alpha( theme.palette.md3.colors.secondaryContainer, - 1 - theme.state.pressed.stateLayerOpacity, + 1 - theme.md3.state.pressed.stateLayerOpacity, ), outlined: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.pressed.stateLayerOpacity})` + } / ${(theme.vars || theme).md3.state.pressed.stateLayerOpacity})` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.pressed.stateLayerOpacity, + theme.md3.state.pressed.stateLayerOpacity, ), text: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.pressed.stateLayerOpacity})` + } / ${(theme.vars || theme).md3.state.pressed.stateLayerOpacity})` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.pressed.stateLayerOpacity, + theme.md3.state.pressed.stateLayerOpacity, ), }; const focusedContainerColor = { elevated: theme.vars ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).state.focus.stateLayerOpacity + (theme.vars || theme).md3.state.focus.stateLayerOpacity })` - : alpha(theme.palette.md3.colors.primary, theme.state.focus.stateLayerOpacity), + : alpha(theme.palette.md3.colors.primary, theme.md3.state.focus.stateLayerOpacity), filled: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).state.focus.stateLayerOpacity}))` + } / calc(1 - ${(theme.vars || theme).md3.state.focus.stateLayerOpacity}))` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.state.focus.stateLayerOpacity, + 1 - theme.md3.state.focus.stateLayerOpacity, ), filledTonal: theme.vars ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).state.focus.stateLayerOpacity + (theme.vars || theme).md3.state.focus.stateLayerOpacity }))` - : alpha(theme.palette.md3.colors.secondaryContainer, 1 - theme.state.focus.stateLayerOpacity), + : alpha( + theme.palette.md3.colors.secondaryContainer, + 1 - theme.md3.state.focus.stateLayerOpacity, + ), outlined: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.focus.stateLayerOpacity})` + } / ${(theme.vars || theme).md3.state.focus.stateLayerOpacity})` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.focus.stateLayerOpacity, + theme.md3.state.focus.stateLayerOpacity, ), text: theme.vars ? `rgba(${ (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).state.focus.stateLayerOpacity})` + } / ${(theme.vars || theme).md3.state.focus.stateLayerOpacity})` : alpha( theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.state.focus.stateLayerOpacity, + theme.md3.state.focus.stateLayerOpacity, ), }; @@ -258,7 +264,7 @@ export const ButtonRoot = styled('button', { : alpha(theme.palette.md3.colors.onSurface, 0.38); const letterSpacing = `${ - theme.typescale.label.large.tracking / theme.typescale.label.large.size + theme.md3.typescale.label.large.tracking / theme.md3.typescale.label.large.size }rem`; return { @@ -284,8 +290,8 @@ export const ButtonRoot = styled('button', { '--md-comp-button-disabled-icon-color': disabledLabelTextColor, // Dynamic variables '--md-comp-button-label-text-line-height': `calc(${ - (theme.vars || theme).typescale.label.large.lineHeight - } / ${theme.typescale.label.large.size})`, + (theme.vars || theme).md3.typescale.label.large.lineHeight + } / ${theme.md3.typescale.label.large.size})`, // Noramlized styles for buttons display: 'inline-flex', alignItems: 'center', @@ -321,16 +327,16 @@ export const ButtonRoot = styled('button', { }, ), fontFamily: `var(--md-comp-button-label-text-font, ${ - (theme.vars || theme).typescale.label.large.family + (theme.vars || theme).md3.typescale.label.large.family })`, fontWeight: `var(--md-comp-button-label-text-weight, ${ - (theme.vars || theme).typescale.label.large.weight + (theme.vars || theme).md3.typescale.label.large.weight })`, fontSize: `var(--md-comp-button-label-text-size, ${ - theme.typography.pxToRem(theme.typescale.label.large.size) // the pxToRem should be moved to typescale in the future + theme.typography.pxToRem(theme.md3.typescale.label.large.size) // the pxToRem should be moved to typescale in the future })`, lineHeight: 'var(--md-comp-button-label-text-line-height)', - borderRadius: (theme.vars || theme).shape.borderRadius, + borderRadius: (theme.vars || theme).md3.shape.borderRadius, background: `var(--md-comp-button-container-color, ${ containerColor[ownerState.variant ?? 'text'] })`, @@ -348,7 +354,7 @@ export const ButtonRoot = styled('button', { // Sizes are not specified in Material You, this need to be revised ...(ownerState.size === 'small' && { fontSize: `var(--md-comp-button-label-text-size, ${ - theme.typography.pxToRem(theme.typescale.label.large.size - 1) // the pxToRem should be moved to typescale in the future + theme.typography.pxToRem(theme.md3.typescale.label.large.size - 1) // the pxToRem should be moved to typescale in the future })`, padding: '8px 20px', ...(ownerState.variant === 'outlined' && { @@ -357,7 +363,7 @@ export const ButtonRoot = styled('button', { }), ...(ownerState.size === 'large' && { fontSize: `var(--md-comp-button-label-text-size, ${ - theme.typography.pxToRem(theme.typescale.label.large.size + 1) // the pxToRem should be moved to typescale in the future + theme.typography.pxToRem(theme.md3.typescale.label.large.size + 1) // the pxToRem should be moved to typescale in the future })`, padding: '12px 26px', ...(ownerState.variant === 'outlined' && { diff --git a/packages/mui-material-next/src/styles/Theme.types.ts b/packages/mui-material-next/src/styles/Theme.types.ts index 0126830505de53..26998eb45e2eab 100644 --- a/packages/mui-material-next/src/styles/Theme.types.ts +++ b/packages/mui-material-next/src/styles/Theme.types.ts @@ -146,14 +146,20 @@ export interface MD3PaletteWithTokens extends MD3Palettes { export interface Theme extends Omit { useMaterialYou?: boolean; - palette: MD2Theme['palette'] & { md3: MD3PaletteWithTokens }; - state: MD3States; - typescale: MD3Typescale; - shape: Shapes; - vars: MD2Theme['vars'] & { - palette: MD2Theme['vars']['palette'] & { md3: MD3PaletteWithTokens }; + md3: { + // Others should be added state: MD3States; typescale: MD3Typescale; shape: Shapes; }; + palette: MD2Theme['palette'] & { md3: MD3PaletteWithTokens }; + vars: MD2Theme['vars'] & { + palette: MD2Theme['vars']['palette'] & { md3: MD3PaletteWithTokens }; + md3: { + // Others should be added + state: MD3States; + typescale: MD3Typescale; + shape: Shapes; + }; + }; } diff --git a/packages/mui-material-next/src/styles/extendTheme.ts b/packages/mui-material-next/src/styles/extendTheme.ts index 11d98134ce1ca7..6f9fe3f883dfb1 100644 --- a/packages/mui-material-next/src/styles/extendTheme.ts +++ b/packages/mui-material-next/src/styles/extendTheme.ts @@ -72,12 +72,14 @@ export default function extendTheme( ...input, ...(useMaterialYou && { useMaterialYou: true, - typescale: md3Typescale, - typeface: md3Typeface, - state: md3State, - shape: { - borderRadius: 100, - ...input?.shape, + md3: { + typescale: md3Typescale, + typeface: md3Typeface, + state: md3State, + shape: { + borderRadius: 100, + ...input?.shape, + }, }, }), palette: { diff --git a/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js b/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js index 018ce75fda3ed1..5bf13d5f356586 100644 --- a/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js +++ b/test/regressions/fixtures/ButtonNext/IconLabelButtonsNext.js @@ -2,31 +2,25 @@ import * as React from 'react'; import Button from '@mui/material-next/Button'; import Icon from '@mui/material/Icon'; import SendIcon from '@mui/icons-material/Send'; -import { extendTheme } from '@mui/material-next/styles'; -import { Experimental_CssVarsProvider as CssVarsProvider } from '@mui/material/styles'; - -const theme = extendTheme(); export default function IconLabelButtonsNext() { return ( - -
- - - - - -
-
+
+ + + + + +
); } diff --git a/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js b/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js index 2d80b028f194d3..546607ecc4db32 100644 --- a/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js +++ b/test/regressions/fixtures/ButtonNext/MultilineButtonNext.js @@ -1,20 +1,14 @@ import * as React from 'react'; import Button from '@mui/material-next/Button'; -import { extendTheme } from '@mui/material-next/styles'; -import { Experimental_CssVarsProvider as CssVarsProvider } from '@mui/material/styles'; - -const theme = extendTheme(); export default function MultilineButtonNext() { return ( - - - + ); } From 755bb6f823209ceb7d1b31b11ab588c71a60ae90 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 16:57:09 +0200 Subject: [PATCH 16/49] Fix defaultTheme --- packages/mui-material-next/src/styles/defaultTheme.ts | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/packages/mui-material-next/src/styles/defaultTheme.ts b/packages/mui-material-next/src/styles/defaultTheme.ts index eac9d73ffe7249..9688c5054bf391 100644 --- a/packages/mui-material-next/src/styles/defaultTheme.ts +++ b/packages/mui-material-next/src/styles/defaultTheme.ts @@ -10,8 +10,7 @@ export const getThemeWithVars = ( opacity, overlays, shape, - state, - typescale, + md3, palette: paletteInput, ...restTheme } = extendTheme(themeInput); @@ -25,8 +24,7 @@ export const getThemeWithVars = ( opacity, overlays, shape, - state, - typescale, + md3: md3, ...restTheme, colorSchemes: { ...colorSchemes, @@ -41,8 +39,7 @@ export const getThemeWithVars = ( opacity, overlays, shape, - state, - typescale, + md3, palette, }, } as unknown as Theme; From 775bd0ca5ab8a68f5d7c49e7817a14061282b8da Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 20 Oct 2022 17:12:46 +0200 Subject: [PATCH 17/49] lint fix --- packages/mui-material-next/src/styles/defaultTheme.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/mui-material-next/src/styles/defaultTheme.ts b/packages/mui-material-next/src/styles/defaultTheme.ts index 9688c5054bf391..be1a4fe44e88ba 100644 --- a/packages/mui-material-next/src/styles/defaultTheme.ts +++ b/packages/mui-material-next/src/styles/defaultTheme.ts @@ -24,7 +24,7 @@ export const getThemeWithVars = ( opacity, overlays, shape, - md3: md3, + md3, ...restTheme, colorSchemes: { ...colorSchemes, From fb1e07c54c669b9137e198ffbfdce5aeb7d7fcd5 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 21 Oct 2022 09:03:04 +0200 Subject: [PATCH 18/49] Use imports from @mui/material-next --- docs/pages/experiments/md3/index.tsx | 12 +++---- .../mui-material-next/src/styles/index.ts | 36 +++++++++++++++++++ 2 files changed, 40 insertions(+), 8 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index 25562983bfdc01..ae9b5492e18357 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -1,17 +1,13 @@ import * as React from 'react'; -import { - Experimental_CssVarsProvider as CssVarsProvider, - Tooltip, - IconButton, - useColorScheme, - Stack, -} from '@mui/material'; +import Tooltip from '@mui/material/Tooltip'; +import IconButton from '@mui/material/IconButton'; +import Stack from '@mui/material/Stack'; import MD2Button, { ButtonProps as MD2ButtonProps } from '@mui/material/Button'; import { unstable_capitalize as capitalize } from '@mui/utils'; import DeleteIcon from '@mui/icons-material/Delete'; import SendIcon from '@mui/icons-material/Send'; import Button, { ButtonProps } from '@mui/material-next/Button'; -import { extendTheme } from '@mui/material-next/styles'; +import { CssVarsProvider, useColorScheme, extendTheme } from '@mui/material-next/styles'; import DarkIcon from '@mui/icons-material/DarkModeOutlined'; import LightIcon from '@mui/icons-material/LightModeOutlined'; diff --git a/packages/mui-material-next/src/styles/index.ts b/packages/mui-material-next/src/styles/index.ts index 026e1621625149..410cbaf000a6a0 100644 --- a/packages/mui-material-next/src/styles/index.ts +++ b/packages/mui-material-next/src/styles/index.ts @@ -3,3 +3,39 @@ export * from './extendTheme'; export { default as extendTheme } from './extendTheme'; export { default as styled } from './styled'; export { default as defaultTheme } from './defaultTheme'; +export { + Experimental_CssVarsProvider as CssVarsProvider, + useColorScheme, + // All types exported from @mui/material + ColorSchemeOverrides, + SupportedColorScheme, + ColorSystem, + CssVarsPalette, + Opacity, + Overlays, + PaletteAlert, + PaletteActionChannel, + PaletteAppBar, + PaletteAvatar, + PaletteChip, + PaletteColorChannel, + PaletteCommonChannel, + PaletteFilledInput, + PaletteLinearProgress, + PaletteSkeleton, + PaletteSlider, + PaletteSnackbarContent, + PaletteSpeedDialAction, + PaletteStepConnector, + PaletteStepContent, + PaletteSwitch, + PaletteTableCell, + PaletteTextChannel, + PaletteTooltip, + CssVarsThemeOptions, + CssVarsTheme, + ThemeVars, + ThemeCssVar, + ThemeCssVarOverrides, + ColorSystemOptions, +} from '@mui/material/styles'; From 4c03b3bfa9d55478c00ef2717585e6d390e66e1a Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 21 Oct 2022 09:12:03 +0200 Subject: [PATCH 19/49] SxProps type --- packages/mui-material-next/src/Button/Button.types.ts | 5 ++--- packages/mui-material-next/src/styles/Theme.types.ts | 4 +++- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.types.ts b/packages/mui-material-next/src/Button/Button.types.ts index 592f220d7f3bdb..dae09ef0fd224a 100644 --- a/packages/mui-material-next/src/Button/Button.types.ts +++ b/packages/mui-material-next/src/Button/Button.types.ts @@ -5,8 +5,7 @@ import { OverridableComponent, OverridableTypeMap, } from '@mui/types'; -import { SxProps } from '@mui/system'; -import { Theme } from '../styles'; +import { SxProps } from '../styles/Theme.types'; import { ButtonClasses } from './buttonClasses'; export interface ButtonPropsVariantOverrides {} @@ -106,7 +105,7 @@ export type ButtonTypeMap

= { /** * The system prop that allows defining system overrides as well as additional CSS styles. */ - sx?: SxProps; + sx?: SxProps; /** * The variant to use. * @default 'text' diff --git a/packages/mui-material-next/src/styles/Theme.types.ts b/packages/mui-material-next/src/styles/Theme.types.ts index 26998eb45e2eab..6f085ed57a72bd 100644 --- a/packages/mui-material-next/src/styles/Theme.types.ts +++ b/packages/mui-material-next/src/styles/Theme.types.ts @@ -1,4 +1,4 @@ -// Needs to be keep in sync with @mui/material/MaterialYouModuleAugmentation +import { SxProps as SystemSxProps } from '@mui/system'; import { CssVarsTheme as MD2Theme, SupportedColorScheme, @@ -163,3 +163,5 @@ export interface Theme extends Omit { }; }; } + +export type SxProps = SystemSxProps; From 2ea93a3b3fb5c4bc968a56ad1aed9d83a2a0009b Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 21 Oct 2022 09:43:07 +0200 Subject: [PATCH 20/49] Don't export types just yet --- .../mui-material-next/src/styles/index.ts | 32 ------------------- 1 file changed, 32 deletions(-) diff --git a/packages/mui-material-next/src/styles/index.ts b/packages/mui-material-next/src/styles/index.ts index 410cbaf000a6a0..d1e3d03bf42943 100644 --- a/packages/mui-material-next/src/styles/index.ts +++ b/packages/mui-material-next/src/styles/index.ts @@ -6,36 +6,4 @@ export { default as defaultTheme } from './defaultTheme'; export { Experimental_CssVarsProvider as CssVarsProvider, useColorScheme, - // All types exported from @mui/material - ColorSchemeOverrides, - SupportedColorScheme, - ColorSystem, - CssVarsPalette, - Opacity, - Overlays, - PaletteAlert, - PaletteActionChannel, - PaletteAppBar, - PaletteAvatar, - PaletteChip, - PaletteColorChannel, - PaletteCommonChannel, - PaletteFilledInput, - PaletteLinearProgress, - PaletteSkeleton, - PaletteSlider, - PaletteSnackbarContent, - PaletteSpeedDialAction, - PaletteStepConnector, - PaletteStepContent, - PaletteSwitch, - PaletteTableCell, - PaletteTextChannel, - PaletteTooltip, - CssVarsThemeOptions, - CssVarsTheme, - ThemeVars, - ThemeCssVar, - ThemeCssVarOverrides, - ColorSystemOptions, } from '@mui/material/styles'; From 5c16e1f3daa47e7301310dbad2e12e26bd834c29 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 27 Oct 2022 13:16:29 +0200 Subject: [PATCH 21/49] Remove component's CSS vars --- .../mui-material-next/src/Button/Button.tsx | 86 ++++--------------- 1 file changed, 19 insertions(+), 67 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 95ceaf4c24dc93..98d26bcd06a187 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -268,30 +268,12 @@ export const ButtonRoot = styled('button', { }rem`; return { - // What's missing: - // 1. The container state opacities are calculated in the background color for now - // '--md-comp-button-disabled-container-opacity': '', - // '--md-comp-button-disabled-label-text-opacity': '', - // '--md-comp-button-disabled-icon-opacity': '', - // '--md-comp-button-hovered-container-state-layer-opacity': '', - // '--md-comp-button-focused-container-state-layer-opacity': '', - // '--md-comp-button-pressed-container-state-layer-opacity': '', - // 2. The elevations are not correctly implemented, as I still couldn't find an actual specification around their values - // '--md-comp-button-container-shadow-color': '', - // '--md-comp-button-focused-container-elevation': '', - // '--md-comp-button-pressed-container-elevation': '', - // 3. Not sure how to make the tracking work with the CSS variables as there is a calculation needed - // '--md-comp-button-label-text-tracking': (theme.vars || theme).typescale.label.large.tracking, // Icon variables default values '--md-comp-button-icon-color': labelTextColor[ownerState.variant ?? 'text'], '--md-comp-button-hovered-icon-color': labelTextColor[ownerState.variant ?? 'text'], // same as default '--md-comp-button-pressed-icon-color': labelTextColor[ownerState.variant ?? 'text'], // same as default '--md-comp-button-focused-icon-color': labelTextColor[ownerState.variant ?? 'text'], // same as default '--md-comp-button-disabled-icon-color': disabledLabelTextColor, - // Dynamic variables - '--md-comp-button-label-text-line-height': `calc(${ - (theme.vars || theme).md3.typescale.label.large.lineHeight - } / ${theme.md3.typescale.label.large.size})`, // Noramlized styles for buttons display: 'inline-flex', alignItems: 'center', @@ -326,26 +308,16 @@ export const ButtonRoot = styled('button', { duration: theme.transitions.duration.short, }, ), - fontFamily: `var(--md-comp-button-label-text-font, ${ - (theme.vars || theme).md3.typescale.label.large.family + fontFamily: (theme.vars || theme).md3.typescale.label.large.family, + fontWeight: (theme.vars || theme).md3.typescale.label.large.weight, + fontSize: theme.typography.pxToRem(theme.md3.typescale.label.large.size), // the pxToRem should be moved to typescale in the future + lineHeight: `calc(${(theme.vars || theme).md3.typescale.label.large.lineHeight} / ${ + theme.md3.typescale.label.large.size })`, - fontWeight: `var(--md-comp-button-label-text-weight, ${ - (theme.vars || theme).md3.typescale.label.large.weight - })`, - fontSize: `var(--md-comp-button-label-text-size, ${ - theme.typography.pxToRem(theme.md3.typescale.label.large.size) // the pxToRem should be moved to typescale in the future - })`, - lineHeight: 'var(--md-comp-button-label-text-line-height)', borderRadius: (theme.vars || theme).md3.shape.borderRadius, - background: `var(--md-comp-button-container-color, ${ - containerColor[ownerState.variant ?? 'text'] - })`, - color: `var(--md-comp-button-label-text-color, ${ - labelTextColor[ownerState.variant ?? 'text'] - })`, - boxShadow: `var(--md-comp-button-container-elevation, ${ - containerElevation[ownerState.variant ?? 'text'] - })`, + background: containerColor[ownerState.variant ?? 'text'], + color: labelTextColor[ownerState.variant ?? 'text'], + boxShadow: containerElevation[ownerState.variant ?? 'text'], // Outlined varaiant ...(ownerState.variant === 'outlined' && { border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, @@ -353,18 +325,14 @@ export const ButtonRoot = styled('button', { }), // Sizes are not specified in Material You, this need to be revised ...(ownerState.size === 'small' && { - fontSize: `var(--md-comp-button-label-text-size, ${ - theme.typography.pxToRem(theme.md3.typescale.label.large.size - 1) // the pxToRem should be moved to typescale in the future - })`, + fontSize: theme.typography.pxToRem(theme.md3.typescale.label.large.size - 1), // the pxToRem should be moved to typescale in the future padding: '8px 20px', ...(ownerState.variant === 'outlined' && { padding: '7px 19px', }), }), ...(ownerState.size === 'large' && { - fontSize: `var(--md-comp-button-label-text-size, ${ - theme.typography.pxToRem(theme.md3.typescale.label.large.size + 1) // the pxToRem should be moved to typescale in the future - })`, + fontSize: theme.typography.pxToRem(theme.md3.typescale.label.large.size + 1), // the pxToRem should be moved to typescale in the future padding: '12px 26px', ...(ownerState.variant === 'outlined' && { padding: '11px 25px', @@ -372,43 +340,27 @@ export const ButtonRoot = styled('button', { }), '&:hover': { '--md-comp-button-icon-color': 'var(--md-comp-button-hovered-icon-color)', - color: `var(--md-comp-button-hovered-label-text-color, ${ - labelTextColor[ownerState.variant ?? 'text'] - })`, - backgroundColor: `var(--md-comp-button-hovered-container-state-layer-color, ${ - hoveredContainerColor[ownerState.variant ?? 'text'] - })`, - boxShadow: `var(--md-comp-button-hovered-container-elevation, ${ - hoveredContainerElevation[ownerState.variant ?? 'text'] - })`, + color: labelTextColor[ownerState.variant ?? 'text'], + backgroundColor: hoveredContainerColor[ownerState.variant ?? 'text'], + boxShadow: hoveredContainerElevation[ownerState.variant ?? 'text'], }, '&:active': { '--md-comp-button-icon-color': 'var(--md-comp-button-pressed-icon-color)', - color: `var(--md-comp-button-pressed-label-text-color, ${ - labelTextColor[ownerState.variant ?? 'text'] - })`, - backgroundColor: `var(--md-comp-button-pressed-container-state-layer-color, ${ - pressedContainerColor[ownerState.variant ?? 'text'] - })`, + color: labelTextColor[ownerState.variant ?? 'text'], + backgroundColor: pressedContainerColor[ownerState.variant ?? 'text'], }, [`&.${buttonClasses.focusVisible}`]: { '--md-comp-button-icon-color': 'var(--md-comp-button-focused-icon-color)', - color: `var(--md-comp-button-focused-label-text-color, ${ - labelTextColor[ownerState.variant ?? 'text'] - })`, - backgroundColor: `var(--md-comp-button-focused-container-state-layer-color, ${ - focusedContainerColor[ownerState.variant ?? 'text'] - })`, + color: labelTextColor[ownerState.variant ?? 'text'], + backgroundColor: focusedContainerColor[ownerState.variant ?? 'text'], }, [`&.${buttonClasses.disabled}`]: { // Allows deverloper to specify the disabled icon color var '--md-comp-button-icon-color': 'var(--md-comp-button-disabled-icon-color)', pointerEvents: 'none', // Disable link interactions cursor: 'default', - color: `var(--md-comp-button-disabled-label-text-color, ${disabledLabelTextColor})`, - background: `var(--md-comp-button-disabled-container-color, ${ - disabeldContainerColor[ownerState.variant ?? 'text'] - })`, + color: disabledLabelTextColor, + background: disabeldContainerColor[ownerState.variant ?? 'text'], boxShadow: 'var(--md-comp-button-disabled-container-elevation, none)', // Should be md.sys.elevation.level0 ...(ownerState.variant === 'outlined' && { border: `1px solid ${ From 0cdc39bcbdfefb72599a86a98694b14fb0fe427c Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 27 Oct 2022 14:36:46 +0200 Subject: [PATCH 22/49] Change the theme structure --- .../mui-material-next/src/Button/Button.tsx | 168 +++++++++--------- .../src/styles/Theme.types.ts | 28 ++- .../src/styles/createDarkColorScheme.ts | 58 +++--- .../src/styles/createLightColorScheme.ts | 58 +++--- .../src/styles/extendTheme.ts | 112 ++++++------ 5 files changed, 221 insertions(+), 203 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 98d26bcd06a187..95a0668343c40c 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -92,75 +92,75 @@ export const ButtonRoot = styled('button', { })<{ ownerState: ButtonOwnerState }>(({ ownerState, theme }) => { const containerColor = { elevated: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${ - (theme.vars || theme).palette.md3.colors.surface + (theme.vars || theme).sys.color.surface }`, - filled: (theme.vars || theme).palette.md3.colors[ownerState.color ?? 'primary'], - filledTonal: (theme.vars || theme).palette.md3.colors.secondaryContainer, + filled: (theme.vars || theme).sys.color[ownerState.color ?? 'primary'], + filledTonal: (theme.vars || theme).sys.color.secondaryContainer, outlined: 'none', text: 'none', }; const labelTextColor = { - elevated: (theme.vars || theme).palette.md3.colors.primary, - filled: (theme.vars || theme).palette.md3.colors[ + elevated: (theme.vars || theme).sys.color.primary, + filled: (theme.vars || theme).sys.color[ `on${capitalize(ownerState.color ?? 'primary')}` as keyof MD3ColorSchemeTokens ], - filledTonal: (theme.vars || theme).palette.md3.colors.onSecondaryContainer, - outlined: (theme.vars || theme).palette.md3.colors[ownerState.color ?? 'primary'], - text: (theme.vars || theme).palette.md3.colors[ownerState.color ?? 'primary'], + filledTonal: (theme.vars || theme).sys.color.onSecondaryContainer, + outlined: (theme.vars || theme).sys.color[ownerState.color ?? 'primary'], + text: (theme.vars || theme).sys.color[ownerState.color ?? 'primary'], }; const disabeldContainerColor = { elevated: theme.vars - ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` - : alpha(theme.palette.md3.colors.onSurface, 0.12), + ? `rgba(${theme.vars.sys.color.onSurfaceChannel} / 0.12)` + : alpha(theme.sys.color.onSurface, 0.12), filled: theme.vars - ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` - : alpha(theme.palette.md3.colors.onSurface, 0.12), + ? `rgba(${theme.vars.sys.color.onSurfaceChannel} / 0.12)` + : alpha(theme.sys.color.onSurface, 0.12), filledTonal: theme.vars - ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` - : alpha(theme.palette.md3.colors.onSurface, 0.12), + ? `rgba(${theme.vars.sys.color.onSurfaceChannel} / 0.12)` + : alpha(theme.sys.color.onSurface, 0.12), outlined: 'none', text: 'none', }; const hoveredContainerColor = { elevated: theme.vars - ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).md3.state.hover.stateLayerOpacity + ? `rgba(${(theme.vars || theme).sys.color.primaryChannel} / ${ + (theme.vars || theme).sys.state.hover.stateLayerOpacity })` - : alpha(theme.palette.md3.colors.primary, theme.md3.state.hover.stateLayerOpacity), + : alpha(theme.sys.color.primary, theme.sys.state.hover.stateLayerOpacity), filled: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).md3.state.hover.stateLayerOpacity}))` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).sys.state.hover.stateLayerOpacity}))` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.md3.state.hover.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + 1 - theme.sys.state.hover.stateLayerOpacity, ), filledTonal: theme.vars - ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).md3.state.hover.stateLayerOpacity + ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ + (theme.vars || theme).sys.state.hover.stateLayerOpacity }))` : alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.md3.state.hover.stateLayerOpacity, + theme.sys.color.secondaryContainer, + 1 - theme.sys.state.hover.stateLayerOpacity, ), outlined: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).md3.state.hover.stateLayerOpacity})` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).sys.state.hover.stateLayerOpacity})` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.md3.state.hover.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + theme.sys.state.hover.stateLayerOpacity, ), text: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).md3.state.hover.stateLayerOpacity})` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).sys.state.hover.stateLayerOpacity})` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.md3.state.hover.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + theme.sys.state.hover.stateLayerOpacity, ), }; @@ -174,81 +174,81 @@ export const ButtonRoot = styled('button', { const pressedContainerColor = { elevated: theme.vars - ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).md3.state.pressed.stateLayerOpacity + ? `rgba(${(theme.vars || theme).sys.color.primaryChannel} / ${ + (theme.vars || theme).sys.state.pressed.stateLayerOpacity })` - : alpha(theme.palette.md3.colors.primary, theme.md3.state.pressed.stateLayerOpacity), + : alpha(theme.sys.color.primary, theme.sys.state.pressed.stateLayerOpacity), filled: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).md3.state.pressed.stateLayerOpacity}))` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).sys.state.pressed.stateLayerOpacity}))` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.md3.state.pressed.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + 1 - theme.sys.state.pressed.stateLayerOpacity, ), filledTonal: theme.vars - ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).md3.state.pressed.stateLayerOpacity + ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ + (theme.vars || theme).sys.state.pressed.stateLayerOpacity }))` : alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.md3.state.pressed.stateLayerOpacity, + theme.sys.color.secondaryContainer, + 1 - theme.sys.state.pressed.stateLayerOpacity, ), outlined: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).md3.state.pressed.stateLayerOpacity})` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).sys.state.pressed.stateLayerOpacity})` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.md3.state.pressed.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + theme.sys.state.pressed.stateLayerOpacity, ), text: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).md3.state.pressed.stateLayerOpacity})` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).sys.state.pressed.stateLayerOpacity})` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.md3.state.pressed.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + theme.sys.state.pressed.stateLayerOpacity, ), }; const focusedContainerColor = { elevated: theme.vars - ? `rgba(${(theme.vars || theme).palette.md3.colors.primaryChannel} / ${ - (theme.vars || theme).md3.state.focus.stateLayerOpacity + ? `rgba(${(theme.vars || theme).sys.color.primaryChannel} / ${ + (theme.vars || theme).sys.state.focus.stateLayerOpacity })` - : alpha(theme.palette.md3.colors.primary, theme.md3.state.focus.stateLayerOpacity), + : alpha(theme.sys.color.primary, theme.sys.state.focus.stateLayerOpacity), filled: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).md3.state.focus.stateLayerOpacity}))` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / calc(1 - ${(theme.vars || theme).sys.state.focus.stateLayerOpacity}))` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - 1 - theme.md3.state.focus.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + 1 - theme.sys.state.focus.stateLayerOpacity, ), filledTonal: theme.vars - ? `rgba(${(theme.vars || theme).palette.md3.colors.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).md3.state.focus.stateLayerOpacity + ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ + (theme.vars || theme).sys.state.focus.stateLayerOpacity }))` : alpha( - theme.palette.md3.colors.secondaryContainer, - 1 - theme.md3.state.focus.stateLayerOpacity, + theme.sys.color.secondaryContainer, + 1 - theme.sys.state.focus.stateLayerOpacity, ), outlined: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).md3.state.focus.stateLayerOpacity})` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).sys.state.focus.stateLayerOpacity})` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.md3.state.focus.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + theme.sys.state.focus.stateLayerOpacity, ), text: theme.vars ? `rgba(${ - (theme.vars || theme).palette.md3.colors[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).md3.state.focus.stateLayerOpacity})` + (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] + } / ${(theme.vars || theme).sys.state.focus.stateLayerOpacity})` : alpha( - theme.palette.md3.colors[ownerState.color ?? 'primary'], - theme.md3.state.focus.stateLayerOpacity, + theme.sys.color[ownerState.color ?? 'primary'], + theme.sys.state.focus.stateLayerOpacity, ), }; @@ -260,11 +260,11 @@ export const ButtonRoot = styled('button', { text: 'none', // md.sys.elevation.level0 }; const disabledLabelTextColor = theme.vars - ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.38)` - : alpha(theme.palette.md3.colors.onSurface, 0.38); + ? `rgba(${theme.vars.sys.color.onSurfaceChannel} / 0.38)` + : alpha(theme.sys.color.onSurface, 0.38); const letterSpacing = `${ - theme.md3.typescale.label.large.tracking / theme.md3.typescale.label.large.size + theme.sys.typescale.label.large.tracking / theme.sys.typescale.label.large.size }rem`; return { @@ -308,11 +308,11 @@ export const ButtonRoot = styled('button', { duration: theme.transitions.duration.short, }, ), - fontFamily: (theme.vars || theme).md3.typescale.label.large.family, - fontWeight: (theme.vars || theme).md3.typescale.label.large.weight, - fontSize: theme.typography.pxToRem(theme.md3.typescale.label.large.size), // the pxToRem should be moved to typescale in the future - lineHeight: `calc(${(theme.vars || theme).md3.typescale.label.large.lineHeight} / ${ - theme.md3.typescale.label.large.size + fontFamily: (theme.vars || theme).sys.typescale.label.large.family, + fontWeight: (theme.vars || theme).sys.typescale.label.large.weight, + fontSize: theme.typography.pxToRem(theme.sys.typescale.label.large.size), // the pxToRem should be moved to typescale in the future + lineHeight: `calc(${(theme.vars || theme).sys.typescale.label.large.lineHeight} / ${ + theme.sys.typescale.label.large.size })`, borderRadius: (theme.vars || theme).md3.shape.borderRadius, background: containerColor[ownerState.variant ?? 'text'], @@ -320,19 +320,19 @@ export const ButtonRoot = styled('button', { boxShadow: containerElevation[ownerState.variant ?? 'text'], // Outlined varaiant ...(ownerState.variant === 'outlined' && { - border: `1px solid ${(theme.vars || theme).palette.md3.colors.outline}`, + border: `1px solid ${(theme.vars || theme).sys.color.outline}`, padding: '9px 23px', }), // Sizes are not specified in Material You, this need to be revised ...(ownerState.size === 'small' && { - fontSize: theme.typography.pxToRem(theme.md3.typescale.label.large.size - 1), // the pxToRem should be moved to typescale in the future + fontSize: theme.typography.pxToRem(theme.sys.typescale.label.large.size - 1), // the pxToRem should be moved to typescale in the future padding: '8px 20px', ...(ownerState.variant === 'outlined' && { padding: '7px 19px', }), }), ...(ownerState.size === 'large' && { - fontSize: theme.typography.pxToRem(theme.md3.typescale.label.large.size + 1), // the pxToRem should be moved to typescale in the future + fontSize: theme.typography.pxToRem(theme.sys.typescale.label.large.size + 1), // the pxToRem should be moved to typescale in the future padding: '12px 26px', ...(ownerState.variant === 'outlined' && { padding: '11px 25px', @@ -365,8 +365,8 @@ export const ButtonRoot = styled('button', { ...(ownerState.variant === 'outlined' && { border: `1px solid ${ theme.vars - ? `rgba(${theme.vars.palette.md3.colors.onSurfaceChannel} / 0.12)` - : alpha(theme.palette.md3.colors.onSurface, 0.12) + ? `rgba(${theme.vars.sys.color.onSurfaceChannel} / 0.12)` + : alpha(theme.sys.color.onSurface, 0.12) }`, }), }, diff --git a/packages/mui-material-next/src/styles/Theme.types.ts b/packages/mui-material-next/src/styles/Theme.types.ts index 6f085ed57a72bd..9b9c0852367cd1 100644 --- a/packages/mui-material-next/src/styles/Theme.types.ts +++ b/packages/mui-material-next/src/styles/Theme.types.ts @@ -146,19 +146,31 @@ export interface MD3PaletteWithTokens extends MD3Palettes { export interface Theme extends Omit { useMaterialYou?: boolean; - md3: { - // Others should be added + ref: { + palette: MD3Palettes; + typeface: any; + }; + sys: { + color: MD3ColorSchemeTokens + typescale: MD3Typescale state: MD3States; - typescale: MD3Typescale; + }; + md3: { shape: Shapes; }; - palette: MD2Theme['palette'] & { md3: MD3PaletteWithTokens }; + palette: MD2Theme['palette']; vars: MD2Theme['vars'] & { - palette: MD2Theme['vars']['palette'] & { md3: MD3PaletteWithTokens }; - md3: { - // Others should be added + palette: MD2Theme['vars']['palette']; + ref: { + palette: MD3Palettes; + typeface: any; + }; + sys: { + color: MD3ColorSchemeTokens + typescale: MD3Typescale state: MD3States; - typescale: MD3Typescale; + }; + md3: { shape: Shapes; }; }; diff --git a/packages/mui-material-next/src/styles/createDarkColorScheme.ts b/packages/mui-material-next/src/styles/createDarkColorScheme.ts index 6b8f17ab1c62cb..07815002ae8708 100644 --- a/packages/mui-material-next/src/styles/createDarkColorScheme.ts +++ b/packages/mui-material-next/src/styles/createDarkColorScheme.ts @@ -4,36 +4,34 @@ const createDarkColorScheme = ( getCssVar: (cssVar: string, defaultVal: string) => string, palette: MD3Palettes, ) => ({ - colors: { - surfaceTint: getCssVar('palette-md3-primary-40', palette.primary[40]), - onErrorContainer: getCssVar('palette-md3-error-80', palette.error[80]), - onError: getCssVar('palette-md3-error-20', palette.error[20]), - errorContainer: getCssVar('palette-md3-error-30', palette.error[30]), - onTertiaryContainer: getCssVar('palette-md3-tertiary-90', palette.tertiary[90]), - onTertiary: getCssVar('palette-md3-tertiary-20', palette.tertiary[20]), - tertiaryContainer: getCssVar('palette-md3-tertiary-30', palette.tertiary[30]), - tertiary: getCssVar('palette-md3-tertiary-80', palette.tertiary[80]), - shadow: getCssVar('palette-md3-common-black', palette.common.black), - error: getCssVar('palette-md3-error-80', palette.error[80]), - outline: getCssVar('palette-md3-neutralVariant-60', palette.neutralVariant[60]), - onBackground: getCssVar('palette-md3-neutral-90', palette.neutral[90]), - background: getCssVar('palette-md3-neutral-10', palette.neutral[10]), - inverseOnSurface: getCssVar('palette-md3-neutral-20', palette.neutral[20]), - inverseSurface: getCssVar('palette-md3-neutral-90', palette.neutral[90]), - onSurfaceVariant: getCssVar('palette-md3-neutralVariant-80', palette.neutralVariant[80]), - onSurface: getCssVar('palette-md3-neutral-90', palette.neutral[90]), - surfaceVariant: getCssVar('palette-md3-neutralVariant-30', palette.neutralVariant[30]), - surface: getCssVar('palette-md3-neutral-10', palette.neutral[10]), - onSecondaryContainer: getCssVar('palette-md3-secondary-90', palette.secondary[90]), - onSecondary: getCssVar('palette-md3-secondary-20', palette.secondary[20]), - secondaryContainer: getCssVar('palette-md3-secondary-30', palette.secondary[30]), - secondary: getCssVar('palette-md3-secondary-80', palette.secondary[80]), - inversePrimary: getCssVar('palette-md3-primary-40', palette.primary[40]), - onPrimaryContainer: getCssVar('palette-md3-primary-90', palette.primary[90]), - onPrimary: getCssVar('palette-md3-primary-20', palette.primary[20]), - primaryContainer: getCssVar('palette-md3-primary-30', palette.primary[30]), - primary: getCssVar('palette-md3-primary-80', palette.primary[80]), - }, + surfaceTint: getCssVar('ref-palette-primary-40', palette.primary[40]), + onErrorContainer: getCssVar('ref-palette-error-80', palette.error[80]), + onError: getCssVar('ref-palette-error-20', palette.error[20]), + errorContainer: getCssVar('ref-palette-error-30', palette.error[30]), + onTertiaryContainer: getCssVar('ref-palette-tertiary-90', palette.tertiary[90]), + onTertiary: getCssVar('ref-palette-tertiary-20', palette.tertiary[20]), + tertiaryContainer: getCssVar('ref-palette-tertiary-30', palette.tertiary[30]), + tertiary: getCssVar('ref-palette-tertiary-80', palette.tertiary[80]), + shadow: getCssVar('ref-palette-common-black', palette.common.black), + error: getCssVar('ref-palette-error-80', palette.error[80]), + outline: getCssVar('ref-palette-neutralVariant-60', palette.neutralVariant[60]), + onBackground: getCssVar('ref-palette-neutral-90', palette.neutral[90]), + background: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + inverseOnSurface: getCssVar('ref-palette-neutral-20', palette.neutral[20]), + inverseSurface: getCssVar('ref-palette-neutral-90', palette.neutral[90]), + onSurfaceVariant: getCssVar('ref-palette-neutralVariant-80', palette.neutralVariant[80]), + onSurface: getCssVar('ref-palette-neutral-90', palette.neutral[90]), + surfaceVariant: getCssVar('ref-palette-neutralVariant-30', palette.neutralVariant[30]), + surface: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + onSecondaryContainer: getCssVar('ref-palette-secondary-90', palette.secondary[90]), + onSecondary: getCssVar('ref-palette-secondary-20', palette.secondary[20]), + secondaryContainer: getCssVar('ref-palette-secondary-30', palette.secondary[30]), + secondary: getCssVar('ref-palette-secondary-80', palette.secondary[80]), + inversePrimary: getCssVar('ref-palette-primary-40', palette.primary[40]), + onPrimaryContainer: getCssVar('ref-palette-primary-90', palette.primary[90]), + onPrimary: getCssVar('ref-palette-primary-20', palette.primary[20]), + primaryContainer: getCssVar('ref-palette-primary-30', palette.primary[30]), + primary: getCssVar('ref-palette-primary-80', palette.primary[80]), }); export default createDarkColorScheme; diff --git a/packages/mui-material-next/src/styles/createLightColorScheme.ts b/packages/mui-material-next/src/styles/createLightColorScheme.ts index 2498953855df5a..c2e87465df4153 100644 --- a/packages/mui-material-next/src/styles/createLightColorScheme.ts +++ b/packages/mui-material-next/src/styles/createLightColorScheme.ts @@ -4,36 +4,34 @@ const createLightColorScheme = ( getCssVar: (cssVar: string, defaultVal: string) => string, palette: MD3Palettes, ) => ({ - colors: { - surfaceTint: getCssVar('palette-md3-primary-40', palette.primary[40]), - onErrorContainer: getCssVar('palette-md3-error-10', palette.error[10]), - onError: getCssVar('palette-md3-error-100', palette.error[100]), - errorContainer: getCssVar('palette-md3-error-90', palette.error[90]), - onTertiaryContainer: getCssVar('palette-md3-tertiary-10', palette.tertiary[10]), - onTertiary: getCssVar('palette-md3-tertiary-100', palette.tertiary[100]), - tertiaryContainer: getCssVar('palette-md3-tertiary-90', palette.tertiary[90]), - tertiary: getCssVar('palette-md3-tertiary-40', palette.tertiary[40]), - shadow: getCssVar('palette-md3-common-black', palette.common.black), - error: getCssVar('palette-md3-error-40', palette.error[40]), - outline: getCssVar('palette-md3-neutralVariant-50', palette.neutralVariant[50]), - onBackground: getCssVar('palette-md3-neutral-10', palette.neutral[10]), - background: getCssVar('palette-md3-neutral-99', palette.neutral[99]), - inverseOnSurface: getCssVar('palette-md3-neutral-95', palette.neutral[95]), - inverseSurface: getCssVar('palette-md3-neutral-20', palette.neutral[20]), - onSurfaceVariant: getCssVar('palette-md3-neutralVariant-30', palette.neutralVariant[30]), - onSurface: getCssVar('palette-md3-neutral-10', palette.neutral[10]), - surfaceVariant: getCssVar('palette-md3-neutralVariant-90', palette.neutralVariant[90]), - surface: getCssVar('palette-md3-neutral-99', palette.neutral[99]), - onSecondaryContainer: getCssVar('palette-md3-secondary-10', palette.secondary[10]), - onSecondary: getCssVar('palette-md3-secondary-100', palette.secondary[100]), - secondaryContainer: getCssVar('palette-md3-secondary-90', palette.secondary[90]), - secondary: getCssVar('palette-md3-secondary-40', palette.secondary[40]), - inversePrimary: getCssVar('palette-md3-primary-80', palette.primary[80]), - onPrimaryContainer: getCssVar('palette-md3-primary-10', palette.primary[10]), - onPrimary: getCssVar('palette-md3-primary-100', palette.primary[100]), - primaryContainer: getCssVar('palette-md3-primary-90', palette.primary[90]), - primary: getCssVar('palette-md3-primary-40', palette.primary[40]), - }, + surfaceTint: getCssVar('ref-palette-primary-40', palette.primary[40]), + onErrorContainer: getCssVar('ref-palette-error-10', palette.error[10]), + onError: getCssVar('ref-palette-error-100', palette.error[100]), + errorContainer: getCssVar('ref-palette-error-90', palette.error[90]), + onTertiaryContainer: getCssVar('ref-palette-tertiary-10', palette.tertiary[10]), + onTertiary: getCssVar('ref-palette-tertiary-100', palette.tertiary[100]), + tertiaryContainer: getCssVar('ref-palette-tertiary-90', palette.tertiary[90]), + tertiary: getCssVar('ref-palette-tertiary-40', palette.tertiary[40]), + shadow: getCssVar('ref-palette-common-black', palette.common.black), + error: getCssVar('ref-palette-error-40', palette.error[40]), + outline: getCssVar('ref-palette-neutralVariant-50', palette.neutralVariant[50]), + onBackground: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + background: getCssVar('ref-palette-neutral-99', palette.neutral[99]), + inverseOnSurface: getCssVar('ref-palette-neutral-95', palette.neutral[95]), + inverseSurface: getCssVar('ref-palette-neutral-20', palette.neutral[20]), + onSurfaceVariant: getCssVar('ref-palette-neutralVariant-30', palette.neutralVariant[30]), + onSurface: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + surfaceVariant: getCssVar('ref-palette-neutralVariant-90', palette.neutralVariant[90]), + surface: getCssVar('ref-palette-neutral-99', palette.neutral[99]), + onSecondaryContainer: getCssVar('ref-palette-secondary-10', palette.secondary[10]), + onSecondary: getCssVar('ref-palette-secondary-100', palette.secondary[100]), + secondaryContainer: getCssVar('ref-palette-secondary-90', palette.secondary[90]), + secondary: getCssVar('ref-palette-secondary-40', palette.secondary[40]), + inversePrimary: getCssVar('ref-palette-primary-80', palette.primary[80]), + onPrimaryContainer: getCssVar('ref-palette-primary-10', palette.primary[10]), + onPrimary: getCssVar('ref-palette-primary-100', palette.primary[100]), + primaryContainer: getCssVar('ref-palette-primary-90', palette.primary[90]), + primary: getCssVar('ref-palette-primary-40', palette.primary[40]), }); export default createLightColorScheme; diff --git a/packages/mui-material-next/src/styles/extendTheme.ts b/packages/mui-material-next/src/styles/extendTheme.ts index 6f9fe3f883dfb1..bac8d35a4adc2f 100644 --- a/packages/mui-material-next/src/styles/extendTheme.ts +++ b/packages/mui-material-next/src/styles/extendTheme.ts @@ -46,62 +46,67 @@ function setColor(obj: any, key: string, defaultValue: any) { export const createGetCssVar = (cssVarPrefix = 'mui') => systemCreateGetCssVar(cssVarPrefix); export default function extendTheme( - options: CssVarsThemeOptions & { useMaterialYou?: boolean } = {}, + options: CssVarsThemeOptions = {}, ...args: any[] ) { const { colorSchemes: colorSchemesInput = {}, cssVarPrefix = 'mui', - useMaterialYou = true, ...input } = options; const getCssVar = createGetCssVar(cssVarPrefix); - const md3LightPalette = { - ...md3CommonPalette, - ...createMd3LightColorScheme(getCssVar, md3CommonPalette), - }; - - const md3DarkPalette = { - ...md3CommonPalette, - ...createMd3DarkColorScheme(getCssVar, md3CommonPalette), - }; + const md3LightColors = createMd3LightColorScheme(getCssVar, md3CommonPalette); + const md3DarkColors = createMd3DarkColorScheme(getCssVar, md3CommonPalette); // @ts-ignore - it's fine, everything that is not supported will be spread - const { palette: lightPalette, ...muiTheme } = createThemeWithoutVars({ + const { palette: lightPalette, sys: lightSys, ref: lightRef, ...muiTheme } = createThemeWithoutVars({ ...input, - ...(useMaterialYou && { - useMaterialYou: true, - md3: { - typescale: md3Typescale, - typeface: md3Typeface, - state: md3State, - shape: { - borderRadius: 100, - ...input?.shape, - }, + // Material You specific tokens + useMaterialYou: true, + ref: { + ...input.ref, + typeface: { ...md3Typeface, ...input.ref?.typeface }, + palette: { + ...md3CommonPalette, + ...colorSchemesInput.light?.ref?.palette, + } + }, + sys: { + ...input.sys, + typescale: { ...md3Typescale, ...input.sys?.typescale }, + state: { ...md3State, ...input.sys?.state }, + color: { ...md3LightColors, ...colorSchemesInput.light?.sys?.color } + }, + md3: { + shape: { + borderRadius: 100, + ...input?.shape, }, - }), + }, palette: { ...(colorSchemesInput.light && colorSchemesInput.light?.palette), - ...(useMaterialYou && { - md3: { - ...md3LightPalette, - ...colorSchemesInput.light?.palette?.md3, - }, - }), }, }); - const { palette: darkPalette } = createThemeWithoutVars({ + const { palette: darkPalette, sys: darkSys, ref: darkRef } = createThemeWithoutVars({ palette: { mode: 'dark', ...colorSchemesInput.dark?.palette, - ...(useMaterialYou && { - md3: { - ...md3DarkPalette, - ...colorSchemesInput.dark?.palette?.md3, - }, - }), + }, + ref: { + ...input.ref, + typeface: { ...md3Typeface, ...input.ref?.typeface }, + palette: { + ...md3CommonPalette, + ...colorSchemesInput.dark?.ref?.palette, + } + }, + + sys: { + ...input.sys, + typescale: { ...md3Typescale, ...input.sys?.typescale }, + state: { ...md3State, ...input.sys?.state }, + color: { ...md3DarkColors, ...colorSchemesInput.dark?.sys?.color } }, }); @@ -123,6 +128,8 @@ export default function extendTheme( ...colorSchemesInput.light?.opacity, }, overlays: colorSchemesInput.light?.overlays || defaultLightOverlays, + sys: lightSys, + ref: lightRef }, dark: { ...colorSchemesInput.dark, @@ -136,6 +143,8 @@ export default function extendTheme( ...colorSchemesInput.dark?.opacity, }, overlays: colorSchemesInput.dark?.overlays || defaultDarkOverlays, + sys: darkSys, + ref: darkRef }, }, }; @@ -146,6 +155,9 @@ export default function extendTheme( md3: MD3Palettes & { colors: MD3ColorSchemeTokens }; }; + const colorSchemeSys = theme.colorSchemes[key as SupportedColorScheme].sys; + const colorSchemeRef = theme.colorSchemes[key as SupportedColorScheme].ref; + // attach black & white channels to common node if (key === 'light') { setColor(palette.common, 'background', '#fff'); @@ -365,21 +377,19 @@ export default function extendTheme( } }); - // Needs to be handled better, the values are now hardcoded to the default values for these tokens - if (useMaterialYou) { - if (key === 'light') { - palette.md3.colors.primaryChannel = colorChannel(palette.md3.primary['40']); - palette.md3.colors.secondaryChannel = colorChannel(palette.md3.secondary['40']); - palette.md3.colors.tertiaryChannel = colorChannel(palette.md3.tertiary['40']); - palette.md3.colors.secondaryContainerChannel = colorChannel(palette.md3.secondary['90']); - palette.md3.colors.onSurfaceChannel = colorChannel(palette.md3.neutral['10']); - } else { - palette.md3.colors.primaryChannel = colorChannel(palette.md3.primary['80']); - palette.md3.colors.secondaryChannel = colorChannel(palette.md3.secondary['80']); - palette.md3.colors.tertiaryChannel = colorChannel(palette.md3.tertiary['80']); - palette.md3.colors.secondaryContainerChannel = colorChannel(palette.md3.secondary['30']); - palette.md3.colors.onSurfaceChannel = colorChannel(palette.md3.neutral['90']); - } + // Material You specific channels + if (key === 'light') { + colorSchemeSys.color.primaryChannel = colorChannel(colorSchemeRef.palette.primary['40']); + colorSchemeSys.color.secondaryChannel = colorChannel(colorSchemeRef.palette.secondary['40']); + colorSchemeSys.color.tertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['40']); + colorSchemeSys.color.secondaryContainerChannel = colorChannel(colorSchemeRef.palette.secondary['90']); + colorSchemeSys.color.onSurfaceChannel = colorChannel(colorSchemeRef.palette.neutral['10']); + } else { + colorSchemeSys.color.primaryChannel = colorChannel(colorSchemeRef.palette.primary['80']); + colorSchemeSys.color.secondaryChannel = colorChannel(colorSchemeRef.palette.secondary['80']); + colorSchemeSys.color.tertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['80']); + colorSchemeSys.color.secondaryContainerChannel = colorChannel(colorSchemeRef.palette.secondary['30']); + colorSchemeSys.color.onSurfaceChannel = colorChannel(colorSchemeRef.palette.neutral['90']); } }); From db6ddd94cd888b036ae9f116657060bd200e3556 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 28 Oct 2022 09:03:56 +0200 Subject: [PATCH 23/49] Some fixed and types issues --- docs/pages/experiments/md3/index.tsx | 110 +++++++++++++++++- .../mui-material-next/src/Button/Button.tsx | 51 ++++---- .../src/styles/Theme.types.ts | 64 ++++++---- .../src/styles/createDarkColorScheme.ts | 56 ++++----- .../src/styles/createLightColorScheme.ts | 56 ++++----- .../src/styles/createMd3Palette.ts | 77 ------------ .../src/styles/extendTheme.ts | 56 ++++----- 7 files changed, 256 insertions(+), 214 deletions(-) delete mode 100644 packages/mui-material-next/src/styles/createMd3Palette.ts diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index ae9b5492e18357..27492327259423 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -156,8 +156,114 @@ const DemoComponents = () => { ); }; -// default MD3 theme -const cssVarsTheme = extendTheme(); +const customPalette = { + primary: { + '0': '#000000', + '10': '#1b1d00', + '20': '#303300', + '30': '#464a00', + '40': '#5e6300', + '50': '#777c0b', + '60': '#919729', + '70': '#abb242', + '80': '#c7cd5a', + '90': '#e3ea73', + '95': '#f2f880', + '99': '#ffffd3', + '100': '#ffffff', + }, + secondary: { + '0': '#000000', + '10': '#1c1d06', + '20': '#313219', + '30': '#47482e', + '40': '#5f6043', + '50': '#78795b', + '60': '#929373', + '70': '#adad8c', + '80': '#c8c9a6', + '90': '#e5e5c0', + '95': '#f3f3ce', + '99': '#fffed9', + '100': '#ffffff', + }, + tertiary: { + '0': '#000000', + '10': '#002118', + '20': '#09372b', + '30': '#244e41', + '40': '#3c6658', + '50': '#557f71', + '60': '#6e9a8a', + '70': '#88b4a4', + '80': '#a3d0bf', + '90': '#bfecdb', + '95': '#ccfbe9', + '99': '#f3fff8', + '100': '#ffffff', + }, + neutral: { + '0': '#000000', + '10': '#1c1c17', + '20': '#31312b', + '30': '#484741', + '40': '#605e58', + '50': '#797770', + '60': '#929189', + '70': '#adaba3', + '80': '#c9c6be', + '90': '#e5e2da', + '95': '#f4f1e8', + '99': '#ffffd3', + '100': '#ffffff', + }, + neutralVariant: { + '0': '#000000', + '10': '#1c1c12', + '20': '#313125', + '30': '#48473b', + '40': '#5f5f51', + '50': '#787869', + '60': '#929182', + '70': '#adac9c', + '80': '#c9c7b6', + '90': '#e5e3d2', + '95': '#f4f1df', + '99': '#ffffd3', + '100': '#ffffff', + }, + error: { + '0': '#000000', + '10': '#410002', + '20': '#690005', + '30': '#93000a', + '40': '#ba1a1a', + '50': '#de3730', + '60': '#ff5449', + '70': '#ff897d', + '80': '#ffb4ab', + '90': '#ffdad6', + '95': '#ffedea', + '99': '#fffbff', + '100': '#ffffff', + }, +}; + +// custom MD3 theme +const cssVarsTheme = extendTheme({ + colorSchemes: { + light: { + ref: { + palette: customPalette, + }, + }, + dark: { + ref: { + palette: customPalette, + }, + }, + }, +}); export default function App() { return ( diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 95a0668343c40c..e11c82d6fab8ae 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -142,22 +142,19 @@ export const ButtonRoot = styled('button', { ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ (theme.vars || theme).sys.state.hover.stateLayerOpacity }))` - : alpha( - theme.sys.color.secondaryContainer, - 1 - theme.sys.state.hover.stateLayerOpacity, - ), + : alpha(theme.sys.color.secondaryContainer, 1 - theme.sys.state.hover.stateLayerOpacity), outlined: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).sys.state.hover.stateLayerOpacity})` + ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + (theme.vars || theme).sys.state.hover.stateLayerOpacity + })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.hover.stateLayerOpacity, ), text: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).sys.state.hover.stateLayerOpacity})` + ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + (theme.vars || theme).sys.state.hover.stateLayerOpacity + })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.hover.stateLayerOpacity, @@ -190,22 +187,19 @@ export const ButtonRoot = styled('button', { ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ (theme.vars || theme).sys.state.pressed.stateLayerOpacity }))` - : alpha( - theme.sys.color.secondaryContainer, - 1 - theme.sys.state.pressed.stateLayerOpacity, - ), + : alpha(theme.sys.color.secondaryContainer, 1 - theme.sys.state.pressed.stateLayerOpacity), outlined: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).sys.state.pressed.stateLayerOpacity})` + ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + (theme.vars || theme).sys.state.pressed.stateLayerOpacity + })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.pressed.stateLayerOpacity, ), text: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).sys.state.pressed.stateLayerOpacity})` + ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + (theme.vars || theme).sys.state.pressed.stateLayerOpacity + })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.pressed.stateLayerOpacity, @@ -230,22 +224,19 @@ export const ButtonRoot = styled('button', { ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ (theme.vars || theme).sys.state.focus.stateLayerOpacity }))` - : alpha( - theme.sys.color.secondaryContainer, - 1 - theme.sys.state.focus.stateLayerOpacity, - ), + : alpha(theme.sys.color.secondaryContainer, 1 - theme.sys.state.focus.stateLayerOpacity), outlined: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).sys.state.focus.stateLayerOpacity})` + ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + (theme.vars || theme).sys.state.focus.stateLayerOpacity + })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.focus.stateLayerOpacity, ), text: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / ${(theme.vars || theme).sys.state.focus.stateLayerOpacity})` + ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + (theme.vars || theme).sys.state.focus.stateLayerOpacity + })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.focus.stateLayerOpacity, diff --git a/packages/mui-material-next/src/styles/Theme.types.ts b/packages/mui-material-next/src/styles/Theme.types.ts index 9b9c0852367cd1..5db38f25017d04 100644 --- a/packages/mui-material-next/src/styles/Theme.types.ts +++ b/packages/mui-material-next/src/styles/Theme.types.ts @@ -6,19 +6,6 @@ import { CssVarsThemeOptions as MD2CssVarsThemeOptions, } from '@mui/material/styles'; -export interface ColorSystemOptions extends Omit { - palette?: MD2ColorSystemOptions['palette'] & { - md3?: MD3Palettes & { colors: MD3ColorSchemeTokens }; - }; -} - -export interface CssVarsThemeOptions extends Omit { - /** - * Color schemes configuration - */ - colorSchemes?: Partial>; -} - export interface MD3Tones { 0: string; 10: string; @@ -47,8 +34,6 @@ export interface MD3Palettes { }; } -export interface MD3PalettesOptions extends Partial {} - export interface MD3ColorSchemeTokens { primary: string; onPrimary: string; @@ -94,7 +79,15 @@ export interface MD3ColorSchemeTokens { secondaryContainerChannel: string; } -export interface MD3ColorSchemeTokensOptions extends Partial {} +export interface MD3Typeface { + plain: string; + brand: string; + weight: { + bold: string; + medium: string; + regular: string; + }; +} export interface MD3States { hover: { @@ -140,19 +133,44 @@ export interface Shapes { borderRadius: number; } -export interface MD3PaletteWithTokens extends MD3Palettes { - colors: MD3ColorSchemeTokens; +export interface MD3CssVarsThemeOptions extends Omit { + md3?: { + shape?: Partial; + }; + ref?: { + typeface?: Partial; + }; + sys?: { + typescale?: Partial; + state?: Partial; + }; +} + +export interface ColorSystemOptions extends MD2ColorSystemOptions { + ref?: { + palette?: Partial; + }; + sys?: { + color?: Partial; + }; +} + +export interface CssVarsThemeOptions extends Omit { + /** + * Color schemes configuration + */ + colorSchemes?: Partial>; } export interface Theme extends Omit { useMaterialYou?: boolean; ref: { palette: MD3Palettes; - typeface: any; + typeface: MD3Typeface; }; sys: { - color: MD3ColorSchemeTokens - typescale: MD3Typescale + color: MD3ColorSchemeTokens; + typescale: MD3Typescale; state: MD3States; }; md3: { @@ -166,8 +184,8 @@ export interface Theme extends Omit { typeface: any; }; sys: { - color: MD3ColorSchemeTokens - typescale: MD3Typescale + color: MD3ColorSchemeTokens; + typescale: MD3Typescale; state: MD3States; }; md3: { diff --git a/packages/mui-material-next/src/styles/createDarkColorScheme.ts b/packages/mui-material-next/src/styles/createDarkColorScheme.ts index 07815002ae8708..55ffd8e5707df4 100644 --- a/packages/mui-material-next/src/styles/createDarkColorScheme.ts +++ b/packages/mui-material-next/src/styles/createDarkColorScheme.ts @@ -4,34 +4,34 @@ const createDarkColorScheme = ( getCssVar: (cssVar: string, defaultVal: string) => string, palette: MD3Palettes, ) => ({ - surfaceTint: getCssVar('ref-palette-primary-40', palette.primary[40]), - onErrorContainer: getCssVar('ref-palette-error-80', palette.error[80]), - onError: getCssVar('ref-palette-error-20', palette.error[20]), - errorContainer: getCssVar('ref-palette-error-30', palette.error[30]), - onTertiaryContainer: getCssVar('ref-palette-tertiary-90', palette.tertiary[90]), - onTertiary: getCssVar('ref-palette-tertiary-20', palette.tertiary[20]), - tertiaryContainer: getCssVar('ref-palette-tertiary-30', palette.tertiary[30]), - tertiary: getCssVar('ref-palette-tertiary-80', palette.tertiary[80]), - shadow: getCssVar('ref-palette-common-black', palette.common.black), - error: getCssVar('ref-palette-error-80', palette.error[80]), - outline: getCssVar('ref-palette-neutralVariant-60', palette.neutralVariant[60]), - onBackground: getCssVar('ref-palette-neutral-90', palette.neutral[90]), - background: getCssVar('ref-palette-neutral-10', palette.neutral[10]), - inverseOnSurface: getCssVar('ref-palette-neutral-20', palette.neutral[20]), - inverseSurface: getCssVar('ref-palette-neutral-90', palette.neutral[90]), - onSurfaceVariant: getCssVar('ref-palette-neutralVariant-80', palette.neutralVariant[80]), - onSurface: getCssVar('ref-palette-neutral-90', palette.neutral[90]), - surfaceVariant: getCssVar('ref-palette-neutralVariant-30', palette.neutralVariant[30]), - surface: getCssVar('ref-palette-neutral-10', palette.neutral[10]), - onSecondaryContainer: getCssVar('ref-palette-secondary-90', palette.secondary[90]), - onSecondary: getCssVar('ref-palette-secondary-20', palette.secondary[20]), - secondaryContainer: getCssVar('ref-palette-secondary-30', palette.secondary[30]), - secondary: getCssVar('ref-palette-secondary-80', palette.secondary[80]), - inversePrimary: getCssVar('ref-palette-primary-40', palette.primary[40]), - onPrimaryContainer: getCssVar('ref-palette-primary-90', palette.primary[90]), - onPrimary: getCssVar('ref-palette-primary-20', palette.primary[20]), - primaryContainer: getCssVar('ref-palette-primary-30', palette.primary[30]), - primary: getCssVar('ref-palette-primary-80', palette.primary[80]), + surfaceTint: getCssVar('ref-palette-primary-40', palette.primary[40]), + onErrorContainer: getCssVar('ref-palette-error-80', palette.error[80]), + onError: getCssVar('ref-palette-error-20', palette.error[20]), + errorContainer: getCssVar('ref-palette-error-30', palette.error[30]), + onTertiaryContainer: getCssVar('ref-palette-tertiary-90', palette.tertiary[90]), + onTertiary: getCssVar('ref-palette-tertiary-20', palette.tertiary[20]), + tertiaryContainer: getCssVar('ref-palette-tertiary-30', palette.tertiary[30]), + tertiary: getCssVar('ref-palette-tertiary-80', palette.tertiary[80]), + shadow: getCssVar('ref-palette-common-black', palette.common.black), + error: getCssVar('ref-palette-error-80', palette.error[80]), + outline: getCssVar('ref-palette-neutralVariant-60', palette.neutralVariant[60]), + onBackground: getCssVar('ref-palette-neutral-90', palette.neutral[90]), + background: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + inverseOnSurface: getCssVar('ref-palette-neutral-20', palette.neutral[20]), + inverseSurface: getCssVar('ref-palette-neutral-90', palette.neutral[90]), + onSurfaceVariant: getCssVar('ref-palette-neutralVariant-80', palette.neutralVariant[80]), + onSurface: getCssVar('ref-palette-neutral-90', palette.neutral[90]), + surfaceVariant: getCssVar('ref-palette-neutralVariant-30', palette.neutralVariant[30]), + surface: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + onSecondaryContainer: getCssVar('ref-palette-secondary-90', palette.secondary[90]), + onSecondary: getCssVar('ref-palette-secondary-20', palette.secondary[20]), + secondaryContainer: getCssVar('ref-palette-secondary-30', palette.secondary[30]), + secondary: getCssVar('ref-palette-secondary-80', palette.secondary[80]), + inversePrimary: getCssVar('ref-palette-primary-40', palette.primary[40]), + onPrimaryContainer: getCssVar('ref-palette-primary-90', palette.primary[90]), + onPrimary: getCssVar('ref-palette-primary-20', palette.primary[20]), + primaryContainer: getCssVar('ref-palette-primary-30', palette.primary[30]), + primary: getCssVar('ref-palette-primary-80', palette.primary[80]), }); export default createDarkColorScheme; diff --git a/packages/mui-material-next/src/styles/createLightColorScheme.ts b/packages/mui-material-next/src/styles/createLightColorScheme.ts index c2e87465df4153..b5894088a3de0e 100644 --- a/packages/mui-material-next/src/styles/createLightColorScheme.ts +++ b/packages/mui-material-next/src/styles/createLightColorScheme.ts @@ -4,34 +4,34 @@ const createLightColorScheme = ( getCssVar: (cssVar: string, defaultVal: string) => string, palette: MD3Palettes, ) => ({ - surfaceTint: getCssVar('ref-palette-primary-40', palette.primary[40]), - onErrorContainer: getCssVar('ref-palette-error-10', palette.error[10]), - onError: getCssVar('ref-palette-error-100', palette.error[100]), - errorContainer: getCssVar('ref-palette-error-90', palette.error[90]), - onTertiaryContainer: getCssVar('ref-palette-tertiary-10', palette.tertiary[10]), - onTertiary: getCssVar('ref-palette-tertiary-100', palette.tertiary[100]), - tertiaryContainer: getCssVar('ref-palette-tertiary-90', palette.tertiary[90]), - tertiary: getCssVar('ref-palette-tertiary-40', palette.tertiary[40]), - shadow: getCssVar('ref-palette-common-black', palette.common.black), - error: getCssVar('ref-palette-error-40', palette.error[40]), - outline: getCssVar('ref-palette-neutralVariant-50', palette.neutralVariant[50]), - onBackground: getCssVar('ref-palette-neutral-10', palette.neutral[10]), - background: getCssVar('ref-palette-neutral-99', palette.neutral[99]), - inverseOnSurface: getCssVar('ref-palette-neutral-95', palette.neutral[95]), - inverseSurface: getCssVar('ref-palette-neutral-20', palette.neutral[20]), - onSurfaceVariant: getCssVar('ref-palette-neutralVariant-30', palette.neutralVariant[30]), - onSurface: getCssVar('ref-palette-neutral-10', palette.neutral[10]), - surfaceVariant: getCssVar('ref-palette-neutralVariant-90', palette.neutralVariant[90]), - surface: getCssVar('ref-palette-neutral-99', palette.neutral[99]), - onSecondaryContainer: getCssVar('ref-palette-secondary-10', palette.secondary[10]), - onSecondary: getCssVar('ref-palette-secondary-100', palette.secondary[100]), - secondaryContainer: getCssVar('ref-palette-secondary-90', palette.secondary[90]), - secondary: getCssVar('ref-palette-secondary-40', palette.secondary[40]), - inversePrimary: getCssVar('ref-palette-primary-80', palette.primary[80]), - onPrimaryContainer: getCssVar('ref-palette-primary-10', palette.primary[10]), - onPrimary: getCssVar('ref-palette-primary-100', palette.primary[100]), - primaryContainer: getCssVar('ref-palette-primary-90', palette.primary[90]), - primary: getCssVar('ref-palette-primary-40', palette.primary[40]), + surfaceTint: getCssVar('ref-palette-primary-40', palette.primary[40]), + onErrorContainer: getCssVar('ref-palette-error-10', palette.error[10]), + onError: getCssVar('ref-palette-error-100', palette.error[100]), + errorContainer: getCssVar('ref-palette-error-90', palette.error[90]), + onTertiaryContainer: getCssVar('ref-palette-tertiary-10', palette.tertiary[10]), + onTertiary: getCssVar('ref-palette-tertiary-100', palette.tertiary[100]), + tertiaryContainer: getCssVar('ref-palette-tertiary-90', palette.tertiary[90]), + tertiary: getCssVar('ref-palette-tertiary-40', palette.tertiary[40]), + shadow: getCssVar('ref-palette-common-black', palette.common.black), + error: getCssVar('ref-palette-error-40', palette.error[40]), + outline: getCssVar('ref-palette-neutralVariant-50', palette.neutralVariant[50]), + onBackground: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + background: getCssVar('ref-palette-neutral-99', palette.neutral[99]), + inverseOnSurface: getCssVar('ref-palette-neutral-95', palette.neutral[95]), + inverseSurface: getCssVar('ref-palette-neutral-20', palette.neutral[20]), + onSurfaceVariant: getCssVar('ref-palette-neutralVariant-30', palette.neutralVariant[30]), + onSurface: getCssVar('ref-palette-neutral-10', palette.neutral[10]), + surfaceVariant: getCssVar('ref-palette-neutralVariant-90', palette.neutralVariant[90]), + surface: getCssVar('ref-palette-neutral-99', palette.neutral[99]), + onSecondaryContainer: getCssVar('ref-palette-secondary-10', palette.secondary[10]), + onSecondary: getCssVar('ref-palette-secondary-100', palette.secondary[100]), + secondaryContainer: getCssVar('ref-palette-secondary-90', palette.secondary[90]), + secondary: getCssVar('ref-palette-secondary-40', palette.secondary[40]), + inversePrimary: getCssVar('ref-palette-primary-80', palette.primary[80]), + onPrimaryContainer: getCssVar('ref-palette-primary-10', palette.primary[10]), + onPrimary: getCssVar('ref-palette-primary-100', palette.primary[100]), + primaryContainer: getCssVar('ref-palette-primary-90', palette.primary[90]), + primary: getCssVar('ref-palette-primary-40', palette.primary[40]), }); export default createLightColorScheme; diff --git a/packages/mui-material-next/src/styles/createMd3Palette.ts b/packages/mui-material-next/src/styles/createMd3Palette.ts deleted file mode 100644 index 3a08f2a242c1d6..00000000000000 --- a/packages/mui-material-next/src/styles/createMd3Palette.ts +++ /dev/null @@ -1,77 +0,0 @@ -import { deepmerge } from '@mui/utils'; -import { MD3PaletteWithTokens } from './Theme.types'; -import globalPalette from './palette'; - -const createMd3Palette = (palette: MD3PaletteWithTokens, mode = 'light'): MD3PaletteWithTokens => { - const resolvedGlobalPalette = deepmerge(globalPalette, palette) as MD3PaletteWithTokens; - - return { - ...resolvedGlobalPalette, - colors: { - ...(mode === 'light' - ? { - surfaceTint: resolvedGlobalPalette.primary['40'], - onErrorContainer: resolvedGlobalPalette.error['10'], - onError: resolvedGlobalPalette.error['100'], - errorContainer: resolvedGlobalPalette.error['90'], - onTertiaryContainer: resolvedGlobalPalette.tertiary['10'], - onTertiary: resolvedGlobalPalette.tertiary['100'], - tertiaryContainer: resolvedGlobalPalette.tertiary['90'], - tertiary: resolvedGlobalPalette.tertiary['40'], - shadow: resolvedGlobalPalette.common.black, - error: resolvedGlobalPalette.error['40'], - outline: resolvedGlobalPalette.neutralVariant['50'], - onBackground: resolvedGlobalPalette.neutral['10'], - background: resolvedGlobalPalette.neutral['99'], - inverseOnSurface: resolvedGlobalPalette.neutral['95'], - inverseSurface: resolvedGlobalPalette.neutral['20'], - onSurfaceVariant: resolvedGlobalPalette.neutralVariant['30'], - onSurface: resolvedGlobalPalette.neutral['10'], - surfaceVariant: resolvedGlobalPalette.neutralVariant['90'], - surface: resolvedGlobalPalette.neutral['99'], - onSecondaryContainer: resolvedGlobalPalette.secondary['10'], - onSecondary: resolvedGlobalPalette.secondary['100'], - secondaryContainer: resolvedGlobalPalette.secondary['90'], - secondary: resolvedGlobalPalette.secondary['40'], - inversePrimary: resolvedGlobalPalette.primary['80'], - onPrimaryContainer: resolvedGlobalPalette.primary['10'], - onPrimary: resolvedGlobalPalette.primary['100'], - primaryContainer: resolvedGlobalPalette.primary['90'], - primary: resolvedGlobalPalette.primary['40'], - } - : { - surfaceTint: resolvedGlobalPalette.primary['40'], - onErrorContainer: resolvedGlobalPalette.error['80'], - onError: resolvedGlobalPalette.error['20'], - errorContainer: resolvedGlobalPalette.error['30'], - onTertiaryContainer: resolvedGlobalPalette.tertiary['90'], - onTertiary: resolvedGlobalPalette.tertiary['20'], - tertiaryContainer: resolvedGlobalPalette.tertiary['30'], - tertiary: resolvedGlobalPalette.tertiary['80'], - shadow: resolvedGlobalPalette.common.black, - error: resolvedGlobalPalette.error['80'], - outline: resolvedGlobalPalette.neutralVariant['60'], - onBackground: resolvedGlobalPalette.neutral['90'], - background: resolvedGlobalPalette.neutral['10'], - inverseOnSurface: resolvedGlobalPalette.neutral['20'], - inverseSurface: resolvedGlobalPalette.neutral['90'], - onSurfaceVariant: resolvedGlobalPalette.neutralVariant['80'], - onSurface: resolvedGlobalPalette.neutral['90'], - surfaceVariant: resolvedGlobalPalette.neutralVariant['30'], - surface: resolvedGlobalPalette.neutral['10'], - onSecondaryContainer: resolvedGlobalPalette.secondary['90'], - onSecondary: resolvedGlobalPalette.secondary['20'], - secondaryContainer: resolvedGlobalPalette.secondary['30'], - secondary: resolvedGlobalPalette.secondary['80'], - inversePrimary: resolvedGlobalPalette.primary['40'], - onPrimaryContainer: resolvedGlobalPalette.primary['90'], - onPrimary: resolvedGlobalPalette.primary['20'], - primaryContainer: resolvedGlobalPalette.primary['30'], - primary: resolvedGlobalPalette.primary['80'], - }), - ...resolvedGlobalPalette?.colors, - }, - }; -}; - -export default createMd3Palette; diff --git a/packages/mui-material-next/src/styles/extendTheme.ts b/packages/mui-material-next/src/styles/extendTheme.ts index bac8d35a4adc2f..f35345d054cb94 100644 --- a/packages/mui-material-next/src/styles/extendTheme.ts +++ b/packages/mui-material-next/src/styles/extendTheme.ts @@ -45,38 +45,34 @@ function setColor(obj: any, key: string, defaultValue: any) { export const createGetCssVar = (cssVarPrefix = 'mui') => systemCreateGetCssVar(cssVarPrefix); -export default function extendTheme( - options: CssVarsThemeOptions = {}, - ...args: any[] -) { - const { - colorSchemes: colorSchemesInput = {}, - cssVarPrefix = 'mui', - ...input - } = options; +export default function extendTheme(options: CssVarsThemeOptions = {}, ...args: any[]) { + const { colorSchemes: colorSchemesInput = {}, cssVarPrefix = 'mui', ...input } = options; const getCssVar = createGetCssVar(cssVarPrefix); const md3LightColors = createMd3LightColorScheme(getCssVar, md3CommonPalette); const md3DarkColors = createMd3DarkColorScheme(getCssVar, md3CommonPalette); // @ts-ignore - it's fine, everything that is not supported will be spread - const { palette: lightPalette, sys: lightSys, ref: lightRef, ...muiTheme } = createThemeWithoutVars({ + const { + palette: lightPalette, + sys: lightSys, + ref: lightRef, + ...muiTheme + } = createThemeWithoutVars({ ...input, // Material You specific tokens + // @ts-ignore - it's fine, everything that is not supported will be spread useMaterialYou: true, ref: { ...input.ref, typeface: { ...md3Typeface, ...input.ref?.typeface }, - palette: { - ...md3CommonPalette, - ...colorSchemesInput.light?.ref?.palette, - } + palette: deepmerge(md3CommonPalette, colorSchemesInput.light?.ref?.palette), }, sys: { ...input.sys, typescale: { ...md3Typescale, ...input.sys?.typescale }, state: { ...md3State, ...input.sys?.state }, - color: { ...md3LightColors, ...colorSchemesInput.light?.sys?.color } + color: { ...md3LightColors, ...colorSchemesInput.light?.sys?.color }, }, md3: { shape: { @@ -88,25 +84,27 @@ export default function extendTheme( ...(colorSchemesInput.light && colorSchemesInput.light?.palette), }, }); - const { palette: darkPalette, sys: darkSys, ref: darkRef } = createThemeWithoutVars({ + // @ts-ignore sys & ref are md3 specific tokens + const { + palette: darkPalette, + sys: darkSys, + ref: darkRef, + } = createThemeWithoutVars({ palette: { mode: 'dark', ...colorSchemesInput.dark?.palette, }, + // @ts-ignore - it's fine, everything that is not supported will be spread ref: { ...input.ref, typeface: { ...md3Typeface, ...input.ref?.typeface }, - palette: { - ...md3CommonPalette, - ...colorSchemesInput.dark?.ref?.palette, - } + palette: deepmerge(md3CommonPalette, colorSchemesInput.dark?.ref?.palette), }, - sys: { ...input.sys, typescale: { ...md3Typescale, ...input.sys?.typescale }, state: { ...md3State, ...input.sys?.state }, - color: { ...md3DarkColors, ...colorSchemesInput.dark?.sys?.color } + color: { ...md3DarkColors, ...colorSchemesInput.dark?.sys?.color }, }, }); @@ -129,7 +127,7 @@ export default function extendTheme( }, overlays: colorSchemesInput.light?.overlays || defaultLightOverlays, sys: lightSys, - ref: lightRef + ref: lightRef, }, dark: { ...colorSchemesInput.dark, @@ -144,7 +142,7 @@ export default function extendTheme( }, overlays: colorSchemesInput.dark?.overlays || defaultDarkOverlays, sys: darkSys, - ref: darkRef + ref: darkRef, }, }, }; @@ -155,7 +153,9 @@ export default function extendTheme( md3: MD3Palettes & { colors: MD3ColorSchemeTokens }; }; + // @ts-ignore sys is md3 specific token const colorSchemeSys = theme.colorSchemes[key as SupportedColorScheme].sys; + // @ts-ignore ref is md3 specific token const colorSchemeRef = theme.colorSchemes[key as SupportedColorScheme].ref; // attach black & white channels to common node @@ -382,13 +382,17 @@ export default function extendTheme( colorSchemeSys.color.primaryChannel = colorChannel(colorSchemeRef.palette.primary['40']); colorSchemeSys.color.secondaryChannel = colorChannel(colorSchemeRef.palette.secondary['40']); colorSchemeSys.color.tertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['40']); - colorSchemeSys.color.secondaryContainerChannel = colorChannel(colorSchemeRef.palette.secondary['90']); + colorSchemeSys.color.secondaryContainerChannel = colorChannel( + colorSchemeRef.palette.secondary['90'], + ); colorSchemeSys.color.onSurfaceChannel = colorChannel(colorSchemeRef.palette.neutral['10']); } else { colorSchemeSys.color.primaryChannel = colorChannel(colorSchemeRef.palette.primary['80']); colorSchemeSys.color.secondaryChannel = colorChannel(colorSchemeRef.palette.secondary['80']); colorSchemeSys.color.tertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['80']); - colorSchemeSys.color.secondaryContainerChannel = colorChannel(colorSchemeRef.palette.secondary['30']); + colorSchemeSys.color.secondaryContainerChannel = colorChannel( + colorSchemeRef.palette.secondary['30'], + ); colorSchemeSys.color.onSurfaceChannel = colorChannel(colorSchemeRef.palette.neutral['90']); } }); From 03b455cc8e64777acd18b20a6426d231b5cac145 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 28 Oct 2022 09:19:30 +0200 Subject: [PATCH 24/49] More ts fixes --- packages/mui-material-next/src/styles/extendTheme.ts | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/packages/mui-material-next/src/styles/extendTheme.ts b/packages/mui-material-next/src/styles/extendTheme.ts index f35345d054cb94..99bc55eaf5bd56 100644 --- a/packages/mui-material-next/src/styles/extendTheme.ts +++ b/packages/mui-material-next/src/styles/extendTheme.ts @@ -52,10 +52,11 @@ export default function extendTheme(options: CssVarsThemeOptions = {}, ...args: const md3LightColors = createMd3LightColorScheme(getCssVar, md3CommonPalette); const md3DarkColors = createMd3DarkColorScheme(getCssVar, md3CommonPalette); - // @ts-ignore - it's fine, everything that is not supported will be spread const { palette: lightPalette, + // @ts-ignore - sys is md3 specific token sys: lightSys, + // @ts-ignore - ref is md3 specific token ref: lightRef, ...muiTheme } = createThemeWithoutVars({ @@ -84,10 +85,12 @@ export default function extendTheme(options: CssVarsThemeOptions = {}, ...args: ...(colorSchemesInput.light && colorSchemesInput.light?.palette), }, }); - // @ts-ignore sys & ref are md3 specific tokens + const { palette: darkPalette, + // @ts-ignore sys is md3 specific tokens sys: darkSys, + // @ts-ignore ref is md3 specific tokens ref: darkRef, } = createThemeWithoutVars({ palette: { From 346fe6948141f6657d5b8c9948d0471057f817e0 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 28 Oct 2022 11:05:41 +0200 Subject: [PATCH 25/49] Default theme fixes --- .../src/styles/defaultTheme.ts | 35 +++++++++++++++++-- .../src/styles/extendTheme.ts | 16 ++++++--- .../src/cssVars/createCssVarsProvider.js | 15 +++++++- 3 files changed, 59 insertions(+), 7 deletions(-) diff --git a/packages/mui-material-next/src/styles/defaultTheme.ts b/packages/mui-material-next/src/styles/defaultTheme.ts index be1a4fe44e88ba..394ec08f05c481 100644 --- a/packages/mui-material-next/src/styles/defaultTheme.ts +++ b/packages/mui-material-next/src/styles/defaultTheme.ts @@ -11,6 +11,8 @@ export const getThemeWithVars = ( overlays, shape, md3, + ref, + sys, palette: paletteInput, ...restTheme } = extendTheme(themeInput); @@ -18,17 +20,38 @@ export const getThemeWithVars = ( colorSchemes[paletteInput?.colorScheme || 'light'].palette, paletteInput, ); - const { mode = 'light', colorScheme = 'light', ...palette } = colorSchemePalette; + + const { + mode = 'light', + colorScheme = 'light', + // @ts-ignore md3 specific token + ref: colorSchemeRef, + // @ts-ignore md3 specific token + sys: colorSchemeSys, + ...palette + } = colorSchemePalette; return { opacity, overlays, shape, md3, + ref: { + ...ref, + ...colorSchemeRef, + }, + sys: { + ...sys, + ...colorSchemeSys, + }, ...restTheme, colorSchemes: { ...colorSchemes, - [colorScheme]: palette, + [colorScheme]: { + palette, + ref: colorSchemeRef, + sys: colorSchemeSys, + }, }, palette: { ...palette, @@ -39,6 +62,14 @@ export const getThemeWithVars = ( opacity, overlays, shape, + ref: { + ...ref, + ...colorSchemeRef, + }, + sys: { + ...sys, + ...colorSchemeSys, + }, md3, palette, }, diff --git a/packages/mui-material-next/src/styles/extendTheme.ts b/packages/mui-material-next/src/styles/extendTheme.ts index 99bc55eaf5bd56..427d2200de4c30 100644 --- a/packages/mui-material-next/src/styles/extendTheme.ts +++ b/packages/mui-material-next/src/styles/extendTheme.ts @@ -111,10 +111,18 @@ export default function extendTheme(options: CssVarsThemeOptions = {}, ...args: }, }); + const { color: lightSysColor } = lightSys; + const { palette: lightRefPalette } = lightRef; + + const { color: darkSysColor } = darkSys; + const { palette: darkRefPalette } = darkRef; + let theme: Theme = { ...muiTheme, cssVarPrefix, getCssVar, + sys: lightSys, + ref: lightRef, colorSchemes: { ...colorSchemesInput, light: { @@ -129,8 +137,8 @@ export default function extendTheme(options: CssVarsThemeOptions = {}, ...args: ...colorSchemesInput.light?.opacity, }, overlays: colorSchemesInput.light?.overlays || defaultLightOverlays, - sys: lightSys, - ref: lightRef, + sys: { color: lightSysColor }, + ref: { palette: lightRefPalette }, }, dark: { ...colorSchemesInput.dark, @@ -144,8 +152,8 @@ export default function extendTheme(options: CssVarsThemeOptions = {}, ...args: ...colorSchemesInput.dark?.opacity, }, overlays: colorSchemesInput.dark?.overlays || defaultDarkOverlays, - sys: darkSys, - ref: darkRef, + sys: { color: darkSysColor }, + ref: { palette: darkRefPalette }, }, }, }; diff --git a/packages/mui-system/src/cssVars/createCssVarsProvider.js b/packages/mui-system/src/cssVars/createCssVarsProvider.js index b3e2c847215eb2..0b4faa8b6f3239 100644 --- a/packages/mui-system/src/cssVars/createCssVarsProvider.js +++ b/packages/mui-system/src/cssVars/createCssVarsProvider.js @@ -137,15 +137,28 @@ export default function createCssVarsProvider(options) { }); theme.vars = deepmerge(theme.vars, vars); if (key === resolvedColorScheme) { + const { ref, sys, ...restParsedScheme } = parsedScheme; theme = { ...theme, - ...parsedScheme, + ...restParsedScheme, }; if (theme.palette) { // assign runtime mode & colorScheme theme.palette.mode = mode; theme.palette.colorScheme = resolvedColorScheme; } + if (theme.sys) { + theme.sys = { + ...theme.sys, + color: sys.color, + }; + } + if (theme.ref) { + theme.ref = { + ...theme.ref, + palette: ref.palette, + }; + } } const resolvedDefaultColorScheme = (() => { if (typeof defaultColorScheme === 'string') { From da2361d6de1eb3008954cf33732d6b163817dbb4 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 28 Oct 2022 12:02:52 +0200 Subject: [PATCH 26/49] Add basic styleFunctionSx --- .../src/styles/styleFunctionSx.ts | 102 ++++++++++++++++++ .../mui-material-next/src/styles/styled.ts | 5 +- packages/mui-system/src/spacing.d.ts | 14 +++ 3 files changed, 118 insertions(+), 3 deletions(-) create mode 100644 packages/mui-material-next/src/styles/styleFunctionSx.ts diff --git a/packages/mui-material-next/src/styles/styleFunctionSx.ts b/packages/mui-material-next/src/styles/styleFunctionSx.ts new file mode 100644 index 00000000000000..03723049072b57 --- /dev/null +++ b/packages/mui-material-next/src/styles/styleFunctionSx.ts @@ -0,0 +1,102 @@ +import { + Interpolation, + unstable_createStyleFunctionSx, + compose, + style, + display, + flexbox, + grid, + positions, + sizing, + spacing, + border, + borderTop, + borderRight, + borderBottom, + borderLeft, + borderColor, + borderTopColor, + borderRightColor, + borderBottomColor, + borderLeftColor, + getValue, + createUnaryUnit, + handleBreakpoints, + typography, +} from '@mui/system'; +import responsivePropType from '@mui/system/responsivePropType'; +import { SxProps, Theme } from './Theme.types'; + +// Palette values should reference the color tokens +export const color = style({ + prop: 'color', + themeKey: 'sys.color', +}); + +export const bgcolor = style({ + prop: 'bgcolor', + cssProperty: 'backgroundColor', + themeKey: 'sys.color', +}); + +export const backgroundColor = style({ + prop: 'backgroundColor', + themeKey: 'sys.color', +}); + +const palette = compose(color, bgcolor, backgroundColor); + +// Border radius should mapa to md3.shape +export const borderRadius = (props: any) => { + if (props.borderRadius !== undefined && props.borderRadius !== null) { + const transformer = createUnaryUnit(props.theme, 'md3.shape.borderRadius', 4, 'borderRadius'); + const styleFromPropValue = (propValue: any) => ({ + // @ts-ignore + borderRadius: getValue(transformer, propValue), + }); + return handleBreakpoints(props, props.borderRadius, styleFromPropValue); + } + + return null; +}; + +borderRadius.propTypes = + process.env.NODE_ENV !== 'production' ? { borderRadius: responsivePropType } : {}; + +borderRadius.filterProps = ['borderRadius']; +const borders = compose( + border, + borderTop, + borderRight, + borderBottom, + borderLeft, + borderColor, + borderTopColor, + borderRightColor, + borderBottomColor, + borderLeftColor, + borderRadius, +); + +const styleFunctionMapping = { + borders, + display, + flexbox, + grid, + positions, + palette, + sizing, + spacing, + typography, +}; + +const styleFunctionSx = unstable_createStyleFunctionSx(styleFunctionMapping); + +styleFunctionSx.filterProps = ['sx']; + +export const sx = (styles: SxProps) => { + return ({ theme }: { theme: Theme }) => + styleFunctionSx({ sx: styles, theme }) as Interpolation<{ theme: Theme }>; +}; + +export default styleFunctionSx; diff --git a/packages/mui-material-next/src/styles/styled.ts b/packages/mui-material-next/src/styles/styled.ts index ffb0f1ddf7cf3d..2e8f6c5a463872 100644 --- a/packages/mui-material-next/src/styles/styled.ts +++ b/packages/mui-material-next/src/styles/styled.ts @@ -1,9 +1,8 @@ import { createStyled } from '@mui/system'; import { Theme } from './Theme.types'; import defaultTheme from './defaultTheme'; -// TODO: custom styleFunctionSx will be required -// import styleFunctionSx from './styleFunctionSx'; +import styleFunctionSx from './styleFunctionSx'; -const styled = createStyled({ defaultTheme /* styleFunctionSx */ }); +const styled = createStyled({ defaultTheme, styleFunctionSx }); export default styled; diff --git a/packages/mui-system/src/spacing.d.ts b/packages/mui-system/src/spacing.d.ts index 9157d8c676d615..d5587dc06beeb9 100644 --- a/packages/mui-system/src/spacing.d.ts +++ b/packages/mui-system/src/spacing.d.ts @@ -10,6 +10,20 @@ export function createUnarySpacing(theme: { spacing: Spacing }): Spacin : // warns in Dev () => undefined; +export function createUnaryUnit( + theme: { spacing: Spacing }, + themeKey: string, + defaultValue: Spacing, + propName: string, +): Spacing extends number + ? (abs: number | string) => number | number + : Spacing extends any[] + ? (abs: Index | string) => Spacing[Index] | string + : Spacing extends (...args: unknown[]) => unknown + ? Spacing + : // warns in Dev + () => undefined; + export const margin: SimpleStyleFunction< | 'm' | 'mt' From 18cddd16f6916caaf8762c3c2881278bbef0417a Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 28 Oct 2022 13:09:34 +0200 Subject: [PATCH 27/49] Fixes after rebase --- docs/pages/experiments/md3/index.tsx | 8 ++++++-- packages/mui-material-next/src/styles/styleFunctionSx.ts | 2 +- packages/mui-system/src/index.d.ts | 2 ++ packages/mui-system/src/index.js | 1 + packages/mui-system/src/responsivePropType.d.ts | 3 +++ 5 files changed, 13 insertions(+), 3 deletions(-) create mode 100644 packages/mui-system/src/responsivePropType.d.ts diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index 27492327259423..d448225202a613 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -10,6 +10,7 @@ import Button, { ButtonProps } from '@mui/material-next/Button'; import { CssVarsProvider, useColorScheme, extendTheme } from '@mui/material-next/styles'; import DarkIcon from '@mui/icons-material/DarkModeOutlined'; import LightIcon from '@mui/icons-material/LightModeOutlined'; +import CssBaseline from '@mui/material/CssBaseline'; const ModeSwitcher = () => { const { mode, setMode } = useColorScheme(); @@ -269,8 +270,11 @@ export default function App() { return ( - - + + + + + ); diff --git a/packages/mui-material-next/src/styles/styleFunctionSx.ts b/packages/mui-material-next/src/styles/styleFunctionSx.ts index 03723049072b57..b6172bc6407b92 100644 --- a/packages/mui-material-next/src/styles/styleFunctionSx.ts +++ b/packages/mui-material-next/src/styles/styleFunctionSx.ts @@ -22,9 +22,9 @@ import { getValue, createUnaryUnit, handleBreakpoints, + responsivePropType, typography, } from '@mui/system'; -import responsivePropType from '@mui/system/responsivePropType'; import { SxProps, Theme } from './Theme.types'; // Palette values should reference the color tokens diff --git a/packages/mui-system/src/index.d.ts b/packages/mui-system/src/index.d.ts index c2dc1bdda444e8..a89703928d4a5a 100644 --- a/packages/mui-system/src/index.d.ts +++ b/packages/mui-system/src/index.d.ts @@ -165,6 +165,8 @@ export { default as unstable_createCssVarsProvider, CreateCssVarsProviderResult export { default as unstable_createGetCssVar } from './cssVars/createGetCssVar'; export * from './cssVars'; +export { default as responsivePropType } from './responsivePropType'; + export { default as createContainer } from './Container/createContainer'; export * from './Container/createContainer'; diff --git a/packages/mui-system/src/index.js b/packages/mui-system/src/index.js index b6a85cbacdce68..1a964260749787 100644 --- a/packages/mui-system/src/index.js +++ b/packages/mui-system/src/index.js @@ -48,6 +48,7 @@ export * from './colorManipulator'; export { default as ThemeProvider } from './ThemeProvider'; export { default as unstable_createCssVarsProvider } from './cssVars/createCssVarsProvider'; export { default as unstable_createGetCssVar } from './cssVars/createGetCssVar'; +export { default as responsivePropType } from './responsivePropType'; /** ----------------- */ /** Layout components */ diff --git a/packages/mui-system/src/responsivePropType.d.ts b/packages/mui-system/src/responsivePropType.d.ts new file mode 100644 index 00000000000000..e6d62effc86140 --- /dev/null +++ b/packages/mui-system/src/responsivePropType.d.ts @@ -0,0 +1,3 @@ +declare const responsivePropType: object; + +export default responsivePropType; From d41626259af98a2e6fa29535644ccb7379c437b7 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Mon, 31 Oct 2022 10:29:44 +0100 Subject: [PATCH 28/49] [release] v5.10.12 --- CHANGELOG.md | 67 +++++++++++++++++++ benchmark/package.json | 4 +- docs/package.json | 12 ++-- package.json | 2 +- packages/mui-base/package.json | 2 +- packages/mui-codemod/package.json | 2 +- .../mui-core-downloads-tracker/package.json | 2 +- packages/mui-envinfo/package.json | 2 +- packages/mui-joy/package.json | 8 +-- packages/mui-lab/package.json | 6 +- packages/mui-material-next/package.json | 8 +-- packages/mui-material/package.json | 8 +-- packages/mui-system/package.json | 2 +- 13 files changed, 96 insertions(+), 29 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c2605377ae28c3..f1501ae63c55da 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,72 @@ # [Versions](https://mui.com/versions/) +## v5.10.12 + + + +_Oct 31, 2022_ + +A big thanks to the 16 contributors who made this release possible. This release is mostly about πŸ› bug fixes, πŸ“š documentation, and βš™οΈ infrastructure improvements. + +TODO INSERT HIGHLIGHTS + +### `@mui/material@5.10.12` + +- ​[Chip] Don't override icon color (#34247) @emlai +- ​[Radio] Skip default hover style when disableRipple is set (#34902) @VinceCYLiao +- ​[SwipeableDrawer] Fix React 18 issues (#34505) @mnajdova +- ​[Tooltip] Save a few bytes (#34853) @oliviertassinari + +### `@mui/base@5.0.0-alpha.104` + +- ​[ButtonUnstyled] Update to render as link when href or to is provided (#34337) @EduardoSCosta + +### `@mui/joy@5.0.0-alpha.52` + +- ​[Joy][circularprogress] Prevent new styles from being generated when `value` changes (#34897) @hbjORbj +- ​[Joy] Add color inversion feature (#32511) @siriwatknp +- ​[Joy] Add `LinearProgress` component (#34514) @hbjORbj + +### Docs + +- ​[blog] Add blog post for high-level overview of all MUI products (#34325) @samuelsycamore +- ​[blog] Fix hydration mistmatch (#34857) @oliviertassinari +- ​[docs] Revise the Joy UI "Aspect Ratio" page (#34858) @samuelsycamore +- ​[docs] Fix Safari code font size (#34859) @oliviertassinari +- ​[docs] Fix spelling mistake (#34955) @punithnayak +- ​[docs] Fix 404 link of supported Material UI components @oliviertassinari +- ​[docs] Fix Safari button misalignment (#34861) @oliviertassinari +- ​[docs] Fix typo in docs title (#34926) @PunitSoniME +- ​[docs] Standardize all MUI Core "Usage" pages (#34183) @samuelsycamore +- ​[docs] Update templates' readme files to include required dependencies (#34757) @michaldudak +- ​[docs] Fix inconsistent theme colors when applying custom colors in playground (#34866) @cherniavskii +- ​[docs] Fix typo in bottom-navigation.md (#34884) @RoodyCode +- ​[website] Update MUI X open and future roles + about page (#34894) @DanailH +- ​[website] Remove one DOM node (#34960) @oliviertassinari +- ​[website] Use `span` for icon image (#34914) @siriwatknp +- ​[website] Fix subscribe input with Safari (#34869) @oliviertassinari + +### Core + +- ​[core] Ignore compiled icons in CodeQL @oliviertassinari +- ​[core] Add OSSF Scorecard action (#34854) @oliviertassinari +- ​[core] Fix duplicate id @oliviertassinari +- ​[core] A couple of simply fixes from #34870 (#34953) @oliviertassinari +- ​[core] Migrate outdated pattern to convention @oliviertassinari +- ​[core] Pin GitHub Actions dependencies (#34929) @renovate[bot] +- ​[core] Make the reproduction more important in the bug template (#34875) @oliviertassinari +- ​[core] Fix docs GitHub API rate limit (#34856) @oliviertassinari +- ​[core] Pin GitHub Action to digests (#34855) @oliviertassinari +- ​[core] Fix permissions in workflow @oliviertassinari +- ​[core] memoize context values for react/jsx-no-constructed-context-values (#34849) @Janpot +- ​[core] Fix @typescript-eslint/default-param-last issues (#34846) @Janpot +- ​[core] Fix HTML validation error (#34860) @oliviertassinari +- ​[core] Fix duplicate CodeQL build @oliviertassinari +- ​[test] Move Firefox tests to CircleCI (#34764) @oliviertassinari +- ​[test] Use screen when possible for simplicity (#34890) @oliviertassinari + +All contributors of this release in alphabetical order: @cherniavskii, @DanailH, @EduardoSCosta, @emlai, @hbjORbj, @Janpot, @michaldudak, @mnajdova, @oliviertassinari, @punithnayak, @PunitSoniME, @renovate[bot], @RoodyCode, @samuelsycamore, @siriwatknp, @VinceCYLiao + ## v5.10.11 diff --git a/benchmark/package.json b/benchmark/package.json index 16a6a753d81405..cb871a175cbb35 100644 --- a/benchmark/package.json +++ b/benchmark/package.json @@ -15,9 +15,9 @@ "@emotion/react": "^11.10.4", "@emotion/styled": "^11.10.4", "@mdx-js/react": "^2.1.5", - "@mui/material": "^5.10.11", + "@mui/material": "^5.10.12", "@mui/styles": "^5.10.10", - "@mui/system": "^5.10.10", + "@mui/system": "^5.10.12", "@styled-system/css": "^5.1.5", "benchmark": "^2.1.4", "playwright": "^1.27.1", diff --git a/docs/package.json b/docs/package.json index e79409043edadb..9417a49c6dafe5 100644 --- a/docs/package.json +++ b/docs/package.json @@ -33,17 +33,17 @@ "@fortawesome/fontawesome-svg-core": "^6.2.0", "@fortawesome/free-solid-svg-icons": "^6.2.0", "@fortawesome/react-fontawesome": "^0.2.0", - "@mui/base": "5.0.0-alpha.103", + "@mui/base": "5.0.0-alpha.104", "@mui/docs": "^5.10.9", "@mui/icons-material": "^5.10.9", - "@mui/joy": "5.0.0-alpha.51", - "@mui/lab": "5.0.0-alpha.105", - "@mui/material": "^5.10.11", - "@mui/material-next": "6.0.0-alpha.59", + "@mui/joy": "5.0.0-alpha.52", + "@mui/lab": "5.0.0-alpha.106", + "@mui/material": "^5.10.12", + "@mui/material-next": "6.0.0-alpha.60", "@mui/styled-engine": "^5.10.8", "@mui/styled-engine-sc": "^5.10.6", "@mui/styles": "^5.10.10", - "@mui/system": "^5.10.10", + "@mui/system": "^5.10.12", "@mui/types": "^7.2.0", "@mui/x-data-grid": "^5.17.9", "@mui/x-data-grid-generator": "^5.17.9", diff --git a/package.json b/package.json index e8b07d28bf62ee..abc4369f867686 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@mui/monorepo", - "version": "5.10.11", + "version": "5.10.12", "private": true, "scripts": { "proptypes": "cross-env BABEL_ENV=development babel-node --extensions \".tsx,.ts,.js\" ./scripts/generateProptypes.ts", diff --git a/packages/mui-base/package.json b/packages/mui-base/package.json index 5149d325e9f009..de986027c279a8 100644 --- a/packages/mui-base/package.json +++ b/packages/mui-base/package.json @@ -1,6 +1,6 @@ { "name": "@mui/base", - "version": "5.0.0-alpha.103", + "version": "5.0.0-alpha.104", "private": false, "author": "MUI Team", "description": "A library of headless ('unstyled') React UI components and low-level hooks.", diff --git a/packages/mui-codemod/package.json b/packages/mui-codemod/package.json index f041e0f37d8fe4..9557d6c39c5d1e 100644 --- a/packages/mui-codemod/package.json +++ b/packages/mui-codemod/package.json @@ -1,6 +1,6 @@ { "name": "@mui/codemod", - "version": "5.10.11", + "version": "5.10.12", "bin": "./codemod.js", "private": false, "author": "MUI Team", diff --git a/packages/mui-core-downloads-tracker/package.json b/packages/mui-core-downloads-tracker/package.json index ef5a94d631c30f..ec95d0dba27dcf 100644 --- a/packages/mui-core-downloads-tracker/package.json +++ b/packages/mui-core-downloads-tracker/package.json @@ -1,6 +1,6 @@ { "name": "@mui/core-downloads-tracker", - "version": "5.10.11", + "version": "5.10.12", "private": false, "author": "MUI Team", "description": "Internal package to track number of downloads of our design system libraries", diff --git a/packages/mui-envinfo/package.json b/packages/mui-envinfo/package.json index 8b63b5f4ca100c..07e1e1da1f1bf6 100644 --- a/packages/mui-envinfo/package.json +++ b/packages/mui-envinfo/package.json @@ -6,7 +6,7 @@ }, "license": "MIT", "description": "Logs infos about the environment relevant to @mui/*", - "version": "2.0.6", + "version": "2.0.7", "bin": "./envinfo.js", "dependencies": { "envinfo": "^7.8.1" diff --git a/packages/mui-joy/package.json b/packages/mui-joy/package.json index d13f1b21f0a6bb..8daecbb49b223d 100644 --- a/packages/mui-joy/package.json +++ b/packages/mui-joy/package.json @@ -1,6 +1,6 @@ { "name": "@mui/joy", - "version": "5.0.0-alpha.51", + "version": "5.0.0-alpha.52", "private": false, "author": "MUI Team", "description": "A library of beautifully designed React UI components.", @@ -57,9 +57,9 @@ }, "dependencies": { "@babel/runtime": "^7.19.0", - "@mui/base": "5.0.0-alpha.103", - "@mui/core-downloads-tracker": "^5.10.11", - "@mui/system": "^5.10.10", + "@mui/base": "5.0.0-alpha.104", + "@mui/core-downloads-tracker": "^5.10.12", + "@mui/system": "^5.10.12", "@mui/types": "^7.2.0", "@mui/utils": "^5.10.9", "clsx": "^1.2.1", diff --git a/packages/mui-lab/package.json b/packages/mui-lab/package.json index f9c16b33db5a6c..4ae9bb53dba5bb 100644 --- a/packages/mui-lab/package.json +++ b/packages/mui-lab/package.json @@ -1,6 +1,6 @@ { "name": "@mui/lab", - "version": "5.0.0-alpha.105", + "version": "5.0.0-alpha.106", "private": false, "author": "MUI Team", "description": "Laboratory for new MUI modules.", @@ -61,8 +61,8 @@ }, "dependencies": { "@babel/runtime": "^7.19.0", - "@mui/base": "5.0.0-alpha.103", - "@mui/system": "^5.10.10", + "@mui/base": "5.0.0-alpha.104", + "@mui/system": "^5.10.12", "@mui/types": "^7.2.0", "@mui/utils": "^5.10.9", "clsx": "^1.2.1", diff --git a/packages/mui-material-next/package.json b/packages/mui-material-next/package.json index f85453fdfb71b5..87a63bfd4b4c67 100644 --- a/packages/mui-material-next/package.json +++ b/packages/mui-material-next/package.json @@ -1,6 +1,6 @@ { "name": "@mui/material-next", - "version": "6.0.0-alpha.59", + "version": "6.0.0-alpha.60", "private": false, "author": "MUI Team", "description": "v6-alpha: React components that implement Google's Material Design", @@ -59,9 +59,9 @@ }, "dependencies": { "@babel/runtime": "^7.19.0", - "@mui/base": "5.0.0-alpha.103", - "@mui/material": "^5.10.11", - "@mui/system": "^5.10.10", + "@mui/base": "5.0.0-alpha.104", + "@mui/material": "^5.10.12", + "@mui/system": "^5.10.12", "@mui/types": "^7.2.0", "@mui/utils": "^5.10.9", "@popperjs/core": "^2.11.6", diff --git a/packages/mui-material/package.json b/packages/mui-material/package.json index 22f47e264a2a37..5bbfa8bf3141bc 100644 --- a/packages/mui-material/package.json +++ b/packages/mui-material/package.json @@ -1,6 +1,6 @@ { "name": "@mui/material", - "version": "5.10.11", + "version": "5.10.12", "private": false, "author": "MUI Team", "description": "React components that implement Google's Material Design.", @@ -61,9 +61,9 @@ }, "dependencies": { "@babel/runtime": "^7.19.0", - "@mui/base": "5.0.0-alpha.103", - "@mui/core-downloads-tracker": "^5.10.11", - "@mui/system": "^5.10.10", + "@mui/base": "5.0.0-alpha.104", + "@mui/core-downloads-tracker": "^5.10.12", + "@mui/system": "^5.10.12", "@mui/types": "^7.2.0", "@mui/utils": "^5.10.9", "@types/react-transition-group": "^4.4.5", diff --git a/packages/mui-system/package.json b/packages/mui-system/package.json index bba16d3506151e..46b424ace29ac3 100644 --- a/packages/mui-system/package.json +++ b/packages/mui-system/package.json @@ -1,6 +1,6 @@ { "name": "@mui/system", - "version": "5.10.10", + "version": "5.10.12", "private": false, "author": "MUI Team", "description": "CSS utilities for rapidly laying out custom designs.", From a4ac85fb1ebc4a3e7c4310a834de221db2785b63 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Mon, 31 Oct 2022 14:35:10 +0100 Subject: [PATCH 29/49] Remove autogenerated text --- CHANGELOG.md | 2 -- 1 file changed, 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f1501ae63c55da..9f580ac75d58df 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,8 +8,6 @@ _Oct 31, 2022_ A big thanks to the 16 contributors who made this release possible. This release is mostly about πŸ› bug fixes, πŸ“š documentation, and βš™οΈ infrastructure improvements. -TODO INSERT HIGHLIGHTS - ### `@mui/material@5.10.12` - ​[Chip] Don't override icon color (#34247) @emlai From 7e1815a63f02e9f6863b075ca5bf915a8d639470 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Mon, 31 Oct 2022 14:42:09 +0100 Subject: [PATCH 30/49] Updated changelog --- CHANGELOG.md | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9f580ac75d58df..82b7c8d0f3feef 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -35,10 +35,15 @@ A big thanks to the 16 contributors who made this release possible. This release - ​[docs] Fix 404 link of supported Material UI components @oliviertassinari - ​[docs] Fix Safari button misalignment (#34861) @oliviertassinari - ​[docs] Fix typo in docs title (#34926) @PunitSoniME +- ​[docs] Fix missing emotion prefixes (#34958) @oliviertassinari +- ​[docs] Improve UI display for copy code (#34950) @oliviertassinari - ​[docs] Standardize all MUI Core "Usage" pages (#34183) @samuelsycamore - ​[docs] Update templates' readme files to include required dependencies (#34757) @michaldudak - ​[docs] Fix inconsistent theme colors when applying custom colors in playground (#34866) @cherniavskii - ​[docs] Fix typo in bottom-navigation.md (#34884) @RoodyCode +- ​[website] Migrate about-us page to use CSS theme variables (#34919) @brianlu2610 +- ​[website] Migrate Product-Templates page to use CSS theme variables (#34913) @EduardoSCosta +- ​[website] Migrate career page to use CSS theme variables (#34908) @the-mgi - ​[website] Update MUI X open and future roles + about page (#34894) @DanailH - ​[website] Remove one DOM node (#34960) @oliviertassinari - ​[website] Use `span` for icon image (#34914) @siriwatknp @@ -48,7 +53,9 @@ A big thanks to the 16 contributors who made this release possible. This release - ​[core] Ignore compiled icons in CodeQL @oliviertassinari - ​[core] Add OSSF Scorecard action (#34854) @oliviertassinari +- ​[core] Fix extra GitHub Action permission (#34496) @sashashura - ​[core] Fix duplicate id @oliviertassinari +- ​[core] Enforce import \* as React (#34878) @da0x - ​[core] A couple of simply fixes from #34870 (#34953) @oliviertassinari - ​[core] Migrate outdated pattern to convention @oliviertassinari - ​[core] Pin GitHub Actions dependencies (#34929) @renovate[bot] From 1e556dc0379993afaa8f82879e5ab147615cebcd Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Mon, 31 Oct 2022 16:18:20 +0100 Subject: [PATCH 31/49] Updated changelog --- CHANGELOG.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 82b7c8d0f3feef..24270e3f8f00ae 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,7 +6,10 @@ _Oct 31, 2022_ -A big thanks to the 16 contributors who made this release possible. This release is mostly about πŸ› bug fixes, πŸ“š documentation, and βš™οΈ infrastructure improvements. +A big thanks to the 16 contributors who made this release possible. Here are some highlights ✨: + +- πŸš€ The LinearProgress component has been added to Joy UI by @hbjORbj (#34514). +- Many other πŸ› bug fixes, πŸ“š documentation, and βš™οΈ infrastructure improvements. ### `@mui/material@5.10.12` @@ -61,6 +64,7 @@ A big thanks to the 16 contributors who made this release possible. This release - ​[core] Pin GitHub Actions dependencies (#34929) @renovate[bot] - ​[core] Make the reproduction more important in the bug template (#34875) @oliviertassinari - ​[core] Fix docs GitHub API rate limit (#34856) @oliviertassinari +- ​[core] Fix eslint issues (#34964) @mnajdova - ​[core] Pin GitHub Action to digests (#34855) @oliviertassinari - ​[core] Fix permissions in workflow @oliviertassinari - ​[core] memoize context values for react/jsx-no-constructed-context-values (#34849) @Janpot From a0ea0e3ee341befb7c88c683dbda86dbeeabf353 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Tue, 1 Nov 2022 12:21:10 +0100 Subject: [PATCH 32/49] Improve classes --- .../mui-material-next/src/Button/Button.tsx | 5 +- .../src/Button/buttonClasses.ts | 79 +++++-------------- 2 files changed, 21 insertions(+), 63 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index e11c82d6fab8ae..1cd8ac4adc3a5d 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -33,9 +33,8 @@ const useUtilityClasses = (styleProps: ButtonOwnerState) => { disabled && 'disabled', focusVisible && 'focusVisible', variant, - `${variant}${capitalize(color ?? '')}`, + `color${capitalize(color ?? '')}`, `size${capitalize(size ?? '')}`, - `${variant}Size${capitalize(size ?? '')}`, disableElevation && 'disableElevation', fullWidth && 'fullWidth', ], @@ -539,7 +538,7 @@ Button.propTypes /* remove-proptypes */ = { * @default 'primary' */ color: PropTypes /* @typescript-to-proptypes-ignore */.oneOfType([ - PropTypes.oneOf(['inherit', 'primary', 'secondary', 'success', 'error', 'info', 'warning']), + PropTypes.oneOf(['primary', 'secondary', 'tertiary']), PropTypes.string, ]), /** diff --git a/packages/mui-material-next/src/Button/buttonClasses.ts b/packages/mui-material-next/src/Button/buttonClasses.ts index 72aa7d02cb9143..6c5ecf49c3b724 100644 --- a/packages/mui-material-next/src/Button/buttonClasses.ts +++ b/packages/mui-material-next/src/Button/buttonClasses.ts @@ -6,54 +6,26 @@ export interface ButtonClasses { root: string; /** Styles applied to the root element if `variant="text"`. */ text: string; - /** Styles applied to the root element if `variant="text"` and `color="inherit"`. */ - textInherit: string; - /** Styles applied to the root element if `variant="text"` and `color="primary"`. */ - textPrimary: string; - /** Styles applied to the root element if `variant="text"` and `color="secondary"`. */ - textSecondary: string; /** Styles applied to the root element if `variant="outlined"`. */ outlined: string; - /** Styles applied to the root element if `variant="outlined"` and `color="inherit"`. */ - outlinedInherit: string; - /** Styles applied to the root element if `variant="outlined"` and `color="primary"`. */ - outlinedPrimary: string; - /** Styles applied to the root element if `variant="outlined"` and `color="secondary"`. */ - outlinedSecondary: string; - /** Styles applied to the root element if `variant="contained"`. */ - contained: string; - /** Styles applied to the root element if `variant="contained"` and `color="inherit"`. */ - containedInherit: string; - /** Styles applied to the root element if `variant="contained"` and `color="primary"`. */ - containedPrimary: string; - /** Styles applied to the root element if `variant="contained"` and `color="secondary"`. */ - containedSecondary: string; + /** Styles applied to the root element if `variant="filled"`. */ + filled: string; + /** Styles applied to the root element if `variant="filledTonal"`. */ + filledTonal: string; + /** Styles applied to the root element if `variant="elevated"`. */ + elevated: string; /** Styles applied to the root element if `disableElevation={true}`. */ disableElevation: string; /** State class applied to the ButtonBase root element if the button is keyboard focused. */ focusVisible: string; /** State class applied to the root element if `disabled={true}`. */ disabled: string; - /** Styles applied to the root element if `color="inherit"`. */ - colorInherit: string; - /** Styles applied to the root element if `size="small"` and `variant="text"`. */ - textSizeSmall: string; - /** Styles applied to the root element if `size="medium"` and `variant="text"`. */ - textSizeMedium: string; - /** Styles applied to the root element if `size="large"` and `variant="text"`. */ - textSizeLarge: string; - /** Styles applied to the root element if `size="small"` and `variant="outlined"`. */ - outlinedSizeSmall: string; - /** Styles applied to the root element if `size="medium"` and `variant="outlined"`. */ - outlinedSizeMedium: string; - /** Styles applied to the root element if `size="large"` and `variant="outlined"`. */ - outlinedSizeLarge: string; - /** Styles applied to the root element if `size="small"` and `variant="contained"`. */ - containedSizeSmall: string; - /** Styles applied to the root element if `size="small"` and `variant="contained"`. */ - containedSizeMedium: string; - /** Styles applied to the root element if `size="large"` and `variant="contained"`. */ - containedSizeLarge: string; + /** Styles applied to the root element if `color="primary"`. */ + colorPrimary: string; + /** Styles applied to the root element if `color="secondary"`. */ + colorSecondary: string; + /** Styles applied to the root element if `color="tertiary"`. */ + colorTertiary: string; /** Styles applied to the root element if `size="small"`. */ sizeSmall: string; /** Styles applied to the root element if `size="medium"`. */ @@ -83,32 +55,19 @@ export function getButtonUtilityClass(slot: string): string { const buttonClasses: ButtonClasses = generateUtilityClasses('MuiButton', [ 'root', 'text', - 'textInherit', - 'textPrimary', - 'textSecondary', 'outlined', - 'outlinedInherit', - 'outlinedPrimary', - 'outlinedSecondary', - 'contained', - 'containedInherit', - 'containedPrimary', - 'containedSecondary', + 'filled', + 'filledTonal', + 'elevated', + 'colorPrimary', + 'colorSecondary', + 'colorTertiary', 'disableElevation', 'focusVisible', 'disabled', 'colorInherit', - 'textSizeSmall', - 'textSizeMedium', - 'textSizeLarge', - 'outlinedSizeSmall', - 'outlinedSizeMedium', - 'outlinedSizeLarge', - 'containedSizeSmall', - 'containedSizeMedium', - 'containedSizeLarge', - 'sizeMedium', 'sizeSmall', + 'sizeMedium', 'sizeLarge', 'fullWidth', 'startIcon', From 225f5cc566505a3af8e32ce6e5a73c8ee56c006b Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 3 Nov 2022 08:08:55 +0100 Subject: [PATCH 33/49] Update packages/mui-material-next/src/Button/Button.types.ts MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: MichaΕ‚ Dudak Signed-off-by: Marija Najdova --- packages/mui-material-next/src/Button/Button.types.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/mui-material-next/src/Button/Button.types.ts b/packages/mui-material-next/src/Button/Button.types.ts index dae09ef0fd224a..c24fe6c77d9262 100644 --- a/packages/mui-material-next/src/Button/Button.types.ts +++ b/packages/mui-material-next/src/Button/Button.types.ts @@ -126,7 +126,7 @@ export interface ButtonOwnerState extends ButtonProps { } /** - * utility to create component types that inherit props from ButtonBase. + * A utility to create component types that inherit props from the Button. * This component has an additional overload if the `href` prop is set which * can make extension quite tricky */ From 449d93a6abcd1585de2e61cb24863b958917692b Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 9 Nov 2022 10:58:27 +0100 Subject: [PATCH 34/49] address Jun's feedback --- .../src/styles/CssVarsProvider.tsx | 38 ++++++++++++ .../mui-material-next/src/styles/index.ts | 5 +- packages/mui-material/src/styles/index.d.ts | 4 ++ packages/mui-material/src/styles/index.js | 4 ++ .../src/cssVars/createCssVarsProvider.d.ts | 5 ++ .../src/cssVars/createCssVarsProvider.js | 59 +++++++++++++++---- 6 files changed, 99 insertions(+), 16 deletions(-) create mode 100644 packages/mui-material-next/src/styles/CssVarsProvider.tsx diff --git a/packages/mui-material-next/src/styles/CssVarsProvider.tsx b/packages/mui-material-next/src/styles/CssVarsProvider.tsx new file mode 100644 index 00000000000000..d426cbe478e77b --- /dev/null +++ b/packages/mui-material-next/src/styles/CssVarsProvider.tsx @@ -0,0 +1,38 @@ +import { unstable_createCssVarsProvider as createCssVarsProvider } from '@mui/system'; +import { + experimental_extendTheme, + SupportedColorScheme, + private_createTypography as createTypography, + private_excludeVariablesFromRoot as excludeVariablesFromRoot, +} from '@mui/material/styles'; + +const shouldSkipGeneratingVar = (keys: string[]) => + !!keys[0].match(/(typography|mixins|breakpoints|direction|transitions)/) || + (keys[0] === 'palette' && !!keys[1]?.match(/(mode|contrastThreshold|tonalOffset)/)); + +const defaultTheme = experimental_extendTheme(); + +const { CssVarsProvider, useColorScheme, getInitColorSchemeScript } = + createCssVarsProvider({ + theme: defaultTheme, + attribute: 'data-mui-color-scheme', + modeStorageKey: 'mui-mode', + colorSchemeStorageKey: 'mui-color-scheme', + defaultColorScheme: { + light: 'light', + dark: 'dark', + }, + resolveTheme: (theme) => { + const newTheme = { + ...theme, + typography: createTypography(theme.palette, theme.typography), + }; + + return newTheme; + }, + shouldSkipGeneratingVar, + excludeVariablesFromRoot, + additionalColorTokensPaths: ['sys.color', 'ref.palette'], + }); + +export { useColorScheme, getInitColorSchemeScript, shouldSkipGeneratingVar, CssVarsProvider }; diff --git a/packages/mui-material-next/src/styles/index.ts b/packages/mui-material-next/src/styles/index.ts index d1e3d03bf42943..dc8c6c812476a1 100644 --- a/packages/mui-material-next/src/styles/index.ts +++ b/packages/mui-material-next/src/styles/index.ts @@ -3,7 +3,4 @@ export * from './extendTheme'; export { default as extendTheme } from './extendTheme'; export { default as styled } from './styled'; export { default as defaultTheme } from './defaultTheme'; -export { - Experimental_CssVarsProvider as CssVarsProvider, - useColorScheme, -} from '@mui/material/styles'; +export * from './CssVarsProvider'; diff --git a/packages/mui-material/src/styles/index.d.ts b/packages/mui-material/src/styles/index.d.ts index b6870d47403eb0..bb2e23b2f89e26 100644 --- a/packages/mui-material/src/styles/index.d.ts +++ b/packages/mui-material/src/styles/index.d.ts @@ -131,3 +131,7 @@ export type { ColorSystemOptions, } from './experimental_extendTheme'; export { default as getOverlayAlpha } from './getOverlayAlpha'; + +// Private methods for creating parts of the theme +export { default as private_createTypography } from './createTypography'; +export { default as private_excludeVariablesFromRoot } from './excludeVariablesFromRoot'; diff --git a/packages/mui-material/src/styles/index.js b/packages/mui-material/src/styles/index.js index 8c01c3314e37f3..011245f31907b7 100644 --- a/packages/mui-material/src/styles/index.js +++ b/packages/mui-material/src/styles/index.js @@ -36,3 +36,7 @@ export { default as withTheme } from './withTheme'; export * from './CssVarsProvider'; export { default as experimental_extendTheme } from './experimental_extendTheme'; export { default as getOverlayAlpha } from './getOverlayAlpha'; + +// Private methods for creating parts of the theme +export { default as private_createTypography } from './createTypography'; +export { default as private_excludeVariablesFromRoot } from './excludeVariablesFromRoot'; diff --git a/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts b/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts index 808657beebdda9..6a024750997a56 100644 --- a/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts +++ b/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts @@ -47,6 +47,11 @@ export interface CssVarsProviderConfig { * value = 'var(--test)' */ shouldSkipGeneratingVar?: (keys: string[], value: string | number) => boolean; + /** + * Additional color tokens outside of the palette + * @default [] + */ + additionalColorTokensPaths?: string[]; } export interface CreateCssVarsProviderResult { diff --git a/packages/mui-system/src/cssVars/createCssVarsProvider.js b/packages/mui-system/src/cssVars/createCssVarsProvider.js index 1fe0eac88c8f2a..5b4558f8024f1f 100644 --- a/packages/mui-system/src/cssVars/createCssVarsProvider.js +++ b/packages/mui-system/src/cssVars/createCssVarsProvider.js @@ -15,6 +15,35 @@ import useCurrentColorScheme from './useCurrentColorScheme'; export const DISABLE_CSS_TRANSITION = '*{-webkit-transition:none!important;-moz-transition:none!important;-o-transition:none!important;-ms-transition:none!important;transition:none!important}'; +const createObject = (path, value) => { + const result = {}; + const keys = path.split('.'); + let i = 0; + keys.reduce((acc, item) => { + acc[item] = {}; + i += 1; + if (i === keys.length) { + // last key, we need to set the value + acc[item] = value; + } + return acc[item]; + }, result); + return result; +}; + +export function getPath(obj, path) { + if (!path || typeof path !== 'string') { + return null; + } + + return path.split('.').reduce((acc, item) => { + if (acc && acc[item] != null) { + return acc[item]; + } + return null; + }, obj); +} + export default function createCssVarsProvider(options) { const { theme: defaultTheme = {}, @@ -27,6 +56,7 @@ export default function createCssVarsProvider(options) { shouldSkipGeneratingVar: designSystemShouldSkipGeneratingVar, resolveTheme, excludeVariablesFromRoot, + additionalColorTokensPaths = [], } = options; if ( @@ -149,7 +179,14 @@ export default function createCssVarsProvider(options) { theme.vars = deepmerge(theme.vars, vars); if (key === calculatedColorScheme) { - const { ref, sys, ...restParsedScheme } = parsedScheme; + const restParsedScheme = { ...parsedScheme }; + + if (additionalColorTokensPaths.length > 0) { + additionalColorTokensPaths.forEach((path) => { + const firstKey = path.split('.')[0]; + delete restParsedScheme[firstKey]; + }); + } // 4.1 Merge the selected color scheme to the theme theme = { ...theme, @@ -158,17 +195,15 @@ export default function createCssVarsProvider(options) { if (theme.palette) { theme.palette.colorScheme = key; } - if (theme.sys) { - theme.sys = { - ...theme.sys, - color: sys.color, - }; - } - if (theme.ref) { - theme.ref = { - ...theme.ref, - palette: ref.palette, - }; + + if (additionalColorTokensPaths.length > 0) { + additionalColorTokensPaths.forEach((path) => { + const objToMerge = createObject(path, getPath(parsedScheme, path)); + const firstKey = path.split('.')[0]; + if (theme[firstKey]) { + theme[firstKey] = deepmerge(theme[firstKey], objToMerge[firstKey]); + } + }); } } const resolvedDefaultColorScheme = (() => { From 1eefc6333df4a680d1df92d086a06f691fac188a Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 9 Nov 2022 11:39:44 +0100 Subject: [PATCH 35/49] adjust demo colors --- docs/pages/experiments/md3/index.tsx | 110 +++++++++--------- .../src/styles/CssVarsProvider.tsx | 4 +- .../src/styles/extendTheme.ts | 10 ++ 3 files changed, 66 insertions(+), 58 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index d448225202a613..26135e21615830 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -160,77 +160,77 @@ const DemoComponents = () => { const customPalette = { primary: { '0': '#000000', - '10': '#1b1d00', - '20': '#303300', - '30': '#464a00', - '40': '#5e6300', - '50': '#777c0b', - '60': '#919729', - '70': '#abb242', - '80': '#c7cd5a', - '90': '#e3ea73', - '95': '#f2f880', - '99': '#ffffd3', + '10': '#3e001f', + '20': '#640036', + '30': '#8d004e', + '40': '#b70b68', + '50': '#d83181', + '60': '#fa4d9b', + '70': '#ff83b3', + '80': '#ffb0ca', + '90': '#ffd9e3', + '95': '#ffecf0', + '99': '#fffbff', '100': '#ffffff', }, secondary: { '0': '#000000', - '10': '#1c1d06', - '20': '#313219', - '30': '#47482e', - '40': '#5f6043', - '50': '#78795b', - '60': '#929373', - '70': '#adad8c', - '80': '#c8c9a6', - '90': '#e5e5c0', - '95': '#f3f3ce', - '99': '#fffed9', + '10': '#2b151d', + '20': '#422932', + '30': '#5a3f48', + '40': '#74565f', + '50': '#8e6f78', + '60': '#a98892', + '70': '#c5a2ac', + '80': '#e2bdc7', + '90': '#ffd9e3', + '95': '#ffecf0', + '99': '#fffbff', '100': '#ffffff', }, tertiary: { '0': '#000000', - '10': '#002118', - '20': '#09372b', - '30': '#244e41', - '40': '#3c6658', - '50': '#557f71', - '60': '#6e9a8a', - '70': '#88b4a4', - '80': '#a3d0bf', - '90': '#bfecdb', - '95': '#ccfbe9', - '99': '#f3fff8', + '10': '#2f1500', + '20': '#48290c', + '30': '#623f21', + '40': '#7d5636', + '50': '#996e4c', + '60': '#b58763', + '70': '#d2a17c', + '80': '#f0bc95', + '90': '#ffdcc3', + '95': '#ffede3', + '99': '#fffbff', '100': '#ffffff', }, neutral: { '0': '#000000', - '10': '#1c1c17', - '20': '#31312b', - '30': '#484741', - '40': '#605e58', - '50': '#797770', - '60': '#929189', - '70': '#adaba3', - '80': '#c9c6be', - '90': '#e5e2da', - '95': '#f4f1e8', - '99': '#ffffd3', + '10': '#201a1c', + '20': '#352f30', + '30': '#4c4546', + '40': '#645c5e', + '50': '#7e7577', + '60': '#988e90', + '70': '#b3a9aa', + '80': '#cfc4c5', + '90': '#ebe0e1', + '95': '#faeef0', + '99': '#fffbff', '100': '#ffffff', }, neutralVariant: { '0': '#000000', - '10': '#1c1c12', - '20': '#313125', - '30': '#48473b', - '40': '#5f5f51', - '50': '#787869', - '60': '#929182', - '70': '#adac9c', - '80': '#c9c7b6', - '90': '#e5e3d2', - '95': '#f4f1df', - '99': '#ffffd3', + '10': '#23191c', + '20': '#392d31', + '30': '#514347', + '40': '#695b5e', + '50': '#837377', + '60': '#9e8c91', + '70': '#b9a7ab', + '80': '#d5c2c6', + '90': '#f2dde2', + '95': '#ffecf0', + '99': '#fffbff', '100': '#ffffff', }, error: { diff --git a/packages/mui-material-next/src/styles/CssVarsProvider.tsx b/packages/mui-material-next/src/styles/CssVarsProvider.tsx index d426cbe478e77b..1dde1f19cde57f 100644 --- a/packages/mui-material-next/src/styles/CssVarsProvider.tsx +++ b/packages/mui-material-next/src/styles/CssVarsProvider.tsx @@ -1,17 +1,15 @@ import { unstable_createCssVarsProvider as createCssVarsProvider } from '@mui/system'; import { - experimental_extendTheme, SupportedColorScheme, private_createTypography as createTypography, private_excludeVariablesFromRoot as excludeVariablesFromRoot, } from '@mui/material/styles'; +import defaultTheme from './defaultTheme'; const shouldSkipGeneratingVar = (keys: string[]) => !!keys[0].match(/(typography|mixins|breakpoints|direction|transitions)/) || (keys[0] === 'palette' && !!keys[1]?.match(/(mode|contrastThreshold|tonalOffset)/)); -const defaultTheme = experimental_extendTheme(); - const { CssVarsProvider, useColorScheme, getInitColorSchemeScript } = createCssVarsProvider({ theme: defaultTheme, diff --git a/packages/mui-material-next/src/styles/extendTheme.ts b/packages/mui-material-next/src/styles/extendTheme.ts index 427d2200de4c30..90df3bac3eefaf 100644 --- a/packages/mui-material-next/src/styles/extendTheme.ts +++ b/packages/mui-material-next/src/styles/extendTheme.ts @@ -391,16 +391,26 @@ export default function extendTheme(options: CssVarsThemeOptions = {}, ...args: // Material You specific channels if (key === 'light') { colorSchemeSys.color.primaryChannel = colorChannel(colorSchemeRef.palette.primary['40']); + colorSchemeSys.color.onPrimaryChannel = colorChannel(colorSchemeRef.palette.primary['100']); colorSchemeSys.color.secondaryChannel = colorChannel(colorSchemeRef.palette.secondary['40']); + colorSchemeSys.color.onSecondaryChannel = colorChannel( + colorSchemeRef.palette.secondary['100'], + ); colorSchemeSys.color.tertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['40']); + colorSchemeSys.color.onTertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['100']); colorSchemeSys.color.secondaryContainerChannel = colorChannel( colorSchemeRef.palette.secondary['90'], ); colorSchemeSys.color.onSurfaceChannel = colorChannel(colorSchemeRef.palette.neutral['10']); } else { colorSchemeSys.color.primaryChannel = colorChannel(colorSchemeRef.palette.primary['80']); + colorSchemeSys.color.onPrimaryChannel = colorChannel(colorSchemeRef.palette.primary['20']); colorSchemeSys.color.secondaryChannel = colorChannel(colorSchemeRef.palette.secondary['80']); + colorSchemeSys.color.onSecondaryChannel = colorChannel( + colorSchemeRef.palette.secondary['20'], + ); colorSchemeSys.color.tertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['80']); + colorSchemeSys.color.onTertiaryChannel = colorChannel(colorSchemeRef.palette.tertiary['20']); colorSchemeSys.color.secondaryContainerChannel = colorChannel( colorSchemeRef.palette.secondary['30'], ); From a5b0735617d5a8f668723bbead777acd69cc0302 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 9 Nov 2022 13:33:59 +0100 Subject: [PATCH 36/49] Add css vars --- docs/pages/experiments/md3/index.tsx | 38 +++++++++++++++++++ .../mui-material-next/src/Button/Button.tsx | 19 ++++------ 2 files changed, 45 insertions(+), 12 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index 26135e21615830..cad3feee0e6f58 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -1,6 +1,7 @@ import * as React from 'react'; import Tooltip from '@mui/material/Tooltip'; import IconButton from '@mui/material/IconButton'; +import TextField from '@mui/material/TextField'; import Stack from '@mui/material/Stack'; import MD2Button, { ButtonProps as MD2ButtonProps } from '@mui/material/Button'; import { unstable_capitalize as capitalize } from '@mui/utils'; @@ -62,6 +63,9 @@ const md2Colors: MD2ButtonProps['color'][] = [ ]; const DemoComponents = () => { + const [radius, setRadius] = React.useState('10'); + const [gap, setGap] = React.useState('0.5'); + return (

Enabled

@@ -138,6 +142,40 @@ const DemoComponents = () => { ))} +

CSS vars playground

+ + + { + setRadius(e.target.value); + }} + /> + { + setGap(e.target.value); + }} + /> + + + {sizes.map((size) => ( + + ))} + +

Material Design 2 Buttons

{md2Variants.map((variant) => ( diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 1cd8ac4adc3a5d..8efd2235ec8fe8 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -275,7 +275,7 @@ export const ButtonRoot = styled('button', { // We disable the focus ring for mouse, touch and keyboard users. outline: 0, border: 0, - margin: 0, // Remove the margin in Safari + margin: `var(--Button-margin, 0)`, // Remove the margin in Safari by default cursor: 'pointer', userSelect: 'none', verticalAlign: 'middle', @@ -304,7 +304,7 @@ export const ButtonRoot = styled('button', { lineHeight: `calc(${(theme.vars || theme).sys.typescale.label.large.lineHeight} / ${ theme.sys.typescale.label.large.size })`, - borderRadius: (theme.vars || theme).md3.shape.borderRadius, + borderRadius: `var(--Button-radius, ${(theme.vars || theme).md3.shape.borderRadius})`, background: containerColor[ownerState.variant ?? 'text'], color: labelTextColor[ownerState.variant ?? 'text'], boxShadow: containerElevation[ownerState.variant ?? 'text'], @@ -313,8 +313,10 @@ export const ButtonRoot = styled('button', { border: `1px solid ${(theme.vars || theme).sys.color.outline}`, padding: '9px 23px', }), + '--Button-gap': '0.5rem', // Sizes are not specified in Material You, this need to be revised ...(ownerState.size === 'small' && { + '--Button-gap': '0.45rem', fontSize: theme.typography.pxToRem(theme.sys.typescale.label.large.size - 1), // the pxToRem should be moved to typescale in the future padding: '8px 20px', ...(ownerState.variant === 'outlined' && { @@ -322,6 +324,7 @@ export const ButtonRoot = styled('button', { }), }), ...(ownerState.size === 'large' && { + '--Button-gap': '0.55rem', fontSize: theme.typography.pxToRem(theme.sys.typescale.label.large.size + 1), // the pxToRem should be moved to typescale in the future padding: '12px 26px', ...(ownerState.variant === 'outlined' && { @@ -373,11 +376,7 @@ const ButtonStartIcon = styled('span', { }, })<{ ownerState: ButtonOwnerState }>(({ ownerState }) => ({ display: 'inherit', - marginRight: 8, - marginLeft: -8, - ...(ownerState.size === 'small' && { - marginLeft: -2, - }), + marginRight: 'var(--Button-gap)', ...commonIconStyles(ownerState), })); @@ -391,11 +390,7 @@ const ButtonEndIcon = styled('span', { }, })<{ ownerState: ButtonOwnerState }>(({ ownerState }) => ({ display: 'inherit', - marginRight: -8, - marginLeft: 8, - ...(ownerState.size === 'small' && { - marginRight: -2, - }), + marginLeft: 'var(--Button-gap)', ...commonIconStyles(ownerState), })); From 12ee94152e88ee3c434508ec2ea5531da05911fe Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 9 Nov 2022 15:32:31 +0100 Subject: [PATCH 37/49] Fix the border radius --- docs/pages/experiments/md3/index.tsx | 2 +- packages/mui-material-next/src/Button/Button.tsx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index cad3feee0e6f58..dc9782192b398b 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -65,7 +65,7 @@ const md2Colors: MD2ButtonProps['color'][] = [ const DemoComponents = () => { const [radius, setRadius] = React.useState('10'); const [gap, setGap] = React.useState('0.5'); - + return (

Enabled

diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 8efd2235ec8fe8..9b9a44ed67a788 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -304,7 +304,7 @@ export const ButtonRoot = styled('button', { lineHeight: `calc(${(theme.vars || theme).sys.typescale.label.large.lineHeight} / ${ theme.sys.typescale.label.large.size })`, - borderRadius: `var(--Button-radius, ${(theme.vars || theme).md3.shape.borderRadius})`, + borderRadius: `var(--Button-radius, ${(theme.vars || theme).md3.shape.borderRadius}px)`, background: containerColor[ownerState.variant ?? 'text'], color: labelTextColor[ownerState.variant ?? 'text'], boxShadow: containerElevation[ownerState.variant ?? 'text'], From 78638b8af6854609480d2cf04e5f8f876d4a6ab2 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 10 Nov 2022 10:11:10 +0100 Subject: [PATCH 38/49] Fix border radius --- packages/mui-material-next/src/Button/Button.tsx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 9b9a44ed67a788..1eb0371850b907 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -304,7 +304,9 @@ export const ButtonRoot = styled('button', { lineHeight: `calc(${(theme.vars || theme).sys.typescale.label.large.lineHeight} / ${ theme.sys.typescale.label.large.size })`, - borderRadius: `var(--Button-radius, ${(theme.vars || theme).md3.shape.borderRadius}px)`, + borderRadius: `var(--Button-radius, ${ + theme.vars.md3.shape.borderRadius ?? `${theme.md3.shape.borderRadius}px` + })`, background: containerColor[ownerState.variant ?? 'text'], color: labelTextColor[ownerState.variant ?? 'text'], boxShadow: containerElevation[ownerState.variant ?? 'text'], From 92c07354d5d6c6c61aa8d4c6c6ba768753b4f9cc Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 10 Nov 2022 11:44:05 +0100 Subject: [PATCH 39/49] Fix in all cases --- packages/mui-material-next/src/Button/Button.tsx | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 1eb0371850b907..9c6a66137f8de4 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -257,6 +257,9 @@ export const ButtonRoot = styled('button', { theme.sys.typescale.label.large.tracking / theme.sys.typescale.label.large.size }rem`; + const borderRadiusValue: string | number = (theme.vars || theme).md3.shape.borderRadius; + const borderRadius = isNaN(borderRadiusValue) ? borderRadiusValue : `${borderRadiusValue}px`; + return { // Icon variables default values '--md-comp-button-icon-color': labelTextColor[ownerState.variant ?? 'text'], @@ -304,9 +307,7 @@ export const ButtonRoot = styled('button', { lineHeight: `calc(${(theme.vars || theme).sys.typescale.label.large.lineHeight} / ${ theme.sys.typescale.label.large.size })`, - borderRadius: `var(--Button-radius, ${ - theme.vars.md3.shape.borderRadius ?? `${theme.md3.shape.borderRadius}px` - })`, + borderRadius: `var(--Button-radius, ${borderRadius})`, background: containerColor[ownerState.variant ?? 'text'], color: labelTextColor[ownerState.variant ?? 'text'], boxShadow: containerElevation[ownerState.variant ?? 'text'], From 41216b67a8afd9b8ee6648fc9bdeabbff70cfc4f Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 10 Nov 2022 12:32:22 +0100 Subject: [PATCH 40/49] Fix lint issue --- packages/mui-material-next/src/Button/Button.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 9c6a66137f8de4..acb26cab99b661 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -258,7 +258,7 @@ export const ButtonRoot = styled('button', { }rem`; const borderRadiusValue: string | number = (theme.vars || theme).md3.shape.borderRadius; - const borderRadius = isNaN(borderRadiusValue) ? borderRadiusValue : `${borderRadiusValue}px`; + const borderRadius = Number.isNaN(borderRadiusValue) ? borderRadiusValue : `${borderRadiusValue}px`; return { // Icon variables default values From 00a3cd9cb3bd9cf01094ed962d7d260b9d15a7a0 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Thu, 10 Nov 2022 13:16:11 +0100 Subject: [PATCH 41/49] prettier --- packages/mui-material-next/src/Button/Button.tsx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index acb26cab99b661..f12fe8f6f44927 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -258,7 +258,9 @@ export const ButtonRoot = styled('button', { }rem`; const borderRadiusValue: string | number = (theme.vars || theme).md3.shape.borderRadius; - const borderRadius = Number.isNaN(borderRadiusValue) ? borderRadiusValue : `${borderRadiusValue}px`; + const borderRadius = Number.isNaN(borderRadiusValue) + ? borderRadiusValue + : `${borderRadiusValue}px`; return { // Icon variables default values From 909f4667d8552e0babcf55c0e634a4666a7e1519 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 16 Nov 2022 13:31:13 +0100 Subject: [PATCH 42/49] Jun's reviewmerge --- .../mui-material-next/src/Button/Button.tsx | 2 +- .../src/styles/CssVarsProvider.tsx | 1 - .../src/cssVars/createCssVarsProvider.d.ts | 5 -- .../src/cssVars/createCssVarsProvider.js | 64 ++++--------------- 4 files changed, 12 insertions(+), 60 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index f12fe8f6f44927..0adf75ef1dced0 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -258,7 +258,7 @@ export const ButtonRoot = styled('button', { }rem`; const borderRadiusValue: string | number = (theme.vars || theme).md3.shape.borderRadius; - const borderRadius = Number.isNaN(borderRadiusValue) + const borderRadius = Number.isNaN(Number(borderRadiusValue)) ? borderRadiusValue : `${borderRadiusValue}px`; diff --git a/packages/mui-material-next/src/styles/CssVarsProvider.tsx b/packages/mui-material-next/src/styles/CssVarsProvider.tsx index 1dde1f19cde57f..05a9aef2bb47a2 100644 --- a/packages/mui-material-next/src/styles/CssVarsProvider.tsx +++ b/packages/mui-material-next/src/styles/CssVarsProvider.tsx @@ -30,7 +30,6 @@ const { CssVarsProvider, useColorScheme, getInitColorSchemeScript } = }, shouldSkipGeneratingVar, excludeVariablesFromRoot, - additionalColorTokensPaths: ['sys.color', 'ref.palette'], }); export { useColorScheme, getInitColorSchemeScript, shouldSkipGeneratingVar, CssVarsProvider }; diff --git a/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts b/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts index 6a024750997a56..808657beebdda9 100644 --- a/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts +++ b/packages/mui-system/src/cssVars/createCssVarsProvider.d.ts @@ -47,11 +47,6 @@ export interface CssVarsProviderConfig { * value = 'var(--test)' */ shouldSkipGeneratingVar?: (keys: string[], value: string | number) => boolean; - /** - * Additional color tokens outside of the palette - * @default [] - */ - additionalColorTokensPaths?: string[]; } export interface CreateCssVarsProviderResult { diff --git a/packages/mui-system/src/cssVars/createCssVarsProvider.js b/packages/mui-system/src/cssVars/createCssVarsProvider.js index 5b4558f8024f1f..47332eadbd1baf 100644 --- a/packages/mui-system/src/cssVars/createCssVarsProvider.js +++ b/packages/mui-system/src/cssVars/createCssVarsProvider.js @@ -15,35 +15,6 @@ import useCurrentColorScheme from './useCurrentColorScheme'; export const DISABLE_CSS_TRANSITION = '*{-webkit-transition:none!important;-moz-transition:none!important;-o-transition:none!important;-ms-transition:none!important;transition:none!important}'; -const createObject = (path, value) => { - const result = {}; - const keys = path.split('.'); - let i = 0; - keys.reduce((acc, item) => { - acc[item] = {}; - i += 1; - if (i === keys.length) { - // last key, we need to set the value - acc[item] = value; - } - return acc[item]; - }, result); - return result; -}; - -export function getPath(obj, path) { - if (!path || typeof path !== 'string') { - return null; - } - - return path.split('.').reduce((acc, item) => { - if (acc && acc[item] != null) { - return acc[item]; - } - return null; - }, obj); -} - export default function createCssVarsProvider(options) { const { theme: defaultTheme = {}, @@ -56,7 +27,6 @@ export default function createCssVarsProvider(options) { shouldSkipGeneratingVar: designSystemShouldSkipGeneratingVar, resolveTheme, excludeVariablesFromRoot, - additionalColorTokensPaths = [], } = options; if ( @@ -177,34 +147,22 @@ export default function createCssVarsProvider(options) { shouldSkipGeneratingVar, }); theme.vars = deepmerge(theme.vars, vars); - if (key === calculatedColorScheme) { - const restParsedScheme = { ...parsedScheme }; - - if (additionalColorTokensPaths.length > 0) { - additionalColorTokensPaths.forEach((path) => { - const firstKey = path.split('.')[0]; - delete restParsedScheme[firstKey]; - }); - } // 4.1 Merge the selected color scheme to the theme - theme = { - ...theme, - ...restParsedScheme, - }; + Object.keys(parsedScheme).forEach((schemeKey) => { + if (parsedScheme[schemeKey] && typeof parsedScheme[schemeKey] === 'object') { + // shallow merge the 1st level structure of the theme. + theme[schemeKey] = { + ...theme[schemeKey], + ...parsedScheme[schemeKey], + }; + } else { + theme[schemeKey] = parsedScheme[schemeKey]; + } + }); if (theme.palette) { theme.palette.colorScheme = key; } - - if (additionalColorTokensPaths.length > 0) { - additionalColorTokensPaths.forEach((path) => { - const objToMerge = createObject(path, getPath(parsedScheme, path)); - const firstKey = path.split('.')[0]; - if (theme[firstKey]) { - theme[firstKey] = deepmerge(theme[firstKey], objToMerge[firstKey]); - } - }); - } } const resolvedDefaultColorScheme = (() => { if (typeof defaultColorScheme === 'string') { From 5ffb6cf958080c01c94088533f656cd4db04b0d7 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 16 Nov 2022 13:39:27 +0100 Subject: [PATCH 43/49] lint fix --- packages/mui-system/src/cssVars/createCssVarsProvider.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/mui-system/src/cssVars/createCssVarsProvider.js b/packages/mui-system/src/cssVars/createCssVarsProvider.js index 47332eadbd1baf..076771096c80af 100644 --- a/packages/mui-system/src/cssVars/createCssVarsProvider.js +++ b/packages/mui-system/src/cssVars/createCssVarsProvider.js @@ -123,7 +123,7 @@ export default function createCssVarsProvider(options) { } = cssVarsParser(restThemeProp, { prefix: cssVarPrefix, shouldSkipGeneratingVar }); // 3. Start composing the theme object - let theme = { + const theme = { ...parsedTheme, components, colorSchemes, From 2812dea9cddda758c2b2a28df030ef5fafac73e0 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 16 Nov 2022 19:18:25 +0100 Subject: [PATCH 44/49] Fix the sx palette mappings --- docs/pages/experiments/md3/index.tsx | 25 +++++++ .../src/styles/styleFunctionSx.ts | 70 ++++++++++++++++--- packages/mui-system/src/index.js | 2 +- packages/mui-system/src/style.d.ts | 6 ++ packages/mui-system/src/style.js | 6 +- 5 files changed, 96 insertions(+), 13 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index dc9782192b398b..ac1edcc05e1a44 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -142,6 +142,31 @@ const DemoComponents = () => { ))}
+

sx prop showcase

+ + + + + +

CSS vars playground

diff --git a/packages/mui-material-next/src/styles/styleFunctionSx.ts b/packages/mui-material-next/src/styles/styleFunctionSx.ts index b6172bc6407b92..8da43affca9a5a 100644 --- a/packages/mui-material-next/src/styles/styleFunctionSx.ts +++ b/packages/mui-material-next/src/styles/styleFunctionSx.ts @@ -1,8 +1,10 @@ +import { unstable_capitalize as capitalize } from '@mui/utils'; import { Interpolation, unstable_createStyleFunctionSx, compose, - style, + getPath, + getStyleValue as getValue, display, flexbox, grid, @@ -14,12 +16,10 @@ import { borderRight, borderBottom, borderLeft, - borderColor, borderTopColor, borderRightColor, borderBottomColor, borderLeftColor, - getValue, createUnaryUnit, handleBreakpoints, responsivePropType, @@ -27,21 +27,69 @@ import { } from '@mui/system'; import { SxProps, Theme } from './Theme.types'; +interface PaletteStyleOptions { + prop: string; + cssProperty?: string | boolean; +} + +function paletteStyle(options: PaletteStyleOptions = { prop: 'color' }) { + const { prop, cssProperty = options.prop } = options; + + const fn = (props: Record) => { + if (props[prop] == null) { + return null; + } + + const propValue: any = props[prop]; + const theme = props.theme; + const colorThemeMapping = getPath(theme, 'sys.color') || {}; + const paletteThemeMapping = getPath(theme, 'ref.palette') || {}; + + const styleFromPropValue = (propValueFinal: any) => { + // check the value in the color mapping first + let value = getValue(colorThemeMapping, undefined, propValueFinal); + + if (propValueFinal === value) { + // haven't found value in colors mapping, so we are checking in the palette mapping + value = getValue(paletteThemeMapping, undefined, propValueFinal); + } + + if (cssProperty === false) { + return value; + } + + return { + [cssProperty as string]: value, + }; + }; + + return handleBreakpoints(props, propValue, styleFromPropValue); + }; + + fn.propTypes = + process.env.NODE_ENV !== 'production' + ? { + [prop]: responsivePropType, + } + : {}; + + fn.filterProps = [prop]; + + return fn; +} + // Palette values should reference the color tokens -export const color = style({ +export const color = paletteStyle({ prop: 'color', - themeKey: 'sys.color', }); -export const bgcolor = style({ +export const bgcolor = paletteStyle({ prop: 'bgcolor', cssProperty: 'backgroundColor', - themeKey: 'sys.color', }); -export const backgroundColor = style({ +export const backgroundColor = paletteStyle({ prop: 'backgroundColor', - themeKey: 'sys.color', }); const palette = compose(color, bgcolor, backgroundColor); @@ -63,6 +111,10 @@ export const borderRadius = (props: any) => { borderRadius.propTypes = process.env.NODE_ENV !== 'production' ? { borderRadius: responsivePropType } : {}; +const borderColor = paletteStyle({ + prop: 'borderColor', +}); + borderRadius.filterProps = ['borderRadius']; const borders = compose( border, diff --git a/packages/mui-system/src/index.js b/packages/mui-system/src/index.js index 1a964260749787..62c21b57d11bef 100644 --- a/packages/mui-system/src/index.js +++ b/packages/mui-system/src/index.js @@ -22,7 +22,7 @@ export { default as sizing } from './sizing'; export * from './sizing'; export { default as spacing } from './spacing'; export * from './spacing'; -export { default as style, getPath } from './style'; +export { default as style, getPath, getStyleValue } from './style'; export { default as typography } from './typography'; export * from './typography'; export { diff --git a/packages/mui-system/src/style.d.ts b/packages/mui-system/src/style.d.ts index 6cd7220f7ec578..d1f5e5b3b6c2e5 100644 --- a/packages/mui-system/src/style.d.ts +++ b/packages/mui-system/src/style.d.ts @@ -17,3 +17,9 @@ export function style( options: StyleOptions, ): StyleFunction<{ [K in PropKey]?: unknown } & { theme?: Theme }> & { filterProps: string[] }; export function getPath(obj: T, path: string | undefined, checkVars?: boolean): null | unknown; +export function getStyleValue( + themeMapping: object | Function, + transform?: Function, + propValueFinal?: any, + userValue?: any, +): any; diff --git a/packages/mui-system/src/style.js b/packages/mui-system/src/style.js index 3886763eae031a..a07880366b47f2 100644 --- a/packages/mui-system/src/style.js +++ b/packages/mui-system/src/style.js @@ -24,7 +24,7 @@ export function getPath(obj, path, checkVars = true) { }, obj); } -function getValue(themeMapping, transform, propValueFinal, userValue = propValueFinal) { +export function getStyleValue(themeMapping, transform, propValueFinal, userValue = propValueFinal) { let value; if (typeof themeMapping === 'function') { @@ -54,11 +54,11 @@ function style(options) { const theme = props.theme; const themeMapping = getPath(theme, themeKey) || {}; const styleFromPropValue = (propValueFinal) => { - let value = getValue(themeMapping, transform, propValueFinal); + let value = getStyleValue(themeMapping, transform, propValueFinal); if (propValueFinal === value && typeof propValueFinal === 'string') { // Haven't found value - value = getValue( + value = getStyleValue( themeMapping, transform, `${prop}${propValueFinal === 'default' ? '' : capitalize(propValueFinal)}`, From 62c80e301152bd0de313d9bfb782ac3f490d3251 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 16 Nov 2022 19:27:54 +0100 Subject: [PATCH 45/49] Fix lint issue --- packages/mui-material-next/src/styles/styleFunctionSx.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/packages/mui-material-next/src/styles/styleFunctionSx.ts b/packages/mui-material-next/src/styles/styleFunctionSx.ts index 8da43affca9a5a..9160b29d1bd000 100644 --- a/packages/mui-material-next/src/styles/styleFunctionSx.ts +++ b/packages/mui-material-next/src/styles/styleFunctionSx.ts @@ -1,4 +1,3 @@ -import { unstable_capitalize as capitalize } from '@mui/utils'; import { Interpolation, unstable_createStyleFunctionSx, From d418b4a222dcc5ffaac2cf0c7d8b7699f35c6bba Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Wed, 16 Nov 2022 19:41:56 +0100 Subject: [PATCH 46/49] Fix ts issues --- packages/mui-system/src/style.d.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/mui-system/src/style.d.ts b/packages/mui-system/src/style.d.ts index d1f5e5b3b6c2e5..a631aa6c57d4a0 100644 --- a/packages/mui-system/src/style.d.ts +++ b/packages/mui-system/src/style.d.ts @@ -18,8 +18,8 @@ export function style( ): StyleFunction<{ [K in PropKey]?: unknown } & { theme?: Theme }> & { filterProps: string[] }; export function getPath(obj: T, path: string | undefined, checkVars?: boolean): null | unknown; export function getStyleValue( - themeMapping: object | Function, - transform?: Function, + themeMapping: object | ((val: any) => any), + transform?: (val: any, userVal: any) => any, propValueFinal?: any, userValue?: any, ): any; From 4aef1c6447ba45b521ea02f9eb6e2ae72d8736cb Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 18 Nov 2022 14:46:46 +0100 Subject: [PATCH 47/49] Resolve Michal's review --- .../mui-material-next/src/Button/Button.tsx | 103 ++++++++---------- 1 file changed, 45 insertions(+), 58 deletions(-) diff --git a/packages/mui-material-next/src/Button/Button.tsx b/packages/mui-material-next/src/Button/Button.tsx index 0adf75ef1dced0..0e4e9934cbe99f 100644 --- a/packages/mui-material-next/src/Button/Button.tsx +++ b/packages/mui-material-next/src/Button/Button.tsx @@ -89,24 +89,25 @@ export const ButtonRoot = styled('button', { ]; }, })<{ ownerState: ButtonOwnerState }>(({ ownerState, theme }) => { + const tokens = theme.vars || theme; + const containerColor = { - elevated: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${ - (theme.vars || theme).sys.color.surface - }`, - filled: (theme.vars || theme).sys.color[ownerState.color ?? 'primary'], - filledTonal: (theme.vars || theme).sys.color.secondaryContainer, + elevated: `linear-gradient(0deg, rgba(103, 80, 164, 0.05), rgba(103, 80, 164, 0.05)), ${tokens.sys.color.surface}`, + filled: tokens.sys.color[ownerState.color ?? 'primary'], + filledTonal: tokens.sys.color.secondaryContainer, outlined: 'none', text: 'none', }; const labelTextColor = { - elevated: (theme.vars || theme).sys.color.primary, - filled: (theme.vars || theme).sys.color[ - `on${capitalize(ownerState.color ?? 'primary')}` as keyof MD3ColorSchemeTokens - ], - filledTonal: (theme.vars || theme).sys.color.onSecondaryContainer, - outlined: (theme.vars || theme).sys.color[ownerState.color ?? 'primary'], - text: (theme.vars || theme).sys.color[ownerState.color ?? 'primary'], + elevated: tokens.sys.color.primary, + filled: + tokens.sys.color[ + `on${capitalize(ownerState.color ?? 'primary')}` as keyof MD3ColorSchemeTokens + ], + filledTonal: tokens.sys.color.onSecondaryContainer, + outlined: tokens.sys.color[ownerState.color ?? 'primary'], + text: tokens.sys.color[ownerState.color ?? 'primary'], }; const disabeldContainerColor = { @@ -125,34 +126,30 @@ export const ButtonRoot = styled('button', { const hoveredContainerColor = { elevated: theme.vars - ? `rgba(${(theme.vars || theme).sys.color.primaryChannel} / ${ - (theme.vars || theme).sys.state.hover.stateLayerOpacity - })` + ? `rgba(${tokens.sys.color.primaryChannel} / ${tokens.sys.state.hover.stateLayerOpacity})` : alpha(theme.sys.color.primary, theme.sys.state.hover.stateLayerOpacity), filled: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).sys.state.hover.stateLayerOpacity}))` + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / calc(1 - ${ + tokens.sys.state.hover.stateLayerOpacity + }))` : alpha( theme.sys.color[ownerState.color ?? 'primary'], 1 - theme.sys.state.hover.stateLayerOpacity, ), filledTonal: theme.vars - ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).sys.state.hover.stateLayerOpacity - }))` + ? `rgba(${tokens.sys.color.secondaryContainerChannel} / calc(1 - ${tokens.sys.state.hover.stateLayerOpacity}))` : alpha(theme.sys.color.secondaryContainer, 1 - theme.sys.state.hover.stateLayerOpacity), outlined: theme.vars - ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ - (theme.vars || theme).sys.state.hover.stateLayerOpacity + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + tokens.sys.state.hover.stateLayerOpacity })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.hover.stateLayerOpacity, ), text: theme.vars - ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ - (theme.vars || theme).sys.state.hover.stateLayerOpacity + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + tokens.sys.state.hover.stateLayerOpacity })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], @@ -170,34 +167,30 @@ export const ButtonRoot = styled('button', { const pressedContainerColor = { elevated: theme.vars - ? `rgba(${(theme.vars || theme).sys.color.primaryChannel} / ${ - (theme.vars || theme).sys.state.pressed.stateLayerOpacity - })` + ? `rgba(${tokens.sys.color.primaryChannel} / ${tokens.sys.state.pressed.stateLayerOpacity})` : alpha(theme.sys.color.primary, theme.sys.state.pressed.stateLayerOpacity), filled: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).sys.state.pressed.stateLayerOpacity}))` + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / calc(1 - ${ + tokens.sys.state.pressed.stateLayerOpacity + }))` : alpha( theme.sys.color[ownerState.color ?? 'primary'], 1 - theme.sys.state.pressed.stateLayerOpacity, ), filledTonal: theme.vars - ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).sys.state.pressed.stateLayerOpacity - }))` + ? `rgba(${tokens.sys.color.secondaryContainerChannel} / calc(1 - ${tokens.sys.state.pressed.stateLayerOpacity}))` : alpha(theme.sys.color.secondaryContainer, 1 - theme.sys.state.pressed.stateLayerOpacity), outlined: theme.vars - ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ - (theme.vars || theme).sys.state.pressed.stateLayerOpacity + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + tokens.sys.state.pressed.stateLayerOpacity })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.pressed.stateLayerOpacity, ), text: theme.vars - ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ - (theme.vars || theme).sys.state.pressed.stateLayerOpacity + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + tokens.sys.state.pressed.stateLayerOpacity })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], @@ -207,34 +200,30 @@ export const ButtonRoot = styled('button', { const focusedContainerColor = { elevated: theme.vars - ? `rgba(${(theme.vars || theme).sys.color.primaryChannel} / ${ - (theme.vars || theme).sys.state.focus.stateLayerOpacity - })` + ? `rgba(${tokens.sys.color.primaryChannel} / ${tokens.sys.state.focus.stateLayerOpacity})` : alpha(theme.sys.color.primary, theme.sys.state.focus.stateLayerOpacity), filled: theme.vars - ? `rgba(${ - (theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`] - } / calc(1 - ${(theme.vars || theme).sys.state.focus.stateLayerOpacity}))` + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / calc(1 - ${ + tokens.sys.state.focus.stateLayerOpacity + }))` : alpha( theme.sys.color[ownerState.color ?? 'primary'], 1 - theme.sys.state.focus.stateLayerOpacity, ), filledTonal: theme.vars - ? `rgba(${(theme.vars || theme).sys.color.secondaryContainerChannel} / calc(1 - ${ - (theme.vars || theme).sys.state.focus.stateLayerOpacity - }))` + ? `rgba(${tokens.sys.color.secondaryContainerChannel} / calc(1 - ${tokens.sys.state.focus.stateLayerOpacity}))` : alpha(theme.sys.color.secondaryContainer, 1 - theme.sys.state.focus.stateLayerOpacity), outlined: theme.vars - ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ - (theme.vars || theme).sys.state.focus.stateLayerOpacity + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + tokens.sys.state.focus.stateLayerOpacity })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], theme.sys.state.focus.stateLayerOpacity, ), text: theme.vars - ? `rgba(${(theme.vars || theme).sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ - (theme.vars || theme).sys.state.focus.stateLayerOpacity + ? `rgba(${tokens.sys.color[`${ownerState.color ?? 'primary'}Channel`]} / ${ + tokens.sys.state.focus.stateLayerOpacity })` : alpha( theme.sys.color[ownerState.color ?? 'primary'], @@ -257,7 +246,7 @@ export const ButtonRoot = styled('button', { theme.sys.typescale.label.large.tracking / theme.sys.typescale.label.large.size }rem`; - const borderRadiusValue: string | number = (theme.vars || theme).md3.shape.borderRadius; + const borderRadiusValue: string | number = tokens.md3.shape.borderRadius; const borderRadius = Number.isNaN(Number(borderRadiusValue)) ? borderRadiusValue : `${borderRadiusValue}px`; @@ -303,19 +292,17 @@ export const ButtonRoot = styled('button', { duration: theme.transitions.duration.short, }, ), - fontFamily: (theme.vars || theme).sys.typescale.label.large.family, - fontWeight: (theme.vars || theme).sys.typescale.label.large.weight, + fontFamily: tokens.sys.typescale.label.large.family, + fontWeight: tokens.sys.typescale.label.large.weight, fontSize: theme.typography.pxToRem(theme.sys.typescale.label.large.size), // the pxToRem should be moved to typescale in the future - lineHeight: `calc(${(theme.vars || theme).sys.typescale.label.large.lineHeight} / ${ - theme.sys.typescale.label.large.size - })`, + lineHeight: `calc(${tokens.sys.typescale.label.large.lineHeight} / ${theme.sys.typescale.label.large.size})`, borderRadius: `var(--Button-radius, ${borderRadius})`, background: containerColor[ownerState.variant ?? 'text'], color: labelTextColor[ownerState.variant ?? 'text'], boxShadow: containerElevation[ownerState.variant ?? 'text'], // Outlined varaiant ...(ownerState.variant === 'outlined' && { - border: `1px solid ${(theme.vars || theme).sys.color.outline}`, + border: `1px solid ${tokens.sys.color.outline}`, padding: '9px 23px', }), '--Button-gap': '0.5rem', From 702bf5e13f59cb23be21dcc1ed963767efddec42 Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Fri, 18 Nov 2022 16:07:53 +0100 Subject: [PATCH 48/49] Fix lint issues --- docs/pages/experiments/md3/index.tsx | 24 +++++++++++------------- 1 file changed, 11 insertions(+), 13 deletions(-) diff --git a/docs/pages/experiments/md3/index.tsx b/docs/pages/experiments/md3/index.tsx index ac1edcc05e1a44..61614b46bf6467 100644 --- a/docs/pages/experiments/md3/index.tsx +++ b/docs/pages/experiments/md3/index.tsx @@ -13,7 +13,7 @@ import DarkIcon from '@mui/icons-material/DarkModeOutlined'; import LightIcon from '@mui/icons-material/LightModeOutlined'; import CssBaseline from '@mui/material/CssBaseline'; -const ModeSwitcher = () => { +function ModeSwitcher() { const { mode, setMode } = useColorScheme(); const [mounted, setMounted] = React.useState(false); @@ -40,7 +40,7 @@ const ModeSwitcher = () => { ); -}; +} const variants: ButtonProps['variant'][] = [ 'elevated', @@ -62,7 +62,7 @@ const md2Colors: MD2ButtonProps['color'][] = [ 'warning', ]; -const DemoComponents = () => { +function DemoComponents() { const [radius, setRadius] = React.useState('10'); const [gap, setGap] = React.useState('0.5'); @@ -218,7 +218,7 @@ const DemoComponents = () => { ); -}; +} const customPalette = { primary: { @@ -331,14 +331,12 @@ const cssVarsTheme = extendTheme({ export default function App() { return ( - - - - - - - - - + + + + + + + ); } From 0c1f512454c45aef1f789194ff19949bfcb66eca Mon Sep 17 00:00:00 2001 From: Marija Najdova Date: Mon, 21 Nov 2022 10:46:19 +0100 Subject: [PATCH 49/49] Apply suggestions from code review Co-authored-by: Danilo Leal <67129314+danilo-leal@users.noreply.github.com> Signed-off-by: Marija Najdova --- packages/mui-material-next/src/styles/typescale.ts | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/packages/mui-material-next/src/styles/typescale.ts b/packages/mui-material-next/src/styles/typescale.ts index 7a834239faa11a..89d0aca6fd0fef 100644 --- a/packages/mui-material-next/src/styles/typescale.ts +++ b/packages/mui-material-next/src/styles/typescale.ts @@ -3,10 +3,12 @@ const mdSysTypescale = { small: { family: 'Roboto', weight: '500', + tracking: 0.5, }, medium: { family: 'Roboto', weight: '500', + tracking: 0.5, }, large: { family: 'Roboto', @@ -20,24 +22,29 @@ const mdSysTypescale = { small: { family: 'Roboto', weight: '400', + tracking: 0.4, }, medium: { family: 'Roboto', weight: '400', + tracking: 0.25, }, large: { family: 'Roboto', weight: '400', + tracking: 0.15, }, }, title: { small: { family: 'Roboto', weight: '500', + tracking: 0.1, }, medium: { family: 'Roboto', weight: '500', + tracking: 0.15, }, large: { family: 'Roboto',