Как заставить ререндериться страницу react native
Есть страница, на которой я пишу To Do List
export default function func() {
const [todos, setTodos] = useState([
{id: 1, task: "First", completed: true},
{id: 2, task: "Second", completed: false}
])
useEffect(()=>{
saveTodo(todos);
},[todos]);
Сам же список тудушек задан следующим фрагментом:
const ListItem = ({todo}) => {
return <View style={styles.listenItem}>
<View style={{flex: 1}}>
<Text style = {{
fontWeight: 'bold',
fontSize: 15,
color: '#1f145c',
textDecorationLine: todo.completed ? 'line-through' : 'none',
}}>
{todo.task}
</Text>
</View>
{!todo?.completed && (
<TouchableOpacity style={[styles.actionIcon]} onPress={()=>setStatus(todo.id)}>
<Icon name="check" size={20} color={'#fff'}/>
</TouchableOpacity>
)}
<TouchableOpacity style={[styles.actionIcon, {backgroundColor: 'red'}]} onPress={() => deleteTodo(todo?.id)}>
<Icon name="trash-o" size={20} color={'#fff'}/>
</TouchableOpacity>
</View>}
И внутри return
<FlatList
showsVerticalScrollIndicator={false}
contentContainerStyle={{padding: 20, paddingBottom: 100}}
data={todos}
renderItem={ ({item}) => <ListItem todo={item} />}
/>
Я хочу, чтобы при вызове функции setStatus менялась отрисовка элементов списка, что и происходит, когда вызывается другая функция, при которой ререндерится весь компонент, но сама функция setStatus почему-то этого не делает.
const setStatus = (todoId) =>{
var newTodo = todos;
newTodo.forEach(element => {
if(element.id == todoId) {element.completed = true; console.log("success")}
});
setTodos(newTodo);}
Как я понял, useState не видит изменения параметра completed, может есть какой-нибудь другой способ запустить ререндер?
Ответы (1 шт):
Как я понял, useState не видит изменения параметра completed, может есть какой-нибудь другой способ запустить ререндер?
Просто поменять "где-то" значение ключа не достаточно для вызова рендера... Нужно получить новую ссылку на массив и новую ссылку на измененный объект.
Пробуй сделать вот так
const setStatus = (todoId) => {
var newTodo = todos.map(element => {
if (element.id == todoId) {
console.log("success")
element = {...element, completed: true}
}
return element
});
setTodos(newTodo);
}