From d48b1f5de5378bb5cfa3a0b49af312096e66f0e5 Mon Sep 17 00:00:00 2001 From: Luis Felipe Risch <lfr20@inf.ufpr.br> Date: Fri, 25 Jun 2021 11:38:36 -0300 Subject: [PATCH] Fixed pagination comments --- src/Components/CollectionCommentSection.js | 32 +++++++- .../ResourcePageComponents/CommentsArea.js | 80 +++++++++++++++++-- src/Components/SnackbarComponent.js | 2 +- src/env.js | 2 +- 4 files changed, 103 insertions(+), 13 deletions(-) diff --git a/src/Components/CollectionCommentSection.js b/src/Components/CollectionCommentSection.js index 3b5b07b4..49f8861e 100644 --- a/src/Components/CollectionCommentSection.js +++ b/src/Components/CollectionCommentSection.js @@ -50,6 +50,8 @@ export default function CollectionCommentSection(props) { color: '' }); const [reviews, setReviews] = useState([]); + const [totalReviews, setTotalReviews] = useState(0); + const [currPageReviews, setCurrPageReviews] = useState(0); const comment_ref = useRef(null); const forceUpdate = () => { setRenderState(!render_state); } @@ -100,6 +102,20 @@ export default function CollectionCommentSection(props) { return <MuiAlert elevation={6} variant="filled" {...props} />; } + function handleLoadMoreReviews() { + if (reviews.length !== parseInt(totalReviews)) + setCurrPageReviews((previous) => previous + 1) + else { + const info = { + open: true, + text: 'Não há mais comentários para carregar.', + severity: 'warning', + color: '', + } + handleSnackInfo(info) + } + } + const NoCommentsMessage = () => { const NoCommentsContainer = styled.div` text-align: center; @@ -136,7 +152,7 @@ export default function CollectionCommentSection(props) { const CollectionComments = () => { return ( <ComentariosBox> - <h3>{reviews.length} {reviews.length !== 1 ? 'Relatos' : 'Relato'} sobre o uso do Recurso</h3> + <h3>{totalReviews} {totalReviews !== 1 ? 'Relatos' : 'Relato'} sobre o uso do Recurso</h3> {reviews.map(r => { return ( <div className="comentario-template" key={r.created_at}> @@ -159,27 +175,34 @@ export default function CollectionCommentSection(props) { </div> ); })} + <div className="load-more"> + <IconButton className="button" onClick={handleLoadMoreReviews}> + <KeyboardArrowDownIcon /> + </IconButton> + </div> </ComentariosBox> ); } function handleSuccessGet(data, headers) { setReviews((previousState) => previousState.concat(data)); + if (headers.has('X-Total-Count')) + setTotalReviews(headers.get('X-Total-Count')) setIsLoading(false); } function handleFailGet(error) { - console.log(error); setIsLoading(false) + setIsLoading(false) } useEffect(() => { setIsLoading(true) getRequest( - `/collections/${props.id}/reviews`, + `/collections/${props.id}/reviews?page=${currPageReviews}`, handleSuccessGet, (error) => { handleFailGet(error) } ) - }, [render_state]); + }, [render_state, currPageReviews]); return ( <CommentAreaContainer container xs={12} direction="row" justify="center" alignItems="center"> @@ -290,6 +313,7 @@ const ComentariosBox = styled.div` } .load-more{ + width: 100%; display: flex; flex-direction: row; justify-content: center; diff --git a/src/Components/ResourcePageComponents/CommentsArea.js b/src/Components/ResourcePageComponents/CommentsArea.js index 578ab7d2..e68a1a23 100644 --- a/src/Components/ResourcePageComponents/CommentsArea.js +++ b/src/Components/ResourcePageComponents/CommentsArea.js @@ -33,6 +33,9 @@ import SignUpModal from './../SignUpModal' import MuiAlert from '@material-ui/lab/Alert'; import CircularProgress from '@material-ui/core/CircularProgress'; import noAvatar from '../../img/default_profile.png'; +import IconButton from '@material-ui/core/IconButton'; +import KeyboardArrowDownIcon from '@material-ui/icons/KeyboardArrowDown'; +import SnackBarComponent from '../../Components/SnackbarComponent'; function Alert(props) { return <MuiAlert elevation={6} variant="filled" {...props} />; @@ -41,12 +44,35 @@ function Alert(props) { export default function CommentsArea(props) { const { state } = useContext(Store) const [comentarios, setComentarios] = useState([]) + const [totalReviews, setTotalReviews] = useState(0); + const [currPageReviews, setCurrPageReviews] = useState(0); const [gambiarra, setState] = useState(0) const forceUpdate = () => { setState(gambiarra + 1) } const [loginOpen, setLogin] = useState(false) const [successfulLoginOpen, handleSuccessfulLogin] = useState(false) const [signUpOpen, setSignUp] = useState(false) const [isLoading, setIsLoading] = useState(false) + const [snackInfo, setSnackInfo] = useState({ + open: false, + text: '', + severity: '', + color: '' + }); + + function handleSnackInfo(info) { + setSnackInfo({ + ...info + }) + } + + function handleCloseSnack() { + setSnackInfo({ + open: false, + text: '', + severity: '', + color: '', + }) + } const handleSignUp = () => { setSignUp(!signUpOpen) @@ -68,19 +94,42 @@ export default function CommentsArea(props) { handleSuccessfulLogin(false); } - function handleSuccess(data) { + function handleLoadMoreReviews() { + if (comentarios.length !== parseInt(totalReviews)) + setCurrPageReviews((previous) => previous + 1) + else { + const info = { + open: true, + text: 'Não há mais comentários para carregar.', + severity: 'warning', + color: '', + } + handleSnackInfo(info) + } + } + + function handleSuccess(data, headers) { setIsLoading(false) - setComentarios(data.sort((a, b) => a.updated_at > b.updated_at ? -1 : 1)) + setComentarios((previous) => previous.concat(data.sort((a, b) => a.updated_at > b.updated_at ? -1 : 1))) + if (headers.has('X-Total-Count')) + setTotalReviews(headers.get('X-Total-Count')) } useEffect(() => { setIsLoading(true) - const url = `/learning_objects/${props.recursoId}/reviews` + const url = `/learning_objects/${props.recursoId}/reviews?page=${currPageReviews}` getRequest(url, handleSuccess, (error) => { console.log(error); setIsLoading(false) }) - }, [gambiarra]) + }, [gambiarra, currPageReviews]) return ( <React.Fragment> + <SnackBarComponent + snackbarOpen={snackInfo.open} + handleClose={handleCloseSnack} + severity={snackInfo.severity} + text={snackInfo.text} + color={snackInfo.color} + /> <Snackbar open={successfulLoginOpen} autoHideDuration={1000} onClose={toggleSnackbar} anchorOrigin={{ vertical: 'top', horizontal: 'center' }} > @@ -102,7 +151,7 @@ export default function CommentsArea(props) { <Grid container style={{ paddingTop: "20px" }} spacing={1}> <Grid item xs={12} sm={2} style={{ paddingLeft: "15px", paddingRight: "15px" }}> <div style={{ display: 'flex', justifyContent: 'center', alignItems: 'center' }}> - <img src={ state.currentUser.avatar ? apiDomain + state.currentUser.avatar : noAvatar} className="minha-imagem" alt="user avatar" /> + <img src={state.currentUser.avatar ? apiDomain + state.currentUser.avatar : noAvatar} className="minha-imagem" alt="user avatar" /> </div> </Grid> <Grid item xs={12} sm={10}> @@ -135,10 +184,10 @@ export default function CommentsArea(props) { <CircularProgress className="loading" /> </LoadingDiv> : - comentarios.length !== 0 ? + totalReviews !== 0 ? ( <ComentariosBox> - <h3>{comentarios.length} {comentarios.length !== 1 ? 'Relatos' : 'Relato'} sobre o uso do Recurso</h3> + <h3>{totalReviews} {totalReviews !== 1 ? 'Relatos' : 'Relato'} sobre o uso do Recurso</h3> { comentarios.map(comentario => <div className="comentario-template" key={comentario.id}> @@ -162,6 +211,11 @@ export default function CommentsArea(props) { </div> ) } + <div className="load-more"> + <IconButton className="button" onClick={handleLoadMoreReviews}> + <KeyboardArrowDownIcon /> + </IconButton> + </div> </ComentariosBox> ) : @@ -216,6 +270,18 @@ const ComentariosBox = styled.div` padding : 20px 0; border-bottom : 1px solid #f4f4f4; } + + .load-more{ + width: 100%; + display: flex; + flex-direction: row; + justify-content: center; + align-items: center; + } + + .button{ + box-shadow: 0 4px 8px 0 rgba(0,0,0,0.2); + } ` const AoRelatar = styled.div` width : 70%; diff --git a/src/Components/SnackbarComponent.js b/src/Components/SnackbarComponent.js index b0bd36a6..60692e9c 100644 --- a/src/Components/SnackbarComponent.js +++ b/src/Components/SnackbarComponent.js @@ -25,7 +25,7 @@ export default function SnackbarComponent(props) { <Snackbar open={props.snackbarOpen} autoHideDuration={3000} onClose={props.handleClose} anchorOrigin={{ vertical: 'top', horizontal: 'right' }} > - <Alert severity={props.severity} style={props.color ? { backgroundColor: props.color } : { backgroundColor: "#00acc1" }}> + <Alert severity={props.severity}> {props.text} </Alert> </Snackbar> diff --git a/src/env.js b/src/env.js index 7284c427..95815e96 100644 --- a/src/env.js +++ b/src/env.js @@ -17,7 +17,7 @@ You should have received a copy of the GNU Affero General Public License along with Plataforma Integrada MEC. If not, see <http://www.gnu.org/licenses/>.*/ -var apiDomain = 'https://api.portalmectest.c3sl.ufpr.br', +var apiDomain = 'https://api.portalmec.c3sl.ufpr.br', apiVersion = 'v1', apiUrl = apiDomain + '/' + apiVersion; -- GitLab