1+ import React , { ReactElement , useEffect , useState } from 'react' ;
2+ import { StyleSheet , Text , Image , View , TouchableHighlight , SafeAreaView , Button , Alert , Platform , Dimensions , TextInput , ScrollView , Pressable } from 'react-native'
3+ import { Feather } from '@expo/vector-icons' ;
4+ import { AntDesign } from '@expo/vector-icons' ;
5+ import { Ionicons } from '@expo/vector-icons' ;
6+ import DoctorComponent from '@/components/DoctorComponent' ;
7+ import { FontAwesome } from '@expo/vector-icons' ;
8+ import { SvgXml } from "react-native-svg"
9+ import { WhiteHeart } from '@/components/UI/icons/WhiteHeart' ;
10+ import { star } from '@/assets/icons/star' ;
11+ import { search } from '@/assets/icons/search' ;
12+ import { more } from '@/assets/icons/more' ;
13+ import { leftArrow } from '@/assets/icons/left' ;
14+ import data from "../../doctors.json"
15+ import HeaderComponent from '@/components/HeaderComponent' ;
16+ import SearchComponent from '@/components/SearchComponent' ;
17+ import FoundDoctorCount from '@/components/FoundDoctorCount' ;
18+ import NofoundComponent from '@/components/NofoundComponent' ;
19+ import RemovefavoritePopup from '@/components/RemovefavoritePopup' ;
20+ import FilterPopup from '@/components/FilterSearchComponent' ;
21+ import { StatusBar } from 'expo-status-bar' ;
22+ import NotFoundScreen from '@/app/+not-found' ;
23+ import { ThemeContext } from '@/ctx/ThemeContext' ;
24+ import { useContext } from 'react' ;
25+ import { supabase } from '@/lib/supabase' ;
26+
27+
28+
29+ const tableName = 'doctors'
30+
31+
32+
33+
34+ interface imageMapProp {
35+ [ key :string ] :ReturnType < typeof require >
36+ }
37+
38+ const imageMap :imageMapProp = {
39+ 'doctor1.png' : require ( "../../../assets/images/Doctors/doctor1.png" ) ,
40+ 'doctor2.png' : require ( "../../../assets/images/Doctors/doctor2.png" ) ,
41+ 'doctor3.png' : require ( "../../../assets/images/Doctors/doctor3.png" ) ,
42+ 'doctor4.png' : require ( "../../../assets/images/Doctors/doctor4.png" ) ,
43+ 'doctor5.png' :require ( "../../../assets/images/Doctors/doctor5.png" )
44+
45+ }
46+ interface iconMappingProp {
47+ [ key :string ] :ReactElement
48+ }
49+
50+
51+ interface Doctor {
52+ id : number ,
53+ first_name : string ,
54+ last_name : string ,
55+ hospital : string ,
56+ rate : string ,
57+ review : string ,
58+ specialization : string ,
59+ about :string
60+ }
61+ interface categoryProp {
62+ name : string ,
63+ Doctors :Doctor [ ]
64+ }
65+
66+ export const iconMapping :iconMappingProp = {
67+ heart : < SvgXml xml = { WhiteHeart } /> ,
68+ star : < SvgXml xml = { star } /> ,
69+ }
70+
71+
72+
73+ function DoctorScreen ( ) {
74+ const [ showSearch , setShowSearch ] = useState < boolean > ( false )
75+ const [ searchTerm , setSearchTerm ] = useState < string > ( '' )
76+ const [ selectedCategory , setSelectedCategory ] = useState ( data . categories [ 0 ] )
77+ const [ showpopUp , setShowPopup ] = useState ( false )
78+ const [ selectedDoctor , setSelectedDoctor ] = useState ( )
79+ const [ showFilter , setShowfilter ] = useState ( false )
80+ const [ doctors , setDoctors ] = useState < Doctor [ ] > ( [ ] )
81+ const { theme, changeTheme } = useContext ( ThemeContext )
82+ const containerStyle = theme === "dark" ? styles . outerDark : styles . outerLight
83+ const scrollbackColor = theme === "dark" ? styles . scrollDark : styles . scrollLight
84+
85+ useEffect ( ( ) => {
86+ async function fetchData ( ) {
87+ const { data, error } = await supabase . from ( tableName ) . select ( '*' ) ;
88+
89+ if ( error ) {
90+ console . error ( 'Error fetching data:' , error ) ;
91+ return ;
92+ }
93+ setDoctors ( data )
94+
95+ console . log ( 'Fetched data:' , data ) ;
96+ }
97+
98+ fetchData ( ) ;
99+ } , [ ] )
100+
101+ const handleSearchPressed = ( ) => {
102+ setShowSearch ( true )
103+ }
104+ const handleSearchSubmit = ( text : string ) => {
105+ setSearchTerm ( text . toLowerCase ( ) )
106+ }
107+
108+ const handleFilter = ( ) => {
109+ setShowfilter ( true )
110+ }
111+ const handleRemove = ( doctor :any ) => {
112+ setSelectedDoctor ( doctor )
113+
114+ setShowPopup ( true )
115+ }
116+
117+ const filteredDoctors = searchTerm . length > 0 ? doctors . filter ( doctor => doctor . last_name . toLowerCase ( ) . includes ( searchTerm ) ) :doctors
118+ return (
119+ < SafeAreaView style = { [ styles . container , containerStyle ] } >
120+ < StatusBar style = { theme === "dark" ? "light" : "dark" } />
121+ < View >
122+
123+ < View style = { [ styles . upper , containerStyle ] } >
124+ {
125+ ! showSearch ? (
126+ < HeaderComponent
127+ onSearchPressed = { handleSearchPressed }
128+ headerText = "Top Doctor"
129+
130+ />
131+ ) : (
132+
133+ < SearchComponent
134+ onSearchSubmit = { handleSearchSubmit }
135+ filterAction = { handleFilter }
136+
137+
138+ />
139+ )
140+ }
141+ </ View >
142+ < View style = { [ styles . categoryBtnView , containerStyle ] } >
143+ < ScrollView horizontal = { true } showsHorizontalScrollIndicator = { false } style = { styles . categoryScroll }
144+ contentContainerStyle = { {
145+ flexDirection : "row" ,
146+ justifyContent : "space-between" ,
147+ alignItems :'center'
148+
149+ } } >
150+
151+ { data . categories . map ( ( category , index ) =>
152+ < Pressable key = { index } style = { [ styles . categoryBtn ,
153+ selectedCategory === category ? styles . firstCategoryBtn : { } ,
154+ ] } >
155+
156+ < Text style = { [
157+ styles . categoryBtnText ,
158+ selectedCategory === category ? styles . firstCategoryBtnText : { } ,
159+ ] } > { category . name } </ Text >
160+
161+ </ Pressable >
162+ ) }
163+ </ ScrollView >
164+
165+ </ View >
166+ < View style = { styles . foundDoctorView } >
167+ { showSearch && (
168+ < FoundDoctorCount count = { filteredDoctors . length } />
169+ ) }
170+ </ View >
171+ < View >
172+ < ScrollView
173+ showsVerticalScrollIndicator = { false }
174+ style = { [ styles . scroll , scrollbackColor ] }
175+ contentContainerStyle = { {
176+ justifyContent : "center" ,
177+ // alignItems: 'center',
178+ paddingBottom : 150 ,
179+ paddingTop :20
180+ } }
181+ >
182+ { filteredDoctors . length > 0 ? (
183+
184+ filteredDoctors . map ( ( doctor : any , index : any ) =>
185+
186+ < View key = { index } style = { styles . componentView } >
187+ < DoctorComponent
188+
189+ imageSource = { { uri :doctor . image } }
190+ name = { `${ doctor . first_name } ${ doctor . last_name } ` }
191+ iconComponent = { < SvgXml xml = { WhiteHeart } /> }
192+ professionalTitle = { doctor . specialization }
193+ hospital = { doctor . hospital }
194+ star = { < SvgXml xml = { star } /> }
195+ review = { doctor . review }
196+ rate = { doctor . rate }
197+ remove = { ( ) => handleRemove ( doctor ) }
198+
199+ />
200+ </ View >
201+
202+ )
203+
204+ ) : (
205+ < NofoundComponent />
206+ ) }
207+
208+
209+ </ ScrollView >
210+
211+ </ View >
212+
213+
214+
215+ </ View >
216+ < RemovefavoritePopup
217+ cancel = { ( ) => setShowPopup ( false ) }
218+ visible = { showpopUp }
219+ onClose = { ( ) => setShowPopup ( false ) }
220+ doctor = { selectedDoctor }
221+
222+
223+ />
224+ < FilterPopup
225+ cancel = { ( ) => setShowfilter ( false ) }
226+ visible = { showFilter }
227+ onClose = { ( ) => setShowfilter ( false ) }
228+
229+
230+
231+ />
232+
233+
234+
235+ </ SafeAreaView >
236+
237+ ) ;
238+ }
239+
240+ export default DoctorScreen ;
241+
242+ const styles = StyleSheet . create ( {
243+ container : {
244+ flex : 1 ,
245+ zIndex :1
246+ } ,
247+ outerDark : {
248+ backgroundColor :"#181A20"
249+
250+ } ,
251+ outerLight : {
252+ backgroundColor : "white" ,
253+
254+ } ,
255+ upper : {
256+ display : "flex" ,
257+ flexDirection : 'row' ,
258+ justifyContent : "center" ,
259+ alignItems : "center" ,
260+ width :"100%" ,
261+ marginBottom : "7%" ,
262+ marginTop : "18%" ,
263+ } ,
264+ foundDoctorView : {
265+ width : "100%" ,
266+ display : "flex" ,
267+ flexDirection : 'row' ,
268+ justifyContent : "center" ,
269+ alignItems : "center"
270+ } ,
271+ searchComponent : {
272+
273+ } ,
274+ upperInner : {
275+ width : "95%" ,
276+ display : "flex" ,
277+ flexDirection : 'row' ,
278+ justifyContent : "space-between" ,
279+ alignItems : "center" ,
280+ } ,
281+ upperLeft : {
282+ display : "flex" ,
283+ flexDirection : "row" ,
284+ justifyContent : 'space-between' ,
285+ width : "70%" ,
286+ height :"100%" ,
287+ } ,
288+ categoryScroll : {
289+
290+ } ,
291+ categoryBtnView : {
292+ display :"flex" ,
293+ flexDirection : "row" ,
294+ alignItems : 'center' ,
295+ marginBottom : "5%" ,
296+ backgroundColor : "white" ,
297+ } ,
298+ categoryBtn : {
299+ borderWidth : 2 ,
300+ borderColor : "#246BFD" ,
301+ height : 40 ,
302+ paddingHorizontal : 20 ,
303+ paddingVertical :7 ,
304+ borderRadius : 20 ,
305+ display : "flex" ,
306+ flexDirection : "row" ,
307+ justifyContent : "center" ,
308+ alignItems : "center" ,
309+ marginRight : 8 ,
310+ marginLeft :10
311+ } ,
312+ firstCategoryBtn : {
313+ backgroundColor : "#246BFD"
314+ } ,
315+ firstCategoryBtnText : {
316+ color :"white"
317+ } ,
318+ categoryBtnText : {
319+ color : "#246BFD" ,
320+ fontSize :16
321+ } ,
322+ body : {
323+ width : "98%" ,
324+ backgroundColor :"#F7F7F7" ,
325+ } ,
326+ scroll : {
327+ width : "100%" ,
328+ height : "100%" ,
329+ zIndex : 1 ,
330+ } ,
331+ scrollDark : {
332+ backgroundColor :"#181A20"
333+
334+ } ,
335+ scrollLight : {
336+ backgroundColor : "#F7F7F7"
337+
338+ } ,
339+ searchView : {
340+ display : "flex" ,
341+ flexDirection : 'row' ,
342+ justifyContent : "center" ,
343+ alignItems : "center" ,
344+ } ,
345+ moreOuter : {
346+ display : "flex" ,
347+ flexDirection : 'row' ,
348+ justifyContent : "center" ,
349+ alignItems : "center" ,
350+ } ,
351+ Headstyle : {
352+ color : "#212121" ,
353+ fontWeight : "bold" ,
354+ fontSize :20
355+ } ,
356+ NotificationView : {
357+ width :"80%"
358+ } ,
359+ componentView : {
360+ marginBottom : "5%" ,
361+ width : "100%" ,
362+ height :150 ,
363+ display : "flex" ,
364+ flexDirection : 'row' ,
365+ justifyContent : "center" ,
366+ alignItems : "center" ,
367+ } ,
368+ rightView : {
369+ display : "flex" ,
370+ flexDirection : "row" ,
371+ justifyContent : 'space-between' ,
372+ width :"25%"
373+ } ,
374+
375+
376+ } )
0 commit comments