#reactjs
#reactjs
Вопрос:
CodePen: https://codepen.io/masm/pen/zYExBpr
У меня есть родительский компонент, App
, который содержит список шестнадцатеричных цветов в состоянии. Я просматриваю его для отображения списка Input
компонентов. Every Input
просто отображает поле ввода, в котором значение, заданное для параметра color, передается вниз, а также обработчик onChange для обновления соответствующего состояния цвета App
. Нажатие на New Color
кнопку добавит новый цвет в список в состоянии in App
.
Передается этот список цветов из App
PreviewBox
, который представляет собой поле, отображающее градиент из этого списка цветов.
Вот в чем проблема: когда я отображаю список Input
компонентов, Input
выполняется onChange поля ввода компонентов props.setColor()
, но оно меняется очень медленно. Существует задержка, которая мешает мне свободно перетаскивать палитру цветов, и окно выбора цвета закрывается сразу после выбора цвета.
Однако, когда я просто отображаю список полей ввода в приложении, в отличие от рендеринга Input
компонентов и передачи реквизитов, несмотря на наличие одинаковой информации, первое вообще не отстает, в то время как второе. Я бы действительно предпочел, чтобы каждое поле ввода было в своем собственном компоненте.
Кто-нибудь знает, почему это так?
Input.js
import React, {useState} from 'react';
function Input(props) {
return (
<input type="color" value={props.color} onChange={(e) => props.changeColor(props.id, e.target.value)} />
);
}
export default Input;
// App.js
function App(props) {
const [colors, setColors] = useState(["#FFFF00", "#000000"])
const newColor = () => {
setColors(prev=>[...prev, "#ffffff"])
}
const changeColor = (id, color) => {
setColors(prevColors=>prevColors.map((current, index) => id===index ? color : current))
}
// THE PART IN QUESTION. Very slow when picking new color, lags
// const inputArr = colors.map((color, index)=> <Input
// key={index color}
// color={color}
// id={index}
// changeColor={changeColor}
// />)
// color changes just fine with no lag, I'm able to drag
// colorpicker for each input very easily
const inputs = colors.map((color, index) => <input
key={index}
type="color"
value={color}
onChange={(e) => changeColor(index, e.target.value)}
/>)
return (
<>
<PreviewBox colors={colors}/>
{/* THE PART IN QUESTION */}
{/* {inputArr} */}
{inputs}
<button onClick={newColor}>New Color</button>
</>
);
}
// PreviewBox.js (для контекста)
function PreviewBox(props) {
const [gradientStyle, setGradientStyle] = useState({
background: `linear-gradient(0deg, ${props.colors[0]}, ${props.colors[1]})`,
MozBackground: `linear-gradient(0deg, ${props.colors[0]}, ${props.colors[1]})`,
WebkitBackground: `linear-gradient(0deg, ${props.colors[0]}, ${props.colors[1]})`
})
useEffect(()=> {
setGradientStyle(prev=>{
let newStr = props.colors.slice(1).reduce((final,acc)=>{
return `${final}, ${acc}`
}, `${props.colors[0]} `)
return {
background: `linear-gradient(0deg, ${newStr})`,
MozBackground: `linear-gradient(0deg, ${newStr})`,
WebkitBackground: `linear-gradient(0deg, ${newStr})`
}
})
}, [props.colors)
return (
<div style={{...gradientStyle, width: "500px", height: "500px", border: "1px solid #000"}}>
</div>
);
}