工作中的那点事之 动画


工作中的那点事之 动画

AutoAnimate

AutoAnimate

可以零配置实现添加动画。

使用方法则是使用useAutoAnimatehook,会返回第一个元素为ref的数组。把该ref放到想要添加动画的元素上即可。

1
2
3
4
5
6
7
8
import { useAutoAnimate } from "@formkit/auto-animate/react";

function MyList() {
const [animationParent] = useAutoAnimate();
return (
<ul ref={animationParent}>{/* 🪄 Magic animations for your list */}</ul>
);
}

自动动画会应用于父元素(设置 auto animate 的 ref)的直属子元素

官方的文档说是会应用于父元素及其直属父元素。但是直接移除父元素并不会触发动画。

  1. DOM 中添加了子元素。
  2. DOM 中的子元素被移除。
  3. 子元素在 DOM 中被移动

当发生上述三种情况的时候,会触发动画

例子

在官网的 demo 中加了一个直接移除父元素的情况。代码也比较简单易懂。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
import { useState } from "react";
import { useAutoAnimate } from "@formkit/auto-animate/react";

export default function App() {
const [items, setItems] = useState([1, 2, 3]);
const [parent, enableAnimations] = useAutoAnimate();

const add = () => setItems([...items, items.length + 1]);
const remove = () =>
setItems((prev) => {
prev.splice(1, 1);
return [...prev];
});

const [visible, setVisible] = useState(true);
const removeParent = () => {
setVisible(false);
};

return (
<>
{visible ? (
<ul ref={parent}>
{items.map((item) => (
<li key={item}>{item}</li>
))}
</ul>
) : null}

<button onClick={add}>Add number</button>
<button onClick={remove}>Rmove number</button>
<button onClick={removeParent}>Rmove Parent</button>
<button onClick={() => enableAnimations(false)}>Disable</button>
</>
);
}

效果:

图 1 中是启用 AutoAnimate 的效果,图 2 则是关闭后的效果。

React Transition Group

Transition 组件使用会把样式跟组件耦合在一起,使用也不是很方便。所以主要介绍一下CSSTransition

CSSTransition

使用方法跟 Vue 的transition组件类似。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
import { useRef, useState } from "react";
import { CSSTransition } from "react-transition-group";
import "./App.css";

export default function App() {
const [visible, setVisible] = useState(false);
const nodeRef = useRef(null);

return (
<div>
<CSSTransition
nodeRef={nodeRef}
in={visible}
timeout={200}
unmountOnExit
classNames="container"
>
<>
<div ref={nodeRef}>I am CLZ!!!</div>
<div>no transition</div>
</>
</CSSTransition>

<button type="button" onClick={() => setVisible(true)}>
Click to Enter
</button>

<button type="button" onClick={() => setVisible(false)}>
Click to Leave
</button>
</div>
);
}

nodeRef: 需要转换的 don 元素的 React 引用
in: CSSTransitionchildren是否显示
unmountOnExit:触发exit后,是否从 dom 树中移除。触发exit的时间一般是in对应的值修改为false

CSSTransition还需要添加样式才能成功添加动画。类名的规则如下:

其中$$CSSTransitionclassNames(这里的s是因为还可以给每个阶段单独指定className,具体查看官网。

  1. $$-enter: 触发enter前的样式
  2. $$-enter-active:触发enter后的样式。效果就是从$$-enter过渡到$$-enter-active的样式
  3. $$-exit: 触发exit前的样式
  4. $$-exit-active:触发exit后的样式。同$$-enter-active
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
.container-enter {
transform: translateX(-100px);
opacity: 0;
}
.container-enter-active {
transform: translateX(0);
opacity: 1;
transition: all 200ms;
}
.container-exit {
transform: translateX(0);
opacity: 1;
}
.container-exit-active {
transform: translateX(-100px);
opacity: 0;
transition: all 200ms;
}

效果:


文章作者: 赤蓝紫
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 赤蓝紫 !
评论
  目录