feat: close modals with browser back button on mobile (#257)
* feat: close modals with browser back button on mobile Create reusable useModalHistory hook that pushes history state when a modal opens and listens for popstate to close it. Apply to ReportModal, ClearMissedConfirm, ExportModal, ImportConfirm, and all modals using ConfirmModal/ShareDialog/Auth/ExportModal base components. Escape key handling was already in place for desktop. Closes #253 * fix: update tests for renamed button labels and missing useModalHistory mock
This commit is contained in:
@@ -8,6 +8,7 @@ export type { UseMedicationFormReturn } from "./useMedicationForm";
|
||||
export { defaultBlister, defaultForm, useMedicationForm } from "./useMedicationForm";
|
||||
export type { UseMedicationsReturn } from "./useMedications";
|
||||
export { useMedications } from "./useMedications";
|
||||
export { useModalHistory } from "./useModalHistory";
|
||||
export type { UseRefillReturn } from "./useRefill";
|
||||
export { useRefill } from "./useRefill";
|
||||
export type { Settings, UseSettingsReturn } from "./useSettings";
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
import { useEffect, useRef } from "react";
|
||||
|
||||
/**
|
||||
* Push a history entry when a modal opens so the browser back button closes it.
|
||||
* On popstate (back), calls `onClose` to dismiss the modal.
|
||||
*/
|
||||
export function useModalHistory(isOpen: boolean, modalKey: string, onClose: () => void) {
|
||||
const pushedRef = useRef(false);
|
||||
|
||||
useEffect(() => {
|
||||
if (isOpen) {
|
||||
window.history.pushState({ modal: modalKey }, "");
|
||||
pushedRef.current = true;
|
||||
} else if (pushedRef.current) {
|
||||
pushedRef.current = false;
|
||||
}
|
||||
}, [isOpen, modalKey]);
|
||||
|
||||
useEffect(() => {
|
||||
if (!isOpen) return;
|
||||
|
||||
const handlePopState = () => {
|
||||
if (pushedRef.current) {
|
||||
pushedRef.current = false;
|
||||
onClose();
|
||||
}
|
||||
};
|
||||
|
||||
window.addEventListener("popstate", handlePopState);
|
||||
return () => window.removeEventListener("popstate", handlePopState);
|
||||
}, [isOpen, onClose]);
|
||||
}
|
||||
Reference in New Issue
Block a user