refactor: monorepo setup with lerna (#243)
This commit is contained in:
committed by
GitHub
parent
dac29fbf3c
commit
504d95c34f
97
packages/core/src/components/UI/Icon.tsx
Normal file
97
packages/core/src/components/UI/Icon.tsx
Normal file
@ -0,0 +1,97 @@
|
||||
import { styled } from '@mui/material/styles';
|
||||
import React from 'react';
|
||||
|
||||
import icons from './Icon/icons';
|
||||
import transientOptions from '@staticcms/core/lib/util/transientOptions';
|
||||
|
||||
import type { IconType } from './Icon/icons';
|
||||
|
||||
interface IconWrapperProps {
|
||||
$width: number;
|
||||
$height: number;
|
||||
$rotation: string;
|
||||
}
|
||||
|
||||
const IconWrapper = styled(
|
||||
'span',
|
||||
transientOptions,
|
||||
)<IconWrapperProps>(
|
||||
({ $width, $height, $rotation }) => `
|
||||
display: inline-block;
|
||||
line-height: 0;
|
||||
width: ${$width}px;
|
||||
height: ${$height}px;
|
||||
transform: rotate(${$rotation});
|
||||
|
||||
& path:not(.no-fill),
|
||||
& circle:not(.no-fill),
|
||||
& polygon:not(.no-fill),
|
||||
& rect:not(.no-fill) {
|
||||
fill: currentColor;
|
||||
}
|
||||
|
||||
& path.clipped {
|
||||
fill: transparent;
|
||||
}
|
||||
|
||||
svg {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
`,
|
||||
);
|
||||
|
||||
const rotations = { right: 90, down: 180, left: 270, up: 360 };
|
||||
|
||||
export type Direction = keyof typeof rotations;
|
||||
|
||||
/**
|
||||
* Calculates rotation for icons that have a `direction` property configured
|
||||
* in the imported icon definition object. If no direction is configured, a
|
||||
* neutral rotation value is returned.
|
||||
*
|
||||
* Returned value is a string of shape `${degrees}deg`, for use in a CSS
|
||||
* transform.
|
||||
*/
|
||||
function getRotation(iconDirection?: Direction, newDirection?: Direction) {
|
||||
if (!iconDirection || !newDirection) {
|
||||
return '0deg';
|
||||
}
|
||||
const degrees = rotations[newDirection] - rotations[iconDirection];
|
||||
return `${degrees}deg`;
|
||||
}
|
||||
|
||||
const sizes = {
|
||||
xsmall: 12,
|
||||
small: 18,
|
||||
medium: 24,
|
||||
large: 32,
|
||||
};
|
||||
|
||||
export interface IconProps {
|
||||
type: IconType;
|
||||
direction?: Direction;
|
||||
width?: number;
|
||||
height?: number;
|
||||
size?: keyof typeof sizes;
|
||||
className?: string;
|
||||
}
|
||||
|
||||
const Icon = ({ type, direction, width, height, size = 'medium', className }: IconProps) => {
|
||||
const IconSvg = icons[type].image;
|
||||
|
||||
return (
|
||||
<IconWrapper
|
||||
className={className}
|
||||
$width={width ? width : size in sizes ? sizes[size as keyof typeof sizes] : sizes['medium']}
|
||||
$height={
|
||||
height ? height : size in sizes ? sizes[size as keyof typeof sizes] : sizes['medium']
|
||||
}
|
||||
$rotation={getRotation(icons[type].direction, direction)}
|
||||
>
|
||||
<IconSvg />
|
||||
</IconWrapper>
|
||||
);
|
||||
};
|
||||
|
||||
export default Icon;
|
Reference in New Issue
Block a user