简体   繁体   中英

Modal not updating to new item in array,firebase/react native state

my current issue with my react native app is that when a user wants to open a lesson (from the lessons array with each object being a lesson with a title,description,img url etc)to make it bigger through a modal, its state does not update. What i Mean by this is that the books title,description,and other attributes won't change if you press on a new lesson. What would be the solution to this?

export default function Learn() {
      const [modalVisible, setModalVisible] = useState(false);
      const [lessons,setLessons] = useState()
      useEffect(() => {
        async function data() {
          try {
            let todos = []
            const querySnapshot = await getDocs(collection(db, "lessons"));
          querySnapshot.forEach((doc) => {
            todos.push(doc.data())
          });
          setLessons(todos)
          console.log(lessons)
          }
          catch(E) {
            alert(E)
          }
        }
    
        data()
        
      }, [])
      
      return (
        <View style={learnStyle.maincont}>
          <View>
              <Text style={{fontSize:28,marginTop:20}}>Courses</Text>
             <ScrollView style={{paddingBottom:200}}>
              {lessons && lessons.map((doc,key) => 
              <>
             <Modal
    animationType="slide"
    transparent={true}
    visible={modalVisible}
    onRequestClose={() => {
      Alert.alert("Modal has been closed.");
      setModalVisible(!modalVisible);
    }}
  >
    <View style={styles.centeredView}>
      <View style={styles.modalView}>
        <Image source={{
          uri:doc.imgURL
        }} style={{width:"100%",height:300}}/>
        <Text style={{fontWeight:"700",fontSize:25}}>{doc.title}</Text>
        <Text style={{fontWeight:"700",fontSize:16}}>{doc.desc}</Text>
        <Pressable
          style={[styles.button, styles.buttonClose]}
          onPress={() => setModalVisible(!modalVisible)}
        >
          <Text style={styles.textStyle}>Hide Modal</Text>
        </Pressable>
      </View>
    </View>
  </Modal>
          <LessonCard setModalVisible={setModalVisible} title={doc.title} desc={doc.desc} img1={doc.imgURL} modalVisible={modalVisible}/>
              </>
              )}
             <View style={{height:600,width:"100%"}}></View>
             </ScrollView>
              </View>
        </View>
      )
    }

What it looks like: 按模态之前的样子 在你按下模态之后

**image 1 is before you press the modal and the 2nd one is after **the main issue though is that if you press cancel and press on another lesson the modal that opens has the the same state(title,imgurl,anddesc) as the first lesson and does not change.

The problem is that you create a lot of modal windows through the map function, I suggest making one window and passing the key as a parameter and using it to search for a specific array of data that is shown to the user (photo, title, etc.)

The problem is that all 3 Modal s are controlled by the one state variable. So when the code sets modalVisible to true , all 3 modals are being opened at once.

You can fix this in a few ways, but a simple way would be to move the Modal and its state into the LessonCard component. This way each modal will have its own state that's only opened by its card. So the loop in Learn will just be:

 {lessons && lessons.map((doc,key) => (
     <LessonCard lesson={doc} key={key} />
 )}

Adding to address question in comments

LessonCard should not accept setModalVisible or modalVisible props. The

const [modalVisible, setModalVisible] = useState(false);

should be inside LessonCard , not Learn . That way each Card/Modal pair will have its own state.

Additionally, although React wants you to pass the key into LessonCard in the map function, LessonCard should not actually use the key prop for anything. See https://reactjs.org/docs/lists-and-keys.html#extracting-components-with-keys

So, the LessonCard declaration should just be something like

export default function LessonCard({lesson}) {

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM