我试图将我发现here的这个很酷的<canvas>
动画转换为React可重用组件。看起来这个组件需要画布的一个父组件,以及function Ball()
的许多子组件。
出于性能原因,将Balls
变成无状态组件可能会更好,因为它们会有很多。我对制作无状态组件并不熟悉,并且想知道在哪里定义this.update()
中定义的this.draw
和function Ball()
函数。
无状态组件的功能是在组件内部还是外部?换句话说,以下哪个更好?
1:
const Ball = (props) => {
const update = () => {
...
}
const draw = () => {
...
}
return (
...
);
}
2:
function update() {
...
}
function draw() {
...
}
const Ball = (props) => {
return (
...
);
}
每个人的优缺点是什么?对于像我这样的具体用例,其中一个更好吗?
答案 0 :(得分:36)
首先要注意的是无状态功能组件不能有方法,如果它是无状态函数,你不应该依赖于在渲染的update
上调用draw
或Ball
成分
在大多数情况下,您应该在组件函数之外声明函数,因此您只声明它们一次并始终重用相同的引用。在内部声明函数时,每次渲染组件时,都会再次定义函数。
在某些情况下,您需要在组件内部定义一个函数,例如,将其指定为基于组件属性的行为不同的事件处理程序。但您仍然可以在Ball
之外定义函数并将其与属性绑定,从而使代码更清晰,并使update
或draw
函数可重用。
// You can use update somewhere else
const update (propX, a, b) => { ... };
const Ball = props => (
<Something onClick={update.bind(null, props.x)} />
);
而不是:
const Ball = props => {
function update(a, b) {
// props.x is visible here
}
return (
<Something onClick={update} />
);
}
答案 1 :(得分:3)
我们可以在无状态功能组件中包含函数,下面是示例:
const Action = () => {
function handlePick(){
alert("test");
}
return (
<div>
<input type="button" onClick={handlePick} value="What you want to do ?" />
</div>
);
}
但是,这不是一个好习惯,因为每次调用该组件时都会定义函数handlePick()
。
答案 2 :(得分:0)
2:很好,但是当您想使用道具时却有悲剧。
最佳实践是useHooks函数,例如useCallback函数。
从反应库导入它们。
答案 3 :(得分:0)
我们可以在功能组件中如下使用React钩子useCallback
:
const home = (props) => {
const { small, img } = props
const [currentInd, setCurrentInd] = useState(0);
const imgArrayLength = img.length - 1;
useEffect(() => {
let id = setInterval(() => {
if (currentInd < imgArrayLength) {
setCurrentInd(currentInd => currentInd + 1)
}
else {
setCurrentInd(0)
}
}, 5000);
return () => clearInterval(id);
}, [currentInd]);
const onLeftClickHandler = useCallback(
() => {
if (currentInd === 0) {
}
else {
setCurrentInd(currentInd => currentInd - 1)
}
},
[currentInd],
);
const onRightClickHandler = useCallback(
() => {
if (currentInd < imgArrayLength) {
setCurrentInd(currentInd => currentInd + 1)
}
else {
}
},
[currentInd],
);
return (
<Wrapper img={img[currentInd]}>
<LeftSliderArrow className={currentInd > 0 ? "red" : 'no-red'} onClick={onLeftClickHandler}>
<img src={Icon_dir + "chevron_left_light.png"}></img>
</LeftSliderArrow>
<RightSliderArrow className={currentInd < imgArrayLength ? "red" : 'no-red'} onClick={onRightClickHandler}>
<img src={Icon_dir + "chevron_right_light.png"}></img>
</RightSliderArrow>
</Wrapper>);
}
export default home;
我从它的父级那里获取了'img',那是一个数组。
答案 4 :(得分:0)
import React, { useState } from 'react';
function Example() {
// Declare a new state variable, which we'll call "count"
const [count, setCount] = useState(0);
const a = () => {
setCount(count + 1);
};
return (
<div>
<p>You clicked {count} times</p>
<button onClick={a}>Click me</button>
</div>
);
}
export default Example;