Запретить повторную визуализацию компонентов, сопоставленных массиву - PullRequest
1 голос
/ 17 января 2020

Проблема

Каждый раз, когда я отправляю действие (например, TOGGLE_TODO), массив перерисовывается, даже если изменилось только одно из значений состояния

Код

Отображение списка

{
    arr.length > 0 ?
        arr.map(({ id, text } = {}) => {
            return (
                <TaskElement key={id}
                    text={text}
                    toggleTask={() => toggleTask(id)}
                    removeTask={() => removeTask(id)} />
            )
        }) :
        // ...
}

Редуктор

...
case 'TOGGLE_TASK':
        return state.map(task => (
            task.id === action.id ? {
                ...task,
                checked: !task.checked
            } : task
        ))
...

Когда я переключаю задачу, между обновлениями появляется видимая задержка. Я попытался исправить это, сделав TaskElement PureComponent и даже написал свой собственный shouldComponentUpdate, используя поверхностное равенство, но он все еще перерисовывает.

Я знаю, что отображение массива создает совершенно новый один в памяти, который делает недействительным ключевую опору, вызывающую повторную визуализацию. Есть ли способ исправить это.

Заранее спасибо.

РЕДАКТИРОВАТЬ Аналогичный вопрос: Разве Redux не должен предотвращать повторный рендеринг?

1 Ответ

0 голосов
/ 17 января 2020

Сохранить / Сделать TaskElement как PureComponent.

Внутри редуктора обновлять только тот элемент массива, который требует изменения.

Редуктор

...
case 'TOGGLE_TASK':
        let stateCopy = [...state];
        const toggledItemIndex = state.findIndex((task) => task.id === action.id);

        stateCopy[toggledItemIndex] = {
        ...stateCopy[toggledItemIndex],
        checked: !stateCopy[toggledItemIndex].checked,
        };

        return stateCopy;
...
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...