mirror of
https://github.com/R0m1k3/Socialflow.git
synced 2026-10-22 22:48:09 +02:00
Implémentation d'un système responsive robuste avec détection automatique du type d'appareil et switch transparent entre versions desktop et mobile. ## Nouvelles fonctionnalités ### 1. Hook de détection mobile (useIsMobile) - Détection via media query (max-width: 768px) - Validation supplémentaire via user agent - Support des changements dynamiques de taille d'écran - Hook useDeviceType pour détection granulaire (mobile/tablet/desktop) ### 2. Composant ResponsiveRoute - Switch automatique entre versions desktop/mobile - Lazy loading des composants pour performances optimales - Factory function createResponsiveRoute pour création facile - Suspense avec fallback de chargement ### 3. Pages mobiles optimisées (10 pages) **Pages créées :** - dashboard.tsx - Tableau de bord - new-post.tsx - Création de posts (interface tactile optimisée) - calendar.tsx - Calendrier - media.tsx - Bibliothèque de médias - image-editor.tsx - Éditeur d'images - pages.tsx - Gestion des pages sociales - ai.tsx - Assistant IA (admin) - settings.tsx - Paramètres (admin) - users-admin.tsx - Gestion utilisateurs (admin) - sql.tsx - Administration SQL (admin) **Optimisations mobiles appliquées :** - Layout en colonne unique (au lieu de multi-colonnes) - Boutons tactiles : min-height 44-52px (Apple guidelines) - Grilles adaptées (2 colonnes au lieu de 3 pour médias) - Navigation simplifiée avec menu hamburger - Dialogs en plein écran (95vw sur mobile) - Tables converties en cards empilées - Boutons d'action en colonne au lieu de ligne - Padding et espacement optimisés pour petits écrans - Typographie réduite (text-2xl au lieu de 3xl) - Touch-manipulation sur zones interactives - Bottom fixed buttons pour actions principales - Inputs full-width avec min-height 48px ### 4. Routing automatique - App.tsx modifié pour utiliser createResponsiveRoute - Détection transparente du device - Lazy loading de toutes les routes - Aucun changement d'URL entre versions ## Performances - Code splitting automatique (lazy loading) - Seule la version nécessaire est chargée - Cache des composants chargés - Réduction de la taille du bundle initial ## Tests à effectuer 1. Rétrécir la fenêtre du navigateur < 768px 2. Utiliser les DevTools mobile 3. Tester sur un vrai appareil mobile 4. Vérifier que toutes les fonctionnalités marchent Les utilisateurs bénéficient maintenant d'une expérience optimale sur mobile !
73 lines
2.2 KiB
TypeScript
73 lines
2.2 KiB
TypeScript
import { useState, useEffect } from 'react';
|
|
|
|
/**
|
|
* Hook to detect if the user is on a mobile device
|
|
* Uses both media query and user agent for robust detection
|
|
*
|
|
* @param breakpoint - The max-width breakpoint for mobile (default: 768px)
|
|
* @returns boolean - true if mobile, false if desktop
|
|
*/
|
|
export function useIsMobile(breakpoint: number = 768): boolean {
|
|
const [isMobile, setIsMobile] = useState<boolean>(() => {
|
|
// Initial detection (SSR-safe)
|
|
if (typeof window === 'undefined') return false;
|
|
|
|
// Check media query
|
|
const mediaMatch = window.matchMedia(`(max-width: ${breakpoint}px)`).matches;
|
|
|
|
// Check user agent for mobile devices
|
|
const userAgent = navigator.userAgent.toLowerCase();
|
|
const mobileKeywords = ['android', 'webos', 'iphone', 'ipad', 'ipod', 'blackberry', 'windows phone'];
|
|
const isUserAgentMobile = mobileKeywords.some(keyword => userAgent.includes(keyword));
|
|
|
|
// Return true if either media query or user agent indicates mobile
|
|
return mediaMatch || isUserAgentMobile;
|
|
});
|
|
|
|
useEffect(() => {
|
|
// Create media query list
|
|
const mediaQueryList = window.matchMedia(`(max-width: ${breakpoint}px)`);
|
|
|
|
// Handler for media query changes
|
|
const handleChange = (e: MediaQueryListEvent) => {
|
|
setIsMobile(e.matches);
|
|
};
|
|
|
|
// Listen for changes (modern browsers)
|
|
if (mediaQueryList.addEventListener) {
|
|
mediaQueryList.addEventListener('change', handleChange);
|
|
} else {
|
|
// Fallback for older browsers
|
|
mediaQueryList.addListener(handleChange);
|
|
}
|
|
|
|
// Cleanup
|
|
return () => {
|
|
if (mediaQueryList.removeEventListener) {
|
|
mediaQueryList.removeEventListener('change', handleChange);
|
|
} else {
|
|
mediaQueryList.removeListener(handleChange);
|
|
}
|
|
};
|
|
}, [breakpoint]);
|
|
|
|
return isMobile;
|
|
}
|
|
|
|
/**
|
|
* Hook to detect device type with more granularity
|
|
* @returns object with device type information
|
|
*/
|
|
export function useDeviceType() {
|
|
const isMobile = useIsMobile(768);
|
|
const isTablet = useIsMobile(1024) && !useIsMobile(768);
|
|
const isDesktop = !useIsMobile(1024);
|
|
|
|
return {
|
|
isMobile,
|
|
isTablet,
|
|
isDesktop,
|
|
deviceType: isMobile ? 'mobile' : isTablet ? 'tablet' : 'desktop'
|
|
} as const;
|
|
}
|