import 'package:flutter/material.dart'; import 'package:iconsax/iconsax.dart'; import 'package:animate_do/animate_do.dart'; import 'package:getwidget/getwidget.dart'; import 'package:url_launcher/url_launcher.dart'; import 'components/navigation_sidebar.dart'; import 'pages/architech_page.dart'; import 'pages/agents_page.dart'; class ConsoleLandingPage extends StatefulWidget { const ConsoleLandingPage({super.key}); @override State createState() => _ConsoleLandingPageState(); } class _ConsoleLandingPageState extends State { bool _isSidebarExpanded = true; String _currentPage = 'dashboard'; void _toggleSidebar() { setState(() { _isSidebarExpanded = !_isSidebarExpanded; }); } void _navigateToPage(String pageId) { setState(() { _currentPage = pageId; }); } @override Widget build(BuildContext context) { final colorScheme = Theme.of(context).colorScheme; return Scaffold( backgroundColor: colorScheme.surface, body: Row( children: [ // Navigation Sidebar NavigationSidebar( isExpanded: _isSidebarExpanded, onNavigate: _navigateToPage, currentPage: _currentPage, ), // Main Content Area Expanded( child: Column( children: [ // AppBar _buildAppBar(colorScheme), // Main Content Expanded( child: _buildMainContent(colorScheme), ), ], ), ), ], ), ); } Widget _buildAppBar(ColorScheme colorScheme) { return Container( height: 70, decoration: BoxDecoration( color: colorScheme.surfaceContainerLow, border: Border( bottom: BorderSide( color: colorScheme.outline.withValues(alpha:0.2), width: 1, ), ), ), child: Row( children: [ // Toggle Sidebar Button IconButton( icon: Icon( _isSidebarExpanded ? Iconsax.arrow_left_2 : Iconsax.arrow_right_3, color: colorScheme.onSurface, ), onPressed: _toggleSidebar, tooltip: _isSidebarExpanded ? 'Collapse sidebar' : 'Expand sidebar', ), const SizedBox(width: 12), // Page Title Expanded( child: Column( crossAxisAlignment: CrossAxisAlignment.start, mainAxisAlignment: MainAxisAlignment.center, children: [ Text( _getPageTitle(), style: TextStyle( fontSize: 18, fontWeight: FontWeight.bold, color: colorScheme.onSurface, ), ), Text( 'sovereign AI solutions', style: TextStyle( fontSize: 11, color: colorScheme.onSurfaceVariant, ), ), ], ), ), // Action Buttons Container( margin: const EdgeInsets.only(right: 8), child: IconButton( icon: Container( padding: const EdgeInsets.all(8), decoration: BoxDecoration( color: colorScheme.primary.withValues(alpha:0.1), shape: BoxShape.circle, ), child: Icon(Iconsax.notification, color: colorScheme.primary), ), onPressed: () {}, ), ), Container( margin: const EdgeInsets.only(right: 12), child: IconButton( icon: Container( padding: const EdgeInsets.all(8), decoration: BoxDecoration( color: colorScheme.secondary.withValues(alpha:0.1), shape: BoxShape.circle, ), child: Icon(Iconsax.setting_2, color: colorScheme.secondary), ), onPressed: () {}, ), ), ], ), ); } String _getPageTitle() { switch (_currentPage) { case 'dashboard': return 'Dashboard'; case 'architech': return 'The Architech'; case 'agents': return 'AI Agents'; case 'analytics': return 'Analytics'; case 'tools': return 'Tools'; case 'settings': return 'Settings'; default: return 'Svrnty Console'; } } Widget _buildMainContent(ColorScheme colorScheme) { // Switch between different pages switch (_currentPage) { case 'architech': return const ArchitechPage(); case 'agents': return const AgentsPage(); case 'dashboard': default: return _buildDashboardContent(colorScheme); } } Widget _buildDashboardContent(ColorScheme colorScheme) { return LayoutBuilder( builder: (context, constraints) { return SingleChildScrollView( padding: EdgeInsets.all(_getPagePadding(constraints.maxWidth)), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ // Status Cards Grid _buildResponsiveGrid( constraints.maxWidth, [ _buildStatusCard( 'Backend', 'Access Swagger', colorScheme.primary, Icons.api, 'Active', url: 'http://localhost:7108/swagger/', ), _buildStatusCard( 'Frontend', 'UI Status', colorScheme.primary, Icons.web, 'Online', ), _buildStatusCard( 'To-Do', 'Analytics Dashboard', colorScheme.primary, Icons.analytics_outlined, 'Running', ), _buildStatusCard( 'Pull requests', 'Connection Pool', colorScheme.secondary, Icons.storage_outlined, 'Connected', ), _buildStatusCard( 'Work Logs', 'View Recent Activity', colorScheme.secondary, Icons.receipt_long_outlined, 'Active', ), _buildStatusCard( 'Mindbox', 'Metrics & Monitoring', colorScheme.secondary, Icons.speed_outlined, 'Normal', ), ], ), const SizedBox(height: 32), // Recent Activity Section _buildSectionHeader('Recent Activity'), const SizedBox(height: 16), _buildActivityCard( 'PR request', 'Authentification_module.config is updated', '2 minutes ago', Icons.check_circle_outline, colorScheme.primary, ), const SizedBox(height: 12), _buildActivityCard( 'Database Sync', 'Completed backup operation', '3 hours 11 minutes ago', Icons.cloud_done_outlined, colorScheme.secondary, ), const SizedBox(height: 12), _buildActivityCard( 'The Archivist agent created', 'Modele configured and operational', '3 days ago', Icons.security_outlined, colorScheme.secondary, ), ], ), ); }, ); } // Helper method: Get responsive padding based on screen width double _getPagePadding(double width) { if (width < 600) { return 16.0; // Mobile } else if (width < 1024) { return 24.0; // Tablet } else { return 32.0; // Desktop } } // Helper method: Build responsive grid Widget _buildResponsiveGrid(double width, List children) { int crossAxisCount; double spacing; if (width < 600) { // Mobile: 1 column crossAxisCount = 1; spacing = 12.0; } else if (width < 900) { // Tablet: 2 columns crossAxisCount = 2; spacing = 16.0; } else if (width < 1200) { // Small desktop: 3 columns crossAxisCount = 3; spacing = 20.0; } else { // Large desktop: 3 columns with more space crossAxisCount = 3; spacing = 24.0; } return GridView.builder( gridDelegate: SliverGridDelegateWithFixedCrossAxisCount( crossAxisCount: crossAxisCount, mainAxisExtent: 155, crossAxisSpacing: spacing, mainAxisSpacing: spacing, ), itemCount: children.length, shrinkWrap: true, physics: const NeverScrollableScrollPhysics(), itemBuilder: (context, index) => children[index], ); } // Helper method: Build GetWidget-powered status card Widget _buildStatusCard( String title, String subtitle, Color color, IconData icon, String status, { String? url, }) { final colorScheme = Theme.of(context).colorScheme; return FadeInUp( duration: const Duration(milliseconds: 400), child: Container( decoration: BoxDecoration( borderRadius: BorderRadius.circular(16), gradient: LinearGradient( begin: Alignment.topLeft, end: Alignment.bottomRight, colors: [ color.withValues(alpha:0.25), color.withValues(alpha:0.12), ], ), border: Border.all( color: color.withValues(alpha:0.5), width: 1.5, ), ), child: Card( elevation: 4, color: Colors.transparent, shape: RoundedRectangleBorder( borderRadius: BorderRadius.circular(16), ), child: InkWell( // ignore: use_build_context_synchronously onTap: () async { if (url != null) { try { final uri = Uri.parse(url); if (await canLaunchUrl(uri)) { await launchUrl(uri, mode: LaunchMode.externalApplication); if (context.mounted) { // ignore: use_build_context_synchronously final ctx = context; GFToast.showToast( 'Opening $title...', ctx, toastPosition: GFToastPosition.BOTTOM, textStyle: const TextStyle(fontSize: 14, color: Colors.white), backgroundColor: color.withValues(alpha:0.9), toastDuration: 2, ); } } else { if (context.mounted) { // ignore: use_build_context_synchronously final ctx = context; GFToast.showToast( 'Cannot open $url', ctx, toastPosition: GFToastPosition.BOTTOM, textStyle: const TextStyle(fontSize: 14, color: Colors.white), backgroundColor: colorScheme.error.withValues(alpha:0.9), toastDuration: 3, ); } } } catch (e) { if (context.mounted) { // ignore: use_build_context_synchronously final ctx = context; GFToast.showToast( 'Error: ${e.toString()}', ctx, toastPosition: GFToastPosition.BOTTOM, textStyle: const TextStyle(fontSize: 14, color: Colors.white), backgroundColor: colorScheme.error.withValues(alpha:0.9), toastDuration: 3, ); } } } else { GFToast.showToast( '$title tapped', context, toastPosition: GFToastPosition.BOTTOM, textStyle: const TextStyle(fontSize: 14, color: Colors.white), backgroundColor: color.withValues(alpha:0.9), toastDuration: 2, ); } }, borderRadius: BorderRadius.circular(16), child: Container( decoration: BoxDecoration( border: Border( left: BorderSide( color: color, width: 4, ), ), ), child: Padding( padding: const EdgeInsets.all(16.0), child: Column( crossAxisAlignment: CrossAxisAlignment.start, mainAxisSize: MainAxisSize.min, children: [ Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ GFAvatar( backgroundColor: color.withValues(alpha:0.3), radius: 22, shape: GFAvatarShape.standard, child: Icon(icon, size: 24, color: color), ), Container( constraints: const BoxConstraints(minWidth: 90), padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 6), decoration: BoxDecoration( color: color, borderRadius: BorderRadius.circular(20), ), child: Center( child: Text( status, style: const TextStyle( color: Colors.white, fontSize: 11, fontWeight: FontWeight.bold, letterSpacing: 0.5, ), ), ), ), ], ), const SizedBox(height: 12), Text( title, style: TextStyle( fontSize: 18, fontWeight: FontWeight.bold, color: colorScheme.onSurface, letterSpacing: 0.3, ), ), const SizedBox(height: 4), Text( subtitle, style: TextStyle( fontSize: 13, color: colorScheme.onSurfaceVariant, ), ), ], ), ), ), ), ), ), ); } // Helper method: Build section header Widget _buildSectionHeader(String title) { final colorScheme = Theme.of(context).colorScheme; return Row( children: [ Container( width: 4, height: 24, decoration: BoxDecoration( color: colorScheme.primary, borderRadius: BorderRadius.circular(2), ), ), const SizedBox(width: 12), Text( title, style: TextStyle( fontSize: 22, fontWeight: FontWeight.bold, color: colorScheme.onSurface, ), ), ], ); } // Helper method: Build GetWidget-powered activity card Widget _buildActivityCard( String title, String description, String time, IconData icon, Color color, ) { final colorScheme = Theme.of(context).colorScheme; return FadeInLeft( duration: const Duration(milliseconds: 400), child: Container( margin: const EdgeInsets.only(bottom: 0), decoration: BoxDecoration( borderRadius: BorderRadius.circular(12), border: Border.all( color: color.withValues(alpha:0.4), width: 1.5, ), ), child: Card( elevation: 2, child: ListTile( contentPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8), leading: GFAvatar( backgroundColor: color.withValues(alpha:0.25), radius: 22, shape: GFAvatarShape.circle, child: Icon(icon, color: color, size: 22), ), title: Text( title, style: TextStyle( fontWeight: FontWeight.bold, fontSize: 15, color: colorScheme.onSurface, letterSpacing: 0.2, ), ), subtitle: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Padding( padding: const EdgeInsets.only(top: 4), child: Text( description, style: TextStyle( fontSize: 13, color: colorScheme.onSurfaceVariant, ), ), ), Container( margin: const EdgeInsets.only(top: 8), padding: const EdgeInsets.symmetric(horizontal: 10, vertical: 4), decoration: BoxDecoration( color: colorScheme.surfaceContainerHighest, borderRadius: BorderRadius.circular(8), ), child: Text( time, style: TextStyle( fontSize: 11, fontWeight: FontWeight.w500, color: colorScheme.onSurfaceVariant, ), ), ), ], ), ), ), ), ); } }