Ionic 5:如何以编程方式关闭 ion-select

Ionic 5 : How to close ion-select programmatically

在我的 ionic react 应用程序中,我在表单中使用 IonSelect。当下拉菜单打开时,我需要在硬件后退按钮事件侦听器调用中以编程方式关闭 IonSelect 下拉菜单。这是代码

export const SingleSelection: React.FC = () => { 
   const [gender, setGender] = useState<string>();
   
    useEffect(() => {
     
      document.addEventListener('ionBackButton', (ev: any) => {
         ev.detail.register(1000, async (processNextHandler: any) => {
           console.log('Handler B was called!');
    
           processNextHandler();
         });
      });
      return () => {
        console.log("use effect return");
      }
   }, [])

   return (
     <IonPage>
        <IonContent>
          <IonItem>
              <IonLabel>Gender</IonLabel>
              <IonSelect value={gender} placeholder="Select One" onIonChange={e => setGender(e.detail.value)}>
                 <IonSelectOption value="female">Female</IonSelectOption>
                 <IonSelectOption value="male">Male</IonSelectOption>
               </IonSelect>
           </IonItem>
         </IonContent>
      </IonPage>   
    );
};

更新:[已解决]: 这是我更新的带有模态的完整代码。在硬件后退按钮事件侦听器方法中,首先关闭离子 select(如果它保持打开状态),然后关闭模式

const ModalExample: React.FC = () => {
    const [showModal, setShowModal] = useState(false);
    const [gender, setGender] = useState<string>();

    useEffect(() => {
        document.addEventListener('ionBackButton', (ev: any) => {
            ev.detail.register(1000, async (processNextHandler: any) => {
                console.log('Handler B was called!');
                try {
                    console.log("close ion select");
                    const alert = await alertController.getTop();
                    if (alert) {
                        alert.dismiss();
                        return;
                    }
                    console.log("close modal")
                    const element = await modalController.getTop();
                    if (element) {
                        //element.dismiss();
                        setShowModal(false)
                        return;
                    }
                } catch (error) {
                    console.log(error);
                }
                processNextHandler();
            });
        });
        return () => {
            console.log("use effect return");
        }
    }, [])

    return (
        <IonContent>
            <IonModal isOpen={showModal} cssClass='my-custom-class'>
                <p>This is modal content</p>
                <IonItem>
                    <IonLabel>Gender</IonLabel>
                    <IonSelect value={gender} placeholder="Select One" onIonChange={e => setGender(e.detail.value)}>
                        <IonSelectOption value="female">Female</IonSelectOption>
                        <IonSelectOption value="male">Male</IonSelectOption>
                    </IonSelect>
                </IonItem>
                <IonButton onClick={() => setShowModal(false)}>Close Modal</IonButton>
            </IonModal>
            <IonButton onClick={() => setShowModal(true)}>Show Modal</IonButton>
        </IonContent>
    );
};

尽管按下硬件后退按钮会自动关闭 IonSelect 下拉菜单。如果这对你不起作用,这里有一个使用 useRef 钩子的解决方法:

export const SingleSelection: React.FC = () => { 
    const [gender, setGender] = useState<string>();
    const selectRef = useRef<any>(null);

    useEffect(() => {
     
      document.addEventListener('ionBackButton', (ev: any) => {
         ev.preventDefault(); // TO PREVENT THE CLOSING OF MODAL
         ev.detail.register(1000, async (processNextHandler: any) => {
           console.log('Handler B was called!');
           selectRef.current.close() // SEE HERE


           // HERE YOU CAN NOW CLOSE THE MODAL

           processNextHandler();
         });
      });
      return () => {
        console.log("use effect return");
      }
   }, [])

    return (
         ...
         <IonSelect ref={(ref: any) => selectRef.current = ref} value={gender} placeholder="Select One" onIonChange={e => setGender(e.detail.value)}>
            <IonSelectOption value="female">Female</IonSelectOption>
            <IonSelectOption value="male">Male</IonSelectOption>
         </IonSelect>
         ....
    
        );

};

我找到了解决办法。使用 alertController IonSelect 下拉菜单可以通过编程方式关闭,

import { alertController } from "@ionic/core";
.....

useEffect(() => {

    document.addEventListener('ionBackButton', (ev: any) => {
      ev.detail.register(1005, async (processNextHandler: any) => {
        console.log('Handler D was called!');
        const alert = await alertController.getTop();
        console.log(alert);
        if (alert) {
          alert.dismiss();
          return;
        }
        processNextHandler();
      });
    });
    return () => {
      console.log("use effect return");
    }
  }, [])