1- /* eslint-disable sort-keys */
1+ /* eslint-disable max-lines-per-function */
22/* eslint-disable react-hooks/exhaustive-deps */
33import React , { useCallback , useEffect , useState } from 'react' ;
44import Box from '@material-ui/core/Box' ;
@@ -8,7 +8,7 @@ import useMediaQuery from '@material-ui/core/useMediaQuery';
88import { makeStyles , useTheme } from '@material-ui/core/styles' ;
99import axios from 'axios' ;
1010import _ from 'lodash' ;
11-
11+ import { ArrayParam , NumberParam , StringParam , useQueryParam , withDefault } from 'use-query-params' ;
1212import { GetStartedCard , GenericHeaderSection } from '../../components' ;
1313import SearchBar from '../SearchProjects/SearchBar' ;
1414import FAQCard from '../../components/FAQCard' ;
@@ -20,51 +20,71 @@ const useStyles = makeStyles({
2020} ) ;
2121
2222const Faq = ( ) => {
23- const breadCrumbLinks = [
24- { name : 'Home' , href : '/home' } ,
25- { name : 'FAQ' , href : '/about/faq' } ,
26- ] ;
27- const [ data , setData ] = useState ( [ ] ) ;
28- const [ pageNum , setPageNum ] = useState ( 1 ) ;
29- const [ query , setQuery ] = useState ( '' ) ;
30- const [ status , setStatus ] = useState ( 'fetchedFaq' ) ;
31- const [ totalCount , setTotalCount ] = useState ( 0 ) ;
3223 const classes = useStyles ( ) ;
33- const apiUrl = `${ process . env . REACT_APP_API_URL } /api/faqs/` ;
34-
3524 const theme = useTheme ( ) ;
3625 const largeScreen = useMediaQuery ( theme . breakpoints . up ( 'sm' ) , {
3726 noSsr : true ,
3827 } ) ;
28+ const apiUrl = `${ process . env . REACT_APP_API_URL } /api/faqs/` ;
29+ const [ faqs , setFaqs ] = useState ( [ ] ) ;
30+ const [ status , setStatus ] = useState ( 'fetchedFaq' ) ;
31+ const [ totalCount , setTotalCount ] = useState ( 0 ) ;
32+ const [ expandedFaqs , setExpandedFaqs ] = useQueryParam (
33+ 'opened' ,
34+ withDefault ( ArrayParam , [ ] )
35+ ) ;
36+ const [ pageNum , setPageNum ] = useQueryParam (
37+ 'page' ,
38+ withDefault ( NumberParam , 1 )
39+ ) ;
40+ const [ query , setQuery ] = useQueryParam (
41+ 'query' ,
42+ withDefault ( StringParam , '' )
43+ ) ;
3944
40- const getFAQData = async ( currentQuery , resetPageNum ) => {
45+ const breadCrumbLinks = [
46+ { name : 'Home' , href : '/home' } ,
47+ { name : 'FAQ' , href : '/about/faq' } ,
48+ ] ;
49+
50+ const getFaqData = async ( currentQuery , resetState ) => {
4151 const params = {
42- page : resetPageNum ? 1 : pageNum ,
52+ page : resetState ? 1 : pageNum ,
4353 page_size : largeScreen ? 10 : 5 ,
4454 search : currentQuery ,
4555 } ;
46- // reset pagination current page to 1 in certain cases such as new search query input
47- if ( resetPageNum ) {
56+ if ( resetState ) {
57+ setExpandedFaqs ( [ ] ) ;
4858 setPageNum ( 1 ) ;
4959 }
5060 const res = await axios . get ( apiUrl , { params : params } ) ;
51- setData ( res . data . results ) ;
61+ setFaqs ( res . data . results ) ;
5262 setTotalCount ( res . data . count ) ;
5363 setStatus ( params . search ? 'fetchedSearch' : 'fetchedFaq' ) ;
5464 } ;
5565
5666 const debounce = useCallback (
5767 _ . debounce ( ( value ) => {
58- getFAQData ( value , true ) ;
68+ getFaqData ( value , true ) ;
5969 } , 300 ) ,
6070 [ ]
6171 ) ;
6272
6373 useEffect ( ( ) => {
64- getFAQData ( query , false ) ;
65- // eslint-disable-next-line react-hooks/exhaustive-deps
74+ getFaqData ( query , largeScreen ) ;
6675 } , [ pageNum , largeScreen ] ) ;
6776
77+ const handleFaqClick = ( id ) => {
78+ const expanded = [ ...expandedFaqs ] ;
79+ const idx = expanded . indexOf ( id . toString ( ) ) ;
80+ if ( idx > - 1 ) {
81+ expanded . splice ( idx , 1 ) ;
82+ } else {
83+ expanded . push ( id . toString ( ) ) ;
84+ }
85+ setExpandedFaqs ( expanded ) ;
86+ } ;
87+
6888 const handleInput = ( event ) => {
6989 setQuery ( event . target . value ) ;
7090 debounce ( event . target . value ) ;
@@ -87,17 +107,20 @@ const Faq = () => {
87107 dataCy = 'search-faq'
88108 onInput = { handleInput }
89109 placeholder = 'Search the Civic Tech Index'
110+ value = { query }
90111 />
91112 </ Grid >
92113 </ Grid >
93114 </ GenericHeaderSection >
94115 </ Container >
95116 < FAQCard
96- title = { status === 'fetchedFaq' ? 'Top Asked Questions' : `Search results (${ totalCount } )` }
97- faqs = { data }
98- pages = { Math . ceil ( totalCount / ( largeScreen ? 10 : 5 ) ) }
99117 currentPageNum = { pageNum }
118+ expandedFaqs = { expandedFaqs }
119+ faqs = { faqs }
120+ onFaqClick = { handleFaqClick }
100121 onPageChange = { handlePageNumChange }
122+ pages = { Math . ceil ( totalCount / ( largeScreen ? 10 : 5 ) ) }
123+ title = { status === 'fetchedFaq' ? 'Top Asked Questions' : `Search results (${ totalCount } )` }
101124 />
102125 < GetStartedCard
103126 headerTitle = 'Can’t find an answer?'
@@ -107,5 +130,4 @@ const Faq = () => {
107130 </ Box >
108131 ) ;
109132} ;
110-
111133export default Faq ;
0 commit comments