feat: ajoute composant VoteButtons réutilisable
This commit is contained in:
@@ -0,0 +1,136 @@
|
||||
import {useState, useEffect} from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import Box from '@mui/material/Box'
|
||||
import IconButton from '@mui/material/IconButton'
|
||||
import Typography from '@mui/material/Typography'
|
||||
import ThumbUpIcon from '@mui/icons-material/ThumbUp'
|
||||
import ThumbDownIcon from '@mui/icons-material/ThumbDown'
|
||||
import {useSession} from 'next-auth/react'
|
||||
import {handleVote, getUserVote} from '@/lib/directus.js'
|
||||
|
||||
export default function VoteButtons({versionId, isDisabled = false, hasCountsVisible = false, voteCounts = null, onVoteResult = null}) {
|
||||
const {data: session} = useSession()
|
||||
const [currentVote, setCurrentVote] = useState(null)
|
||||
|
||||
useEffect(() => {
|
||||
const fetchVote = async () => {
|
||||
if (session?.user && versionId) {
|
||||
try {
|
||||
const vote = await getUserVote({
|
||||
accessToken: session.user.accessToken,
|
||||
userId: session.user.userId,
|
||||
versionId
|
||||
})
|
||||
setCurrentVote(vote)
|
||||
} catch (error) {
|
||||
console.error('Error fetching vote:', error)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fetchVote()
|
||||
}, [session, versionId])
|
||||
|
||||
const handleVoteClick = async voteValue => {
|
||||
if (isDisabled) {
|
||||
return
|
||||
}
|
||||
|
||||
try {
|
||||
const newVoteValue = await handleVote({
|
||||
accessToken: session.user.accessToken,
|
||||
userId: session.user.userId,
|
||||
versionId,
|
||||
voteValue
|
||||
})
|
||||
setCurrentVote(newVoteValue)
|
||||
|
||||
if (onVoteResult) {
|
||||
onVoteResult({
|
||||
success: true,
|
||||
message: newVoteValue === null ? 'Vote annulé' : 'Vote enregistré avec succès'
|
||||
})
|
||||
}
|
||||
} catch (error) {
|
||||
if (onVoteResult) {
|
||||
onVoteResult({
|
||||
success: false,
|
||||
message: `Erreur lors du vote: ${error}`
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!session?.user) {
|
||||
return null
|
||||
}
|
||||
|
||||
return (
|
||||
<Box sx={{display: 'flex', alignItems: 'center', gap: 1}}>
|
||||
<Box sx={{display: 'flex', alignItems: 'center'}}>
|
||||
<IconButton
|
||||
size='small'
|
||||
aria-label='vote positif'
|
||||
disabled={isDisabled}
|
||||
sx={{
|
||||
color: currentVote === 1 ? '#2E7D32' : '#666666',
|
||||
backgroundColor: currentVote === 1 ? 'rgba(46, 125, 50, 0.1)' : 'transparent',
|
||||
'&:hover': {
|
||||
backgroundColor: 'rgba(46, 125, 50, 0.2)',
|
||||
color: '#2E7D32'
|
||||
},
|
||||
'&:disabled': {
|
||||
color: '#CCCCCC'
|
||||
}
|
||||
}}
|
||||
onClick={() => handleVoteClick(1)}
|
||||
>
|
||||
<ThumbUpIcon />
|
||||
</IconButton>
|
||||
{hasCountsVisible && voteCounts && (
|
||||
<Typography variant='caption' sx={{color: '#333333', ml: 0.5, fontWeight: 'bold'}}>
|
||||
{voteCounts.positive || 0}
|
||||
</Typography>
|
||||
)}
|
||||
</Box>
|
||||
|
||||
<Box sx={{display: 'flex', alignItems: 'center'}}>
|
||||
<IconButton
|
||||
size='small'
|
||||
aria-label='vote négatif'
|
||||
disabled={isDisabled}
|
||||
sx={{
|
||||
color: currentVote === -1 ? '#D32F2F' : '#666666',
|
||||
backgroundColor: currentVote === -1 ? 'rgba(211, 47, 47, 0.1)' : 'transparent',
|
||||
'&:hover': {
|
||||
backgroundColor: 'rgba(211, 47, 47, 0.2)',
|
||||
color: '#D32F2F'
|
||||
},
|
||||
'&:disabled': {
|
||||
color: '#CCCCCC'
|
||||
}
|
||||
}}
|
||||
onClick={() => handleVoteClick(-1)}
|
||||
>
|
||||
<ThumbDownIcon />
|
||||
</IconButton>
|
||||
{hasCountsVisible && voteCounts && (
|
||||
<Typography variant='caption' sx={{color: '#333333', ml: 0.5, fontWeight: 'bold'}}>
|
||||
{voteCounts.negative || 0}
|
||||
</Typography>
|
||||
)}
|
||||
</Box>
|
||||
</Box>
|
||||
)
|
||||
}
|
||||
|
||||
VoteButtons.propTypes = {
|
||||
versionId: PropTypes.string.isRequired,
|
||||
isDisabled: PropTypes.bool,
|
||||
hasCountsVisible: PropTypes.bool,
|
||||
voteCounts: PropTypes.shape({
|
||||
positive: PropTypes.number,
|
||||
negative: PropTypes.number
|
||||
}),
|
||||
onVoteResult: PropTypes.func
|
||||
}
|
||||
Reference in New Issue
Block a user