/** * PWA Install Composable * Handles PWA installation prompting and detection */ export const usePWAInstall = () => { const deferredPrompt = ref(null) const canInstall = ref(false) const isInstalled = ref(false) // Check if already installed const checkInstalled = () => { // Check if running as standalone PWA if (window.matchMedia('(display-mode: standalone)').matches) { isInstalled.value = true return true } // Check for iOS standalone if ((window.navigator as any).standalone === true) { isInstalled.value = true return true } return false } // Listen for install prompt const setupInstallPrompt = () => { if (process.client) { // Check if already installed if (checkInstalled()) { return } window.addEventListener('beforeinstallprompt', (e) => { e.preventDefault() deferredPrompt.value = e canInstall.value = true console.log('[PWA] Install prompt available') }) window.addEventListener('appinstalled', () => { isInstalled.value = true canInstall.value = false deferredPrompt.value = null console.log('[PWA] App installed successfully') }) } } // Show install prompt const promptInstall = async () => { if (!deferredPrompt.value) { console.warn('[PWA] Install prompt not available') return false } deferredPrompt.value.prompt() const { outcome } = await deferredPrompt.value.userChoice console.log('[PWA] User choice:', outcome) if (outcome === 'accepted') { deferredPrompt.value = null canInstall.value = false return true } return false } // Initialize on mount onMounted(() => { setupInstallPrompt() }) return { canInstall: readonly(canInstall), isInstalled: readonly(isInstalled), promptInstall } }