Как использовать переменную, объявленную в useEffect(), в другой функции?
Ps решил мою проблему, но я все равно хотел бы услышать ваши мысли об этом и моем коде, если у вас будет время:)
Я могу присвоить значение этой переменной только ТОЛЬКО после завершения рендеринга, поэтому я предполагаю, что я должен объявить эту переменную в useEffect(), и невозможно присвоить ей значение в глобальной области (которая выполняется до того, как что-либо будет отображаться). Но я также хочу использовать эту переменную в другом useEffect(), но не могу, поскольку она объявлена внутри функции и не принадлежит глобальной области видимости. Кроме того, нормально ли иметь два useEffect -s? Один мне нужен для захвата контекста холста и сохранения этого контекста согласованным (не захватывать новый при каждом обновлении DOM, как это происходит, когда я не помещаю [] в качестве второго аргумента первого useEffect). А другой - для выполнения действий с этим уникальным контекстом при изменении состояния. Имеет ли это смысл? Мой код:
import React, { useState, useRef, useEffect } from "react";
import { degreesToRadiansFlipped } from "./helpers/degreesToRadiansFlipped";
function Circle() {
let [degree, setDegree] = useState(0);
const canvas = useRef();
const inputField = useRef();
const coordinateX = Math.cos(degreesToRadiansFlipped(degree)) * 100 + 250;
const coordinateY = Math.sin(degreesToRadiansFlipped(degree)) * 100 + 250;
useEffect(() => {
const context = canvas.current.getContext("2d");
drawCircle(context, coordinateX, coordinateY);
return context;
/*return function cleanUp() {
context.clearRect(0, 0, 500, 500);
context.beginPath();
drawCircle(context, coordinateX, coordinateY);
};*/
}, []);
useEffect(() => {
drawCircle(context, coordinateX, coordinateY);
}, [degree]);
let drawCircle = function(context, x, y) {
context.beginPath();
//arc has option to make it anti-clockwise, making flipping radians redundant
context.arc(250, 250, 100, 0, Math.PI * 2);
context.moveTo(250, 250);
context.lineTo(x, y);
context.stroke();
};
return (
<div>
<canvas ref={canvas} width={500} height={500}></canvas>
<form
onSubmit={(e) => {
e.preventDefault();
setDegree(inputField.current.value);
}}
>
<input type="text" ref={inputField}></input>
<button type="submit">Submit</button>
</form>
</div>
);
}
export default Circle;
2 ответа
Да , имеет смысл иметь несколько useEffect, если у них разные аргументы во втором параметре, как и у вас.
вы можете объявить переменную вне useEffec как undefined.
let context = undefined // is not constant
useEffect(() => {
context = canvas.current.getContext("2d");
drawCircle(context, coordinateX, coordinateY);
return context;
/*return function cleanUp() {
context.clearRect(0, 0, 500, 500);
context.beginPath();
drawCircle(context, coordinateX, coordinateY);
};*/
}, []);
useEffect(() => {
drawCircle(context, coordinateX, coordinateY);
}, [degree]);
этот способ доступен в области действия функции
Я знаю, что это старая ветка, но на случай, если кто-то с этим столкнется. Если вы объявите переменную вне useEffect, она потеряет все присвоения после каждого рендеринга. Лучше использовать хук useRef и сохранить изменяемое значение в свойстве .current. В противном случае лучше оставить его внутри useEffect.