No Description

EditGrades.js 9.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295
  1. import React, {useState, useEffect} from 'react';
  2. import { FlatList, StatusBar, StyleSheet, Text, TouchableOpacity, TextInput, View, Button, ActivityIndicator, Alert, ScrollView, RefreshControl } from "react-native";
  3. import axios from 'axios'
  4. import * as SecureStore from 'expo-secure-store';
  5. import Modal from 'react-native-modal';
  6. import {Picker} from '@react-native-community/picker';
  7. const Item = ({ item, onPress, style }) => (
  8. <TouchableOpacity onPress={onPress} style={[styles.item, style]}>
  9. <Text style={styles.title}>{`${item.code}: ${item.grade}`}</Text>
  10. </TouchableOpacity>
  11. );
  12. // separates results, taken from https://stackoverflow.com/questions/60350768/how-to-make-search-bar-with-dropdown-list-in-react-native
  13. const renderSeparator = () => {
  14. return (
  15. <View
  16. style={{
  17. height: 1,
  18. width: '100%',
  19. backgroundColor: '#CED0CE',
  20. }}
  21. />
  22. );
  23. };
  24. const CurrentCourses = () =>{
  25. const [courses, setCourses] = useState(null)
  26. const [refreshing, setRefreshing] = useState(false)
  27. const [selectedId, setSelectedId] = useState(null); // course_id
  28. const [animating, setAnimating] = useState(false)
  29. const [modalVisible, setModalVisible] = useState(false)
  30. const [year, setYear] = useState(1)
  31. const [semester, setSemester] = useState(1)
  32. const [grade, setGrade] = useState('A')
  33. const toggle = ()=>{
  34. setModalVisible(!modalVisible)
  35. setSelectedId(null)
  36. }
  37. const getCoursesBySemester = async()=>{
  38. const token = await SecureStore.getItemAsync('token')
  39. let id = await SecureStore.getItemAsync('id')
  40. let user_id = parseInt(id)
  41. console.log(user_id)
  42. try {
  43. let response = await axios(`http://481cb6e289f9.ngrok.io/api/get_all_courses_by_semester?user_id=${user_id}&year=${year}&semestre=${semester}`, {
  44. method: 'GET',
  45. headers: {
  46. 'content-type': 'application/json',
  47. Authorization: `Token ${token}`
  48. }
  49. })
  50. // console.log(response.data.list)
  51. setCourses(response.data.list)
  52. } catch(error){
  53. console.log(error)
  54. }
  55. }
  56. const deleteOneCourse = async()=>{
  57. const token = await SecureStore.getItemAsync('token')
  58. let id = await SecureStore.getItemAsync('id')
  59. let user_id = parseInt(id)
  60. try {
  61. let response = await axios(`http://481cb6e289f9.ngrok.io/api/delete_course`, {
  62. method: 'DELETE',
  63. headers: {
  64. 'content-type': 'application/json',
  65. Authorization: `Token ${token}`
  66. },
  67. data:{
  68. user_id: user_id,
  69. course_id: selectedId,
  70. year: year,
  71. semestre: semester
  72. }
  73. })
  74. setAnimating(true)
  75. // after 3 seconds, the courses, the modal and the activity indicator will disappear
  76. setTimeout(()=>{
  77. setAnimating(false)
  78. setModalVisible(false)
  79. setSelectedId(null)
  80. }, 3000)
  81. setTimeout(()=>{
  82. Alert.alert(response.data.msg)
  83. }, 5000)
  84. getCoursesBySemester() // get current courses again
  85. } catch(error){
  86. console.log(error)
  87. }
  88. }
  89. const updateGrade = async()=>{
  90. const token = await SecureStore.getItemAsync('token')
  91. let id = await SecureStore.getItemAsync('id')
  92. let user_id = parseInt(id)
  93. console.log(semester)
  94. console.log(year)
  95. try {
  96. let response = await axios(`http://481cb6e289f9.ngrok.io/api/update_grade_and_gpa`, {
  97. method: 'PATCH',
  98. headers: {
  99. 'content-type': 'application/json',
  100. Authorization: `Token ${token}`
  101. },
  102. data:{
  103. user_id: user_id,
  104. course_id: selectedId,
  105. year: year,
  106. semestre: semester,
  107. grade: grade
  108. }
  109. })
  110. setAnimating(true)
  111. // after 3 seconds, the courses, the modal and the activity indicator will disappear
  112. setTimeout(()=>{
  113. setAnimating(false)
  114. setModalVisible(false)
  115. setSelectedId(null)
  116. }, 3000)
  117. setTimeout(()=>{
  118. Alert.alert(response.data.msg)
  119. }, 5000)
  120. getCoursesBySemester() // get current courses again
  121. } catch(error){
  122. console.log(error)
  123. }
  124. }
  125. const onRefresh = React.useCallback(async ()=>{
  126. setRefreshing(true)
  127. getCoursesBySemester()
  128. setRefreshing(false)
  129. }, [refreshing])
  130. useEffect(()=>{
  131. getCoursesBySemester()
  132. },[year, semester])
  133. const renderItem = ({ item }) => {
  134. const backgroundColor = item.course_id === selectedId ? "#e60505" : "#fafbfc";
  135. return (
  136. <Item
  137. item={item}
  138. onPress={() => {
  139. setModalVisible(true)
  140. setSelectedId(item.course_id)
  141. setYear(item.year)
  142. setSemester(item.semestre)
  143. setGrade(item.grade)
  144. }}
  145. style={{ backgroundColor }}
  146. />
  147. );
  148. };
  149. // if student does not have courses currently, return this
  150. if(courses === null || courses.length === 0){
  151. return (
  152. <ScrollView
  153. refreshControl={<RefreshControl refreshing={refreshing} onRefresh={onRefresh}/>}
  154. >
  155. <Text>No tienes cursos</Text>
  156. </ScrollView>
  157. )
  158. }
  159. // console.log(grade)
  160. return (
  161. <View style={styles.container}>
  162. <FlatList
  163. data={courses}
  164. renderItem={renderItem}
  165. keyExtractor={(item) => item.course_id.toString()}
  166. extraData={selectedId}
  167. ItemSeparatorComponent={renderSeparator}
  168. refreshControl={<RefreshControl refreshing={refreshing} onRefresh={onRefresh}/>}
  169. />
  170. <Modal isVisible={modalVisible}
  171. >
  172. <View style={styles.modalItem}>
  173. <Button title= "Update grade" onPress={updateGrade} />
  174. <Picker
  175. selectedValue={grade}
  176. style={{ width: 50}}
  177. onValueChange={(itemValue, itemIndex) => setGrade(itemValue) }>
  178. <Picker.Item label="A" value="A" />
  179. <Picker.Item label="B" value="B" />
  180. <Picker.Item label="C" value="C" />
  181. <Picker.Item label="D" value="D" />
  182. <Picker.Item label="F" value="F" />
  183. </Picker>
  184. <ActivityIndicator size="small" color="0000ff" animating={animating}/>
  185. <Button title="Delete Course" onPress={deleteOneCourse}/>
  186. <Button title="Close" onPress={toggle}/>
  187. </View>
  188. </Modal>
  189. <View style={{flexDirection: 'row'}}>
  190. <View style={{margin: 8}}>
  191. <Text>Year</Text>
  192. <Picker
  193. selectedValue={year}
  194. style={{ width: 50}}
  195. onValueChange={(itemValue, itemIndex) => setYear(itemValue) }>
  196. <Picker.Item label="1" value="1" />
  197. <Picker.Item label="2" value="2" />
  198. <Picker.Item label="3" value="3" />
  199. <Picker.Item label="4" value="4" />
  200. <Picker.Item label="5" value="5" />
  201. <Picker.Item label="6" value="6" />
  202. </Picker>
  203. </View>
  204. <View style={{margin: 8}}>
  205. <Text>Semester</Text>
  206. <Picker
  207. selectedValue={semester}
  208. style={{ width: 50}}
  209. onValueChange={(itemValue, itemIndex) => setSemester(itemValue) }>
  210. <Picker.Item label="1" value="1" />
  211. <Picker.Item label="2" value="2" />
  212. <Picker.Item label="3" value="3" />
  213. </Picker>
  214. </View>
  215. </View>
  216. </View>
  217. );
  218. }
  219. export default CurrentCourses
  220. const styles = StyleSheet.create({
  221. container: {
  222. flex: 1,
  223. marginTop: StatusBar.currentHeight || 0,
  224. },
  225. item: {
  226. padding: 10,
  227. marginVertical: 8,
  228. marginHorizontal: 16,
  229. },
  230. title: {
  231. fontSize: 15,
  232. },
  233. searchBar: {
  234. height: 40,
  235. borderColor: '#000',
  236. borderWidth: 1
  237. },
  238. modalItem: {
  239. // width: '30%', // is 30% of container width
  240. margin: 60, // 300
  241. backgroundColor: 'white',
  242. borderRadius:20,
  243. height: 340
  244. },
  245. course_info: {
  246. fontWeight: 'bold',
  247. fontSize: 13
  248. }
  249. });