(Feat) Update Loading screen

This commit is contained in:
2026-07-22 12:55:43 +02:00
parent 54091398a5
commit 77d603f734
5 changed files with 207 additions and 15 deletions
+34 -5
View File
@@ -20,6 +20,10 @@ class ProduitRepository extends ChangeNotifier {
static const _collection = 'produits';
/// Au-delà, on considère le serveur injoignable (évite d'attendre indéfiniment
/// au démarrage quand le Raspberry Pi est éteint ou hors réseau).
static const _delaiMax = Duration(seconds: 12);
PocketBase? _pb;
String _serveurUrl = '';
UnsubscribeFunc? _annulerAbo;
@@ -29,11 +33,20 @@ class ProduitRepository extends ChangeNotifier {
bool _enCours = false;
bool _connecte = false;
String? _erreur;
String _etape = '';
List<Produit> get produits => List.unmodifiable(_produits);
bool get charge => _charge;
bool get enCours => _enCours;
/// Étape en cours du démarrage, affichée sous le loader de l'écran d'accueil.
String get etape => _etape;
void _setEtape(String texte) {
_etape = texte;
notifyListeners();
}
/// Vrai si la dernière synchro avec le serveur a réussi (temps réel actif).
bool get connecte => _connecte;
String? get erreur => _erreur;
@@ -43,9 +56,13 @@ class ProduitRepository extends ChangeNotifier {
/// aux mises à jour temps réel. Ne lève jamais : en cas d'échec, [erreur]
/// est renseigné pour que l'écran propose de réessayer.
Future<void> initialiser() async {
_setEtape('Lecture des réglages…');
_serveurUrl = await Reglages.instance.serveurUrl();
_pb = PocketBase(_serveurUrl);
_setEtape('Chargement des produits enregistrés…');
await _chargerCache(); // affichage instantané + hors ligne
await charger(); // serveur + temps réel
}
@@ -98,21 +115,33 @@ class ProduitRepository extends ChangeNotifier {
Future<void> charger() async {
_enCours = true;
_erreur = null;
notifyListeners();
_setEtape('Connexion au serveur…');
try {
final records =
await _pb!.collection(_collection).getFullList(sort: '-created');
final records = await _pb!
.collection(_collection)
.getFullList(sort: '-created')
.timeout(_delaiMax);
_setEtape('Récupération des produits…');
_produits
..clear()
..addAll(records.map(_versProduit));
_charge = true;
_connecte = true;
_setEtape('Enregistrement hors ligne…');
await _sauverCache();
if (_annulerAbo == null) await _abonner();
if (_annulerAbo == null) {
_setEtape('Activation du temps réel…');
await _abonner();
}
_setEtape('Prêt');
} catch (e) {
_connecte = false;
// On garde les produits en cache ; le bandeau « non synchronisé » suffit.
if (_produits.isEmpty) _erreur = 'Serveur injoignable ($_serveurUrl).\n$e';
_setEtape('Hors ligne');
} finally {
_enCours = false;
notifyListeners();
@@ -132,7 +161,7 @@ class ProduitRepository extends ChangeNotifier {
_connecte = true;
unawaited(_sauverCache());
notifyListeners();
});
}).timeout(_delaiMax);
} catch (_) {
// Pas de temps réel (serveur momentanément indisponible) : pas bloquant,
// les données se rechargeront à la prochaine ouverture / réessai.
+19 -4
View File
@@ -10,8 +10,15 @@ class Reglages {
static const _cleDerniereUnite = 'derniere_unite';
static const _cleServeur = 'serveur_url';
/// Adresse par défaut du serveur PocketBase (le Raspberry Pi du magasin).
static const serveurParDefaut = 'http://192.168.1.32:8090';
/// Adresse par défaut du serveur PocketBase (le Raspberry Pi du magasin,
/// exposé via Tailscale : accessible aussi bien au magasin qu'à l'extérieur).
static const serveurParDefaut = 'https://db.tailb756e1.ts.net';
/// Anciennes adresses par défaut : si la tablette a encore l'une d'elles
/// enregistrée, on bascule automatiquement sur la nouvelle.
static const _anciensDefauts = {
'http://192.168.1.32:8090',
};
SharedPreferences? _prefs;
@@ -19,8 +26,16 @@ class Reglages {
_prefs ??= await SharedPreferences.getInstance();
/// Adresse du serveur PocketBase (modifiable dans les réglages).
Future<String> serveurUrl() async =>
(await _p).getString(_cleServeur) ?? serveurParDefaut;
Future<String> serveurUrl() async {
final p = await _p;
final url = p.getString(_cleServeur);
if (url == null || _anciensDefauts.contains(url)) {
// Jamais réglé, ou ancienne adresse par défaut restée en mémoire.
if (url != null) await p.setString(_cleServeur, serveurParDefaut);
return serveurParDefaut;
}
return url;
}
Future<void> setServeurUrl(String url) async =>
(await _p).setString(_cleServeur, url.trim());