Как в react js реализовать сортировку карточек, которые "лайкнули"
Всем доброго утра) Моя задача заключается в том,что бы вывести на экран карточки-данные в массиве. Сделать,чтобы они "лайкались" и при нажатие на определенную кнопку отображались только "залайканые" карточки.
Что я сделал
Я создал функцию const handleLike=()=> {setLiked(!liked);},которая меняет состояние и тем самым я добавляю модификатор liked к классу place-card__like-icon. Так же я передаю состояние liked классу place-card. Делаю это для того, чтобы при нажатие на кнопку <button onClick={displayAdd} ></button> я получил все "залайканые" карточки.
Что то пошло не так
Вместо того, чтобы "лайкалась" одна карточка- "лайкаются" все. Подскажите пожалуйста, что я делаю не так.
function App() {
const [liked, setLiked] = React.useState(false);
const [isDisplay, setDisplay] = React.useState(false);
const displayAdd=()=>setDisplay(!isDisplay);
const handleLike=()=> {setLiked(!liked);}
const comments = [{
id: 1,
author: 'Лиза',
text: 'Все уже сдали деньги на субботник?',
}, {
id: 2,
author: 'Джеймс',
text: 'Никто не видел мой сэндвич?',
}, {
id: 3,
author: 'Грег',
text: 'Продам мопед',
}];
return (
<>
{comments.map((message, i) => (
<div key={message.id} className={`place-card ${'liked' ? isDisplay && 'display-none':''}`}>
<div className="place-card__image" >
<button onClick={displayAdd} ></button>
<button className="place-card__delete-icon"></button></div>
<div className="place-card__description">
<h3 className="place-card__name">{message.author}</h3>
<button onClick={handleLike} className={`place-card__like-icon ${liked && 'place-card__like-icon_liked'}`} ></button></div></div>
))}
</>
);
}
export default App;```
Ответы (1 шт):
Вариант №1
У вас сейчас одно состояние для всех карточек, потому что и state для них один.
Я предлагаю хранить свойство liked для каждой карточки внутри массива comments. И поместить этот массив в state
const [comments, setComments] = useState([{
id: 1,
author: 'Лиза',
text: 'Все уже сдали деньги на субботник?',
liked: false,
}, {
id: 2,
author: 'Джеймс',
text: 'Никто не видел мой сэндвич?',
liked: false,
}, {
id: 3,
author: 'Грег',
text: 'Продам мопед',
liked: false,
}]);
Передаем функции handleLike явно id сообщения которое будем изменять. Вашу кнопку с handleLike переписываем следующим образом:
<button onClick={() => handleLike(message.id)} className={`place-card__like-icon ${liked && 'place-card__like-icon_liked'}`} ></button></div></div>
Пишем функцию handleLike с изменениями
const handleLike = id => {
setComments(state => state.map(el => {
if (el.id === id) {
return {
...el,
liked: !el.liked,
}
}
return el;
}))
}
После этих изменений все должно работать
Вариант №2
Разделить компоненту с выводом массива (где у вас comments.map) и саму карточку.
Тогда для каждой карточки можно будет держать состояние и его менять. Но я бы не советовал такой вариант.