Icon组件
Icon组件是基于 react-fontawesome
安装插件
@fortawesome/fontawesome-svg-core是Font Awesome 的 SVG 核心库@fortawesome/free-solid-svg-icons包含了 Font Awesome 提供的免费的实心图标集合@fortawesome/react-fontawesome@latest用于在 React 项目中以组件的形式使用 Font Awesome 图标
yarn add @fortawesome/fontawesome-svg-core
yarn add @fortawesome/free-solid-svg-icons
yarn add @fortawesome/react-fontawesome@latest
组件效果
支持不同主题
组件结构
src/components/Icon/icon.tsx
library.add(fas)是添加所有图标- 根据
theme动态生成主题样式 - 使用
FontAwesomeIcon组件渲染Icon
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome'
import classNames from 'classnames'
import { FC } from 'react'
import { fas } from '@fortawesome/free-solid-svg-icons'
import { library } from '@fortawesome/fontawesome-svg-core'
import { IconProps } from './types'
library.add(fas)
export const Icon: FC<IconProps> = (props) => {
const { theme, className, ...restProps } = props
const clsses = classNames('w-design-icon', className, {
[`icon-${theme}`]: theme,
})
return <FontAwesomeIcon className={clsses} {...restProps} />
}
组件类型
src/components/Icon/types.ts
import { FontAwesomeIconProps } from '@fortawesome/react-fontawesome'
export type ThemeProps =
| 'primary'
| 'secondary'
| 'success'
| 'info'
| 'warning'
| 'danger'
| 'light'
| 'dark'
export interface IconProps extends FontAwesomeIconProps {
theme?: ThemeProps
}
组件样式
src/components/Icon/_style.scss
@each是预处理器中的一个迭代器指令,用于在样式表中迭代处理一个列表或映射
@each $key, $val in $theme-colors {
.icon-#{$key} {
color: $val
}
}
src/styles/_variables.scss
$theme-colors: (
"primary": $primary,
"secondary": $secondary,
"success": $success,
"info": $info,
"warning": $warning,
"danger": $danger,
"light": $light,
"dark": $dark
);
Transition组件
Transition组件是基于react-transition-group
yarn add react-transition-group
yarn add @types/react-transition-group
组件结构
src/components/Transition/transition.tsx
unmountOnExit: true过渡结束后将组件从 DOM 中卸载,默认是false过渡结束后组件仍然保留在 DOM 中appear: true在组件的初始渲染时也会应用过渡效果CSSTransition通过添加和移除 CSS 类名来触发过渡动画
import { FC } from 'react'
import { TransitionProps } from './types'
import { CSSTransition } from 'react-transition-group'
export const Transition: FC<TransitionProps> = (props) => {
const { children, classNames, animation, wrapper, ...restProps } = props
return (
<CSSTransition
classNames={classNames ? classNames : animation}
{...restProps}
>
{wrapper ? <>{children}</> : children}
</CSSTransition>
)
}
Transition.defaultProps = {
unmountOnExit: true,
appear: true,
}
组件类型
src/components/Transition/types.ts
import { CSSTransitionProps } from 'react-transition-group/CSSTransition'
export type AnimationName =
| 'zoom-in-top'
| 'zoom-in-left'
| 'zoom-in-bottom'
| 'zoom-in-right'
export type TransitionProps = CSSTransitionProps & {
animation?: AnimationName
wrapper?: boolean
}
组件样式
src/styles/_animation.scss
@include zoom-animation('top', scaleY(0), scaleY(1), center top);
@include zoom-animation('left', scale(.45, .45), scale(1, 1), top left);
@include zoom-animation('right', scale(.45, .45), scale(1, 1), top right);
@include zoom-animation('bottom', scaleY(0), scaleY(1), center bottom);
src/styles/_mixin.scss
控制过渡方向、过渡状态公共mixin
@mixin zoom-animation(
// 从哪个方向的过渡效果
$direction: 'top',
// 缩放开始时的scale值
$scaleStart: scaleY(0),
// 缩放结束时的scale值
$scaleEnd: scaleY(1),
// 缩放起始时的origin值
$origin: center top
) {
// 开始进入
.zoom-in-#{$direction}-enter {
opacity: 0;
transform: $scaleStart;
}
// 正在进入
.zoom-in-#{$direction}-enter-active {
// 设置透明度为1
opacity: 1;
// 设置缩放结束状态
transform: $scaleEnd;
// transform 属性:在 300 毫秒内完成变化,使用 cubic-bezier(0.23, 1, 0.32, 1) 时间曲线,初始延迟 100 毫秒。
transition: transform 300ms cubic-bezier(0.23, 1, 0.32, 1) 100ms,
// opacity 属性:在 300 毫秒内完成变化,使用 cubic-bezier(0.23, 1, 0.32, 1) 时间曲线,初始延迟 100 毫秒。
opacity 300ms cubic-bezier(0.23, 1, 0.32, 1) 100ms;
// 设置缩放原点
transform-origin: $origin;
}
// 设置退出时的透明度为1
.zoom-in-#{$direction}-exit {
opacity: 1;
}
// 正在离开
.zoom-in-#{$direction}-exit-active {
// 设置透明度为0
opacity: 0;
// 设置缩放起始状态
transform: $scaleStart;
// transform 属性:在 300 毫秒内完成变化,使用 cubic-bezier(0.23, 1, 0.32, 1) 时间曲线,初始延迟 100 毫秒。
transition: transform 300ms cubic-bezier(0.23, 1, 0.32, 1) 100ms,
// opacity 属性:在 300 毫秒内完成变化,使用 cubic-bezier(0.23, 1, 0.32, 1) 时间曲线,初始延迟 100 毫秒。
opacity 300ms cubic-bezier(0.23, 1, 0.32, 1) 100ms;
// 设置缩放原点
transform-origin: $origin;
}
}