如何根据用户单击正确显示增量值?
我正在尝试复制用于学习目的的Instagram的喜欢系统。在下面的我的代码中,第一次单击任何照片的递增,这意味着正确显示了喜欢
金额,以及指定的用户ID的DB列的正确递增/减少。
我面临的问题是:每当我尝试喜欢
(单击)第一次照片之后的任何其他照片(如上所述正确更新)时,我需要几次单击它,而不是一次,为了使喜欢
值要更改(增量/减少),即使到那时,它也被错误地显示和更新。
我该如何制作它,以便用户可以自由喜欢/不喜欢(单击一次并再次单击同一照片)任何订单的照片,以便更新正确的数据并在浏览器上显示?预先感谢您的任何反馈。
注意:我正在使用React查询来为每个用户获取数据库数据。
这是Gallery.js
const [currentUserClicks, setCurrentUserClicks] = useState(1);
async function fetchUploads() {
const headers = {
"Accept": 'application/json',
"Authorization": `Bearer ${authToken}`
};
const {data} = await axios.get('http://localhost/api/get-user-uploads-data', {headers});
return data;
}
const handleLikesBasedOnUserId = (likedPhotoUserId) => {
if(currentUserClicks > 1) {
setCurrentUserClicks(currentUserClicks - 1);
handleDisLike(likedPhotoUserId); // sends data to server to decrement DB column
} else {
setCurrentUserClicks(currentUserClicks + 1);
handleLike(likedPhotoUserId); // sends data to server to increment DB column
}
};
const handleLike = (likedPhotoUserId) => {
const url = 'http://localhost/api/like';
const headers = {
"Accept": 'application/json',
"Authorization": `Bearer ${authToken}`
};
let data = {
'UserID': likedPhotoUserId,
'likeCount': currentUserClicks
};
axios.post(url, data, {headers})
.then(resp => {
console.log("handleLike",resp.data.userLikes[0].likes);
}).catch(err => {
console.log(err);
});
};
const handleDisLike = (likedPhotoUserId) => {
const url = 'http://localhost/api/dislike';
const headers = {
"Accept": 'application/json',
"Authorization": `Bearer ${authToken}`
};
let data = {
'UserID': likedPhotoUserId,
'likeCount': currentUserClicks
};
axios.post(url, data, {headers})
.then(resp => {
console.log("handleDisLike", resp.data.userLikes[0].likes);
}).catch(err => {
console.log(err);
});
};
const { data } = useQuery('uploads', fetchUploads);
return(
<div className="main">
<ul className="cards">
{
data.map((photos, index) => {
return <Grid
src={photos.url}
likes={photos.likes}
currentUserClicks={currentUserClicks}
key={index}
onClick={handleLikesBasedOnUserId}
userId={photos.UserID}
/>
})
}
</ul>
</div>
);
这里的Grid.js:
const Grid = (props) => {
const [likes, setLikes] = useState(props.likes);
return (
<>
<img src={props.src} alt="Photo" className="gallery-img" onClick={() => props.onClick(props.userId, props.currentUserClicks > 1 ? setLikes(props.likes) : setLikes(props.likes + 1))}/>
<span style={{display: 'none'}}>{props.currentUserClicks}</span>
<h5 className="likes">Likes: {likes}</h5>
</>
);
}
I'm trying to replicate the likes system that Instagram for learning purposes. With my code below, the very first click on any photo increments correctly which means the likes
amount is correctly being displayed as well as the specified user ID's DB column is correctly being incremented/decremented.
The problem I'm facing is: Whenever I try to like
(click) any other photo after the first photo click (which correctly updates as mentioned above), I'll need to click it a few times, instead of once, in order for the likes
value to change (increment/decrement) and even then, it's being displayed and updated incorrectly.
How can I make it so that the user can freely like/dislike (click once and click again on the same photo) any photo in any order so that the correct data is updated and displayed on the browser? Thanks in advance for any feedback.
Note: I'm using React Query to fetch DB data for each user.
Here's Gallery.js
const [currentUserClicks, setCurrentUserClicks] = useState(1);
async function fetchUploads() {
const headers = {
"Accept": 'application/json',
"Authorization": `Bearer ${authToken}`
};
const {data} = await axios.get('http://localhost/api/get-user-uploads-data', {headers});
return data;
}
const handleLikesBasedOnUserId = (likedPhotoUserId) => {
if(currentUserClicks > 1) {
setCurrentUserClicks(currentUserClicks - 1);
handleDisLike(likedPhotoUserId); // sends data to server to decrement DB column
} else {
setCurrentUserClicks(currentUserClicks + 1);
handleLike(likedPhotoUserId); // sends data to server to increment DB column
}
};
const handleLike = (likedPhotoUserId) => {
const url = 'http://localhost/api/like';
const headers = {
"Accept": 'application/json',
"Authorization": `Bearer ${authToken}`
};
let data = {
'UserID': likedPhotoUserId,
'likeCount': currentUserClicks
};
axios.post(url, data, {headers})
.then(resp => {
console.log("handleLike",resp.data.userLikes[0].likes);
}).catch(err => {
console.log(err);
});
};
const handleDisLike = (likedPhotoUserId) => {
const url = 'http://localhost/api/dislike';
const headers = {
"Accept": 'application/json',
"Authorization": `Bearer ${authToken}`
};
let data = {
'UserID': likedPhotoUserId,
'likeCount': currentUserClicks
};
axios.post(url, data, {headers})
.then(resp => {
console.log("handleDisLike", resp.data.userLikes[0].likes);
}).catch(err => {
console.log(err);
});
};
const { data } = useQuery('uploads', fetchUploads);
return(
<div className="main">
<ul className="cards">
{
data.map((photos, index) => {
return <Grid
src={photos.url}
likes={photos.likes}
currentUserClicks={currentUserClicks}
key={index}
onClick={handleLikesBasedOnUserId}
userId={photos.UserID}
/>
})
}
</ul>
</div>
);
Here's Grid.js:
const Grid = (props) => {
const [likes, setLikes] = useState(props.likes);
return (
<>
<img src={props.src} alt="Photo" className="gallery-img" onClick={() => props.onClick(props.userId, props.currentUserClicks > 1 ? setLikes(props.likes) : setLikes(props.likes + 1))}/>
<span style={{display: 'none'}}>{props.currentUserClicks}</span>
<h5 className="likes">Likes: {likes}</h5>
</>
);
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
如果您使用的是React-Query,那么我看不出需要在本地状态中使用
CurrentUserClicks
。通常,它会像这样:查询
,可以获取照片数据,包括喜欢。突变
在突变成功时更新后端的状态您可以使用乐观的更新通过
QueryClient.SetQueryData
更新React-Query Cache 。这样可以确保按钮立即对用户交互产生反应。if you are using react-query, then I don't see the need of having
currentUserClicks
in local state. Usually, it would go like this:query
that fetches photo data, including likes.mutation
to update the state on the backendYou can make the whole process snappier by using optimistic updates, where you would locally update the react-query cache via
queryClient.setQueryData
before you fire off the mutation. That makes sure the like button instantly reacts to the user interaction.