Skip to content

Commit

Permalink
[DatePicker] Migrate PickersYear to emotion (#25949)
Browse files Browse the repository at this point in the history
* migrate to emotion

* make styleProps optional

* remove lint and add fn name

* use yearButton from styles

* revert types

* [docs] Document all the colors available (#26015)

* [Timeline] Add support for position override on items (#25974)

* [core] Remove deprecated innerRef prop (#26028)

[core] Remove deprecated innerRef prop (#26028)

* [theme] Rename `createMuiTheme` to `createTheme` (#25992)

* [pickers] Remove redundant aria-hidden (#26014)

* [internal][pickers] Remove unused styles (#26023)

* [pickers] Toggle mobile keyboard view in the same commit as the view changes (#26017)

* [DateRangePicker] Fix not being opened on click (#26016)

* Inline classes

* type -> interface

* sort asc

* default props are private

* remove uneccesary type casting

* follow convention

* trigger pipeline

Co-authored-by: Anshuman Pandey <[email protected]>
Co-authored-by: simonecervini <[email protected]>
Co-authored-by: Matheus Wichman <[email protected]>
Co-authored-by: Sebastian Silbermann <[email protected]>
Co-authored-by: Olivier Tassinari <[email protected]>
  • Loading branch information
6 people authored May 12, 2021
1 parent fc40ead commit 52b4efc
Show file tree
Hide file tree
Showing 2 changed files with 124 additions and 77 deletions.
199 changes: 123 additions & 76 deletions packages/material-ui-lab/src/YearPicker/PickersYear.tsx
Original file line number Diff line number Diff line change
@@ -1,12 +1,29 @@
import * as React from 'react';
import clsx from 'clsx';
import { useForkRef } from '@material-ui/core/utils';
import { WithStyles, withStyles, alpha, StyleRules, MuiStyles } from '@material-ui/core/styles';
import { WrapperVariantContext } from '../internal/pickers/wrappers/WrapperVariantContext';
import { useForkRef, capitalize } from '@material-ui/core/utils';
import { alpha, experimentalStyled } from '@material-ui/core/styles';
import {
unstable_composeClasses as composeClasses,
generateUtilityClass,
generateUtilityClasses,
} from '@material-ui/unstyled';
import {
WrapperVariant,
WrapperVariantContext,
} from '../internal/pickers/wrappers/WrapperVariantContext';

export interface YearProps {
autoFocus?: boolean;
children: React.ReactNode;
classes?: {
root?: string;
modeDesktop?: string;
modeMobile?: string;
yearButton?: string;
disabled?: string;
selected?: string;
};
className?: string;
disabled?: boolean;
forwardedRef?: React.Ref<HTMLButtonElement>;
onClick: (event: React.MouseEvent, value: number) => void;
Expand All @@ -15,90 +32,120 @@ export interface YearProps {
value: number;
}

export type PickersYearClassKey = 'root' | 'modeDesktop' | 'yearButton' | 'disabled' | 'selected';
export function getPickersYearUtilityClass(slot: string) {
return generateUtilityClass('PrivatePickersYear', slot);
}

export const styles: MuiStyles<PickersYearClassKey> = (theme): StyleRules<PickersYearClassKey> => ({
root: {
flexBasis: '33.3%',
display: 'flex',
alignItems: 'center',
justifyContent: 'center',
},
modeDesktop: {
export type PickersYearClassKey = keyof NonNullable<YearProps['classes']>;

export const pickersYearClasses = generateUtilityClasses<PickersYearClassKey>(
'PrivatePickersYear',
['root', 'modeMobile', 'modeDesktop', 'yearButton', 'disabled', 'selected'],
);

const useUtilityClasses = (styleProps: YearProps & { wrapperVariant: WrapperVariant }) => {
const { wrapperVariant, disabled, selected, classes } = styleProps;

const slots = {
root: ['root', wrapperVariant && `mode${capitalize(wrapperVariant)}`],
yearButton: ['yearButton', disabled && 'disabled', selected && 'selected'],
};

return composeClasses(slots, getPickersYearUtilityClass, classes);
};

const PickersYearRoot = experimentalStyled(
'div',
{},
{ skipSx: true },
)(({ styleProps }) => ({
flexBasis: '33.3%',
display: 'flex',
alignItems: 'center',
justifyContent: 'center',
...(styleProps?.wrapperVariant === 'desktop' && {
flexBasis: '25%',
}),
}));

const PickersYearButton = experimentalStyled(
'button',
{},
{ skipSx: true },
)(({ theme }) => ({
color: 'unset',
backgroundColor: 'transparent',
border: 0,
outline: 0,
...theme.typography.subtitle1,
margin: '8px 0',
height: 36,
width: 72,
borderRadius: 16,
cursor: 'pointer',
'&:focus, &:hover': {
backgroundColor: alpha(theme.palette.action.active, theme.palette.action.hoverOpacity),
},
yearButton: {
color: 'unset',
backgroundColor: 'transparent',
border: 0,
outline: 0,
...theme.typography.subtitle1,
margin: '8px 0',
height: 36,
width: 72,
borderRadius: 16,
cursor: 'pointer',
[`&.${pickersYearClasses.disabled}`]: {
color: theme.palette.text.secondary,
},
[`&.${pickersYearClasses.selected}`]: {
color: theme.palette.primary.contrastText,
backgroundColor: theme.palette.primary.main,
'&:focus, &:hover': {
backgroundColor: alpha(theme.palette.action.active, theme.palette.action.hoverOpacity),
},
'&$disabled': {
color: theme.palette.text.secondary,
},
'&$selected': {
color: theme.palette.primary.contrastText,
backgroundColor: theme.palette.primary.main,
'&:focus, &:hover': {
backgroundColor: theme.palette.primary.dark,
},
backgroundColor: theme.palette.primary.dark,
},
},
disabled: {},
selected: {},
});
}));

/**
* @ignore - internal component.
*/
const PickersYear = React.forwardRef<HTMLButtonElement, YearProps & WithStyles<typeof styles>>(
(props, forwardedRef) => {
const { autoFocus, classes, children, disabled, onClick, onKeyDown, selected, value } = props;
const ref = React.useRef<HTMLButtonElement>(null);
const refHandle = useForkRef(ref, forwardedRef as React.Ref<HTMLButtonElement>);
const wrapperVariant = React.useContext(WrapperVariantContext);
const PickersYear = React.forwardRef<HTMLButtonElement, YearProps>(function PickersYear(
props,
forwardedRef,
) {
const { autoFocus, className, children, disabled, onClick, onKeyDown, selected, value } = props;
const ref = React.useRef<HTMLButtonElement>(null);
const refHandle = useForkRef(ref, forwardedRef as React.Ref<HTMLButtonElement>);
const wrapperVariant = React.useContext(WrapperVariantContext);

const styleProps = {
...props,
wrapperVariant,
};

// TODO: Can we just forward this to the button?
React.useEffect(() => {
if (autoFocus) {
// `ref.current` being `null` would be a bug in Material-UIu
ref.current!.focus();
}
}, [autoFocus]);
const classes = useUtilityClasses(styleProps);

return (
<div
data-mui-test="year"
className={clsx(classes.root, {
[classes.modeDesktop]: wrapperVariant === 'desktop',
})}
// TODO: Can we just forward this to the button?
React.useEffect(() => {
if (autoFocus) {
// `ref.current` being `null` would be a bug in Material-UIu
ref.current!.focus();
}
}, [autoFocus]);

return (
<PickersYearRoot
data-mui-test="year"
className={clsx(classes.root, className)}
styleProps={styleProps}
>
<PickersYearButton
ref={refHandle}
disabled={disabled}
type="button"
data-mui-test={`year-${children}`}
tabIndex={selected ? 0 : -1}
onClick={(event) => onClick(event, value)}
onKeyDown={(event) => onKeyDown(event, value)}
className={classes.yearButton}
styleProps={styleProps}
>
<button
ref={refHandle}
disabled={disabled}
type="button"
data-mui-test={`year-${children}`}
tabIndex={selected ? 0 : -1}
onClick={(event) => onClick(event, value)}
onKeyDown={(event) => onKeyDown(event, value)}
className={clsx(classes.yearButton, {
[classes.disabled]: disabled,
[classes.selected]: selected,
})}
>
{children}
</button>
</div>
);
},
);
{children}
</PickersYearButton>
</PickersYearRoot>
);
});

export default withStyles(styles, { name: 'PrivatePickersYear' })(PickersYear);
export default PickersYear;
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
export default function composeClasses<ClassKey extends string>(
slots: Record<ClassKey, ReadonlyArray<string | false | undefined>>,
slots: Record<ClassKey, ReadonlyArray<string | false | undefined | null>>,
getUtilityClass: (slot: string) => string,
classes: Record<string, string> | undefined,
): Record<ClassKey, string> {
Expand Down

0 comments on commit 52b4efc

Please sign in to comment.