From 0e144cf7fd334842aa9238ed5f877a3922ddcb8d Mon Sep 17 00:00:00 2001 From: Marcos Date: Mon, 18 May 2026 19:17:59 +0200 Subject: [PATCH] feat: Integrate sync status indicators in app title bar and home screen --- lib/app.dart | 7 ++-- lib/screens/home_screen.dart | 9 ++++++ lib/widgets/app_title_bar_io.dart | 45 ++------------------------ lib/widgets/search_app_bar.dart | 12 +++++++ lib/widgets/sync_status_indicator.dart | 9 +++++- 5 files changed, 34 insertions(+), 48 deletions(-) diff --git a/lib/app.dart b/lib/app.dart index 1d10f83..788e654 100644 --- a/lib/app.dart +++ b/lib/app.dart @@ -705,6 +705,8 @@ class _NotesAppState extends State repository: repository, onOpenSettings: _openSettings, onVaultInvalid: _resetLocalVaultData, + syncStatus: _syncStatus, + syncErrorMessage: _syncErrorMessage, ) : SettingsScreen( key: const ValueKey('settings-screen'), @@ -749,10 +751,7 @@ class _NotesAppState extends State child: SafeArea( child: Column( children: [ - AppTitleBar( - syncStatus: _syncStatus, - syncErrorMessage: _syncErrorMessage, - ), + const AppTitleBar(), Expanded( child: AnimatedSwitcher( duration: _screenTransitionDuration, diff --git a/lib/screens/home_screen.dart b/lib/screens/home_screen.dart index e7cbecd..f09b6cc 100644 --- a/lib/screens/home_screen.dart +++ b/lib/screens/home_screen.dart @@ -10,6 +10,7 @@ import 'package:notas/screens/note_editor_screen.dart'; import 'package:notas/widgets/menu_drawer.dart'; import 'package:notas/widgets/note_card.dart'; import 'package:notas/widgets/search_app_bar.dart'; +import 'package:notas/widgets/sync_status_indicator.dart'; class HomeScreen extends StatefulWidget { const HomeScreen({ @@ -17,11 +18,15 @@ class HomeScreen extends StatefulWidget { required this.repository, required this.onOpenSettings, this.onVaultInvalid, + this.syncStatus = SyncStatus.idle, + this.syncErrorMessage, }); final NoteRepository repository; final VoidCallback onOpenSettings; final Future Function()? onVaultInvalid; + final SyncStatus syncStatus; + final String? syncErrorMessage; @override State createState() => _HomeScreenState(); @@ -512,6 +517,10 @@ class _HomeScreenState extends State { _isMenuOpen = !_isMenuOpen; }); }, + trailingWidget: SyncStatusIndicator( + status: widget.syncStatus, + errorMessage: widget.syncErrorMessage, + ), onSearchChanged: (String query) { setState(() { _searchQuery = query; diff --git a/lib/widgets/app_title_bar_io.dart b/lib/widgets/app_title_bar_io.dart index f932982..51f5eb3 100644 --- a/lib/widgets/app_title_bar_io.dart +++ b/lib/widgets/app_title_bar_io.dart @@ -1,18 +1,12 @@ import 'package:flutter/material.dart'; import 'package:notas/platform/app_platform.dart'; -import 'package:notas/widgets/sync_status_indicator.dart'; import 'package:window_manager/window_manager.dart'; class AppTitleBar extends StatelessWidget { const AppTitleBar({ - this.syncStatus = SyncStatus.idle, - this.syncErrorMessage, super.key, }); - final SyncStatus syncStatus; - final String? syncErrorMessage; - @override Widget build(BuildContext context) { if (isAndroid || isIOS) { @@ -30,11 +24,6 @@ class AppTitleBar extends StatelessWidget { 'Mis Notas', style: TextStyle(color: Colors.white70, fontSize: 13), ), - const SizedBox(width: 8), - SyncStatusIndicator( - status: syncStatus, - errorMessage: syncErrorMessage, - ), ], ), ), @@ -42,10 +31,7 @@ class AppTitleBar extends StatelessWidget { } if (isLinux) { - return _KdeTitleBar( - syncStatus: syncStatus, - syncErrorMessage: syncErrorMessage, - ); + return const _KdeTitleBar(); } return SizedBox( @@ -56,11 +42,6 @@ class AppTitleBar extends StatelessWidget { mainAxisSize: MainAxisSize.min, children: [ const Text('Mis Notas', style: TextStyle(color: Colors.white)), - const SizedBox(width: 8), - SyncStatusIndicator( - status: syncStatus, - errorMessage: syncErrorMessage, - ), ], ), ), @@ -69,13 +50,7 @@ class AppTitleBar extends StatelessWidget { } class _KdeTitleBar extends StatefulWidget { - const _KdeTitleBar({ - this.syncStatus = SyncStatus.idle, - this.syncErrorMessage, - }); - - final SyncStatus syncStatus; - final String? syncErrorMessage; + const _KdeTitleBar(); @override State<_KdeTitleBar> createState() => _KdeTitleBarState(); @@ -182,22 +157,6 @@ class _KdeTitleBarState extends State<_KdeTitleBar> with WindowListener { ), ), ), - Positioned( - left: 0, - top: 0, - bottom: 0, - child: IgnorePointer( - child: Padding( - padding: const EdgeInsets.symmetric(horizontal: 8), - child: Center( - child: SyncStatusIndicator( - status: widget.syncStatus, - errorMessage: widget.syncErrorMessage, - ), - ), - ), - ), - ), Positioned( right: 0, top: 0, diff --git a/lib/widgets/search_app_bar.dart b/lib/widgets/search_app_bar.dart index 3b6738a..75cdeab 100644 --- a/lib/widgets/search_app_bar.dart +++ b/lib/widgets/search_app_bar.dart @@ -7,6 +7,8 @@ class SearchAppBar extends StatefulWidget { this.onLeadingPressed, this.leadingIcon = Icons.menu, this.leadingTooltip = 'Menú', + this.leadingWidget, + this.trailingWidget, this.onSearchChanged, this.searchHint = 'Buscar notas...', this.showSearch = true, @@ -17,6 +19,8 @@ class SearchAppBar extends StatefulWidget { final VoidCallback? onLeadingPressed; final IconData leadingIcon; final String leadingTooltip; + final Widget? leadingWidget; + final Widget? trailingWidget; final ValueChanged? onSearchChanged; final String searchHint; final bool showSearch; @@ -67,6 +71,10 @@ class _SearchAppBarState extends State { splashRadius: 18, constraints: const BoxConstraints(minWidth: 40, minHeight: 40), ), + if (widget.leadingWidget != null) ...[ + const SizedBox(width: 8), + Center(child: widget.leadingWidget!), + ], const SizedBox(width: 8), Expanded( child: widget.showSearch @@ -151,6 +159,10 @@ class _SearchAppBarState extends State { ), ), ), + if (widget.trailingWidget != null) ...[ + const SizedBox(width: 8), + Center(child: widget.trailingWidget!), + ], ], ), ); diff --git a/lib/widgets/sync_status_indicator.dart b/lib/widgets/sync_status_indicator.dart index 744e0a9..af6346d 100644 --- a/lib/widgets/sync_status_indicator.dart +++ b/lib/widgets/sync_status_indicator.dart @@ -21,7 +21,14 @@ class SyncStatusIndicator extends StatelessWidget { Widget build(BuildContext context) { switch (status) { case SyncStatus.idle: - return const SizedBox.shrink(); + return const Tooltip( + message: 'Sincronización en espera', + child: Icon( + Icons.cloud_outlined, + size: 16, + color: Colors.white38, + ), + ); case SyncStatus.syncing: return const Tooltip(