React Hooks 调研2019-06-04Θ
Hooks 是为了解决 React 目前存在的一些问题:
- 有状态的逻辑很难在组件之间重用
- React 没有提供一个有效的可重用方法。render props、HOC 模式的引入会导致重构组件,使得问题变得麻烦,组件难以维护。
- 复杂组件难以阅读和理解
- 类(Classes)让人困惑、影响机器运行效率
强依赖#
react-scripts#
CRA 升级 — react-scripts 3.0.0 以上。CHANGELOG
react-scripts 3.0.0 新增特性:
- Jest 24
- Hooks support — 强制执行 Hooks 规则 eslint-plugin-react-hooks
API#
useState#
import React, { useState } from 'react';
export default function Example() {
const [ count, setCount ] = useState(0);
const addCounter = () => {
const newValue = count + 1;
setCount(newValue);
};
return (
<div>
<p>You clicked {count} times</p>
<button onClick={addCounter}>Click me</button>
</div>
)
}
useEffect#
useEffect(() => {
document.title = `You clicked ${count} times`;
}, [count]);
componentDidUpdate(prevProps, prevState) {
if (prevState.count !== this.state.count) {
document.title = `You clicked ${this.state.count} times`;
}
}
Hooks 的使用要遵循固定的规则 https://www.npmjs.com/package/eslint-plugin-react-hooks CRA 升级 react-scripts 到 3.0.0 默认遵守这个规则
封装 useInterval Hook#
import React, { useState, useEffect, useRef } from 'react';
export default function Counter() {
const [ count, setCount ] = useState(0);
useInterval(() => {
setCount(count + 1);
}, 1000);
function useInterval(callback, delay) {
const savedCallback = useRef();
useEffect(() => {
savedCallback.current = callback;
});
useEffect(() => {
function tick() {
savedCallback.current();
}
if (delay !== null) {
let id = setInterval(tick, delay);
return () => clearInterval(id);
}
}, [delay]);
}
return <h2>{count}</h2>;
}
- Hooks 的使用还是处于探索阶段,使用技巧并不成熟
- 对待 Hooks,建议是在新项目中尝试使用
参考文档#