import 'dart:convert'; import 'package:flutter/material.dart'; import 'package:go_router/go_router.dart'; import 'package:google_fonts/google_fonts.dart'; import 'package:shared_preferences/shared_preferences.dart'; // don't forget import '../services/apiService.dart'; enum TabSelection { allTrips, myTrips, myApprovals } class CustomAppBar extends StatefulWidget implements PreferredSizeWidget { final bool isDesktop; final String? logoUrl; final String? username; final List? actions; final bool showBackButton; const CustomAppBar({ super.key, this.logoUrl, this.username, this.actions, this.showBackButton = false, required this.isDesktop, }); @override Size get preferredSize => const Size.fromHeight(kToolbarHeight); @override _CustomAppBarState createState() => _CustomAppBarState(); } class _CustomAppBarState extends State { final ApiService apiService = ApiService(); TabSelection selectedTab = TabSelection.allTrips; String? token; Map? userData; Map? fetchedUserData; Map userDetails = {}; Map? selectedOrg; Color? layoutColor; Color? bodyColor; Color _myTravelRequestColor = Color(0xFF475569); // Default color EdgeInsets _myTravelRequestPadding = EdgeInsets.symmetric(horizontal: 8, vertical: 4); Color _myApprovalsColor = Color(0xFF475569); // Default color void initState() { super.initState(); // initializeData(); WidgetsBinding.instance.addPostFrameCallback((_) { initializeData(); getOrganizationData(); }); } Future initializeData() async { print("initializeDatainitializeData"); token = await getToken(); fetchedUserData = await getUserData(); if (token == null || fetchedUserData == null) { print("Token or USerId missing"); return; } setState(() { userData = fetchedUserData; }); } String getTabLabel(TabSelection tab) { switch (tab) { case TabSelection.allTrips: return "All Trips"; case TabSelection.myTrips: return "My Trips"; case TabSelection.myApprovals: return "My Approvals"; } } Future getToken() async { final prefs = await SharedPreferences.getInstance(); return prefs.getString("auth_token"); } Future?> getUserData() async { final prefs = await SharedPreferences.getInstance(); final String? userDataString = prefs.getString('user_data'); if (userDataString != null) { try { userDetails = jsonDecode(userDataString); return { "user_id": userDetails["user_id"].toString(), "name": "${userDetails["first_name"]} ${userDetails["last_name"]}", "email": userDetails["email"] ?? "", "role": userDetails["role"] ?? "", }; } catch (e) { print("Error decoding user data: $e"); return null; } } return null; } Future getOrganizationData() async { try { print("getUpdatedServices"); final result = await apiService.fetchOrganization(); final prefs = await SharedPreferences.getInstance(); print("UUPdatedServices - $result"); setState(() { selectedOrg = result; layoutColor = selectedOrg?['layout_color'] != null ? Color(int.parse(selectedOrg!['layout_color'])) : Colors.white; bodyColor = selectedOrg?['color'] != null ? Color(int.parse( selectedOrg!['color'].toString().replaceFirst('0x', ''), radix: 16)) : Colors.blue; String? rawLogoPath = selectedOrg?['logo']; if (rawLogoPath != null && rawLogoPath.contains('/assets')) { const baseUrl = "https://apitest.tripapprovaltool.com"; final assetPath = rawLogoPath.split('/assets').last; selectedOrg!['logo'] = "$baseUrl/assets$assetPath"; } }); // Save to SharedPreferences await prefs.setString('layout_color', selectedOrg?['layout_color']); await prefs.setString('body_color', selectedOrg?['color']); await prefs.setString('body_color', selectedOrg?['plan_action']); print( "Layout Color- ${selectedOrg?['layout_color']} - $layoutColor ---------- bodyColor - $bodyColor"); } catch (e) { print("Error : $e"); } } @override Widget build(BuildContext context) { return AppBar( backgroundColor: Colors.white, surfaceTintColor: Colors.white, // elevation: 3, automaticallyImplyLeading: !widget.isDesktop, iconTheme: IconThemeData( color: layoutColor, // 👈 Set your desired icon color here ), titleSpacing: 0, title: !widget.isDesktop ? Text('') : Padding( padding: EdgeInsets.symmetric( horizontal: MediaQuery.of(context).size.width * 0.05), child: Row( children: [ Padding( padding: const EdgeInsets.all(10), // padding: const EdgeInsets.symmetric(horizontal: 40, vertical: 10), child: selectedOrg?['logo'] != null ? ClipRect( child: Image.network( selectedOrg!['logo'], width: 130, height: 80, // fit: BoxFit.contain, errorBuilder: (context, error, stackTrace) { return const CircleAvatar( radius: 20, backgroundColor: Colors.redAccent, child: Icon(Icons.error, size: 10), ); }, ), ) : const CircleAvatar( radius: 20, backgroundColor: Colors.white, child: Icon( Icons.add_a_photo, size: 10, color: Colors.grey, ), ), ), SizedBox( width: MediaQuery.of(context).size.width * 0.2, ), // Container( // width: MediaQuery.of(context).size.width * 0.35, // // color: Colors.blueGrey, // child: Row( // // crossAxisAlignment: CrossAxisAlignment.start, // mainAxisAlignment: MainAxisAlignment.center, // children: [ // if (userData?["role"] == "Org Admin" || // userData?["role"] == "Travel Admin") // MouseRegion( // cursor: SystemMouseCursors.click, // onEnter: (_) { // setState(() { // // _myTravelRequestPadding = // // EdgeInsets.symmetric(horizontal: 12, vertical: 78); // // _myTravelRequestColor = // // Color(0xFF114D8B); // Change color on hover // }); // }, // onExit: (_) { // setState(() { // // _myTravelRequestPadding = EdgeInsets.symmetric( // // horizontal: 8, vertical: 4); // Normal padding // // _myTravelRequestColor = // // Color(0xFF475569); // Revert color when hover ends // }); // }, // child: InkWell( // onTap: () { // context.go('/listAllPlan'); // }, // child: Text( // "All Trips", // style: TextStyle( // fontSize: 12, // fontWeight: FontWeight.w600, // // color: Color(0xFF475569), // color: _myTravelRequestColor, // fontFamily: "Inter", // ), // )), // ), // const SizedBox(width: 20), // if (userDetails["role"] == "Travel Agent") // MouseRegion( // cursor: SystemMouseCursors.click, // onEnter: (_) { // setState(() { // // _myTravelRequestPadding = // // EdgeInsets.symmetric(horizontal: 12, vertical: 78); // // _myTravelRequestColor = // // Color(0xFF114D8B); // Change color on hover // }); // }, // onExit: (_) { // setState(() { // // _myTravelRequestPadding = EdgeInsets.symmetric( // // horizontal: 8, vertical: 4); // Normal padding // // _myTravelRequestColor = // // Color(0xFF475569); // Revert color when hover ends // }); // }, // child: InkWell( // onTap: () { // context.go('/listTravelAgentPlan'); // }, // child: Text( // "My Trips", // style: TextStyle( // fontSize: 12, // fontWeight: FontWeight.w600, // // color: Color(0xFF475569), // color: _myTravelRequestColor, // fontFamily: "Inter", // ), // )), // ), // if (userDetails["role"] != "Travel Agent") // const SizedBox(width: 20), // if (userDetails["role"] != "Travel Agent") // MouseRegion( // cursor: SystemMouseCursors.click, // onEnter: (_) { // setState(() { // // _myTravelRequestPadding = // // EdgeInsets.symmetric(horizontal: 12, vertical: 78); // // _myTravelRequestColor = // // Color(0xFF114D8B); // Change color on hover // }); // }, // onExit: (_) { // setState(() { // // _myTravelRequestPadding = EdgeInsets.symmetric( // // horizontal: 8, vertical: 4); // Normal padding // // _myTravelRequestColor = // // Color(0xFF475569); // Revert color when hover ends // }); // }, // child: InkWell( // onTap: () { // context.go('/listPlan'); // }, // child: Text( // "My Trips", // style: TextStyle( // fontSize: 12, // fontWeight: FontWeight.w600, // // color: Color(0xFF475569), // color: _myTravelRequestColor, // fontFamily: "Inter", // ), // )), // ), // const SizedBox(width: 20), // if (userData?["role"] != "Travel Agent") // MouseRegion( // cursor: SystemMouseCursors.click, // onEnter: (_) { // setState(() { // _myApprovalsColor = // Color(0xFF114D8B); // Change color on hover // }); // }, // onExit: (_) { // setState(() { // _myApprovalsColor = Color( // 0xFF475569); // Revert color when hover ends // }); // }, // child: InkWell( // onTap: () { // context.go('/ApprovalList'); // }, // child: Text( // "My Approvals", // style: TextStyle( // fontSize: 12, // fontWeight: FontWeight.w600, // color: _myApprovalsColor, // // color: Color(0xFF475569), // fontFamily: "Inter", // ), // )), // ), // if (userData?["role"] == "Travel Agent") // MouseRegion( // cursor: SystemMouseCursors.click, // onEnter: (_) { // setState(() { // _myApprovalsColor = // Color(0xFF114D8B); // Change color on hover // }); // }, // onExit: (_) { // setState(() { // _myApprovalsColor = Color( // 0xFF475569); // Revert color when hover ends // }); // }, // child: InkWell( // onTap: () { // context.go('/listTravelAgentPlan'); // }, // child: Text( // "My Approvals", // style: TextStyle( // fontSize: 12, // fontWeight: FontWeight.w600, // color: _myApprovalsColor, // // color: Color(0xFF475569), // fontFamily: "Inter", // ), // )), // ), // ], // ), // ), Container( width: MediaQuery.of(context).size.width * 0.35, child: Row( mainAxisAlignment: MainAxisAlignment.center, children: [ if (userData?["role"] == "Org Admin" || userData?["role"] == "Travel Admin") buildNavItem("All Trips", _myTravelRequestColor, () => context.go('/listAllPlan'), isSelected: selectedTab == "All Trips"), if (userDetails["role"] != "Travel Agent") const SizedBox(width: 20), if (userData?["role"] == "Travel Agent") buildNavItem( "My Trips", _myTravelRequestColor, () => context.go('/listTravelAgentPlan'), isSelected: selectedTab == "My Trips", ), if (userData?["role"] != "Travel Agent") // for others buildNavItem( "My Trips", _myTravelRequestColor, () => context.go('/listPlan'), isSelected: selectedTab == "My Trips", ), // if (userDetails["role"] == "Travel Agent") // buildNavItem("My Trips", _myTravelRequestColor, // () => context.go('/listTravelAgentPlan'), // isSelected: selectedTab == "My Trips"), // ...[ // const SizedBox(width: 20), // buildNavItem("My Trips", _myTravelRequestColor, // () => context.go('/listPlan'), // isSelected: selectedTab == "My Trips"), // ], // const SizedBox(width: 20), if (userData?["role"] != "Travel Agent") buildNavItem("My Approvals", _myApprovalsColor, () { isSelected: selectedTab == "My Approvals"; context.go('/ApprovalList'); }) // if (userData?["role"] == "Travel Agent") { // isSelected: // selectedTab == "My Approvals"; // context.go('/listTravelAgentPlan'); // } else { // isSelected: // selectedTab == "My Approvals"; // context.go('/ApprovalList'); // } ], ), ), Spacer(), ], ), ), actions: [ Padding( padding: EdgeInsets.symmetric( horizontal: MediaQuery.of(context).size.width * 0.05), child: Row( children: [ // if (userData?["role"] != "User") Builder( builder: (context) => PopupMenuButton( color: Colors.white, padding: EdgeInsets.zero, offset: const Offset(0, 50), // 👈 shift it 50 pixels down onSelected: (String value) { switch (value) { case '/OrganizationSetup': context.go('/OrganizationSetup'); break; case '/listUser': context.go('/listUser'); break; case '/group': context.go('/group'); break; case '/PolicyList': context.go('/PolicyList'); case '/CreateUserDetails': context.go( "/CreateUserDetails", extra: { "selectedUser": userDetails, "isEditProfile": true, "isViewMode": true }, ); case '/logout': context.go('/'); break; } }, // itemBuilder: (BuildContext context) => // menuItems.map(buildMenuItem).toList(), itemBuilder: (BuildContext context) { // final isUser = userData?["role"] == "User"; final role = userData?["role"]; List> filteredItems; if (role == "User") { filteredItems = menuItems .where((item) => item['value'] == '/CreateUserDetails' || item['value'] == '/logout') .toList(); } else if (role == "Travel Agent") { filteredItems = menuItems .where((item) => item['value'] == '/logout') .toList(); } else { filteredItems = menuItems; } // Create a new list starting with role display and divider return [ PopupMenuItem( enabled: false, // ❌ Not clickable child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text( userData?["role"] ?? '', style: GoogleFonts.poppins( fontSize: 12, fontWeight: FontWeight.bold, color: Colors.black, ), ), const Divider(), // 👈 Divider after role ], ), ), ...filteredItems .map(buildMenuItem) .toList(), // 👈 then normal items ]; }, // itemBuilder: (BuildContext context) { // final isUser = userData?["role"] == "User"; // final filteredItems = isUser // ? menuItems // .where((item) => // item['value'] == '/CreateUserDetails' || // item['value'] == '/logout') // .toList() // : menuItems; // // return filteredItems.map(buildMenuItem).toList(); // }, child: MouseRegion( cursor: SystemMouseCursors.click, child: Row( mainAxisSize: MainAxisSize.min, children: [ Text( userData?["name"] ?? "N/A", style: GoogleFonts.poppins( fontSize: 14, fontWeight: FontWeight.w500, color: Colors.black, ), // style: const TextStyle( // fontSize: 14, // fontWeight: FontWeight.w500, // fontFamily: "Roboto", // color: Colors.black, // ), ), const Icon( Icons.arrow_drop_down, size: 20, color: Colors.black87, ), ], ), ), ), ), const SizedBox(width: 8), ], ), ), ], bottom: PreferredSize( preferredSize: Size.fromHeight(1), child: Container( height: 1, // color: Colors.grey.shade200, // Set the color of the bottom border color: layoutColor, // Set the color of the bottom border ), ), ); } @override Size get preferredSize => const Size.fromHeight(kToolbarHeight); } final List> menuItems = [ { 'value': '/OrganizationSetup', 'icon': Icons.business, 'label': 'Organization' }, { 'value': '/listUser', 'icon': Icons.manage_accounts, 'label': 'User Management' }, {'value': '/group', 'icon': Icons.group, 'label': 'Group'}, {'value': '/PolicyList', 'icon': Icons.policy, 'label': 'Policy'}, { 'value': '/CreateUserDetails', 'icon': Icons.account_circle, 'label': 'My Profile' }, {'value': '/logout', 'icon': Icons.login_outlined, 'label': 'Logout'}, ]; PopupMenuItem buildMenuItem(Map item) { return PopupMenuItem( height: 40, // 👈 reduce PopupMenuItem height value: item['value'], padding: EdgeInsets.symmetric(horizontal: 12), // 👈 control left-right spacing child: Row( children: [ Icon(item['icon'], size: 18, color: Colors.black87), // 👈 smaller, cleaner icon SizedBox(width: 10), // 👈 small space between icon and text Text( item['label'], style: GoogleFonts.poppins( fontSize: 12, fontWeight: FontWeight.w400, color: Colors.black87, ), ), ], ), ); } Widget buildNavItem(String label, Color color, VoidCallback onTap, {bool isSelected = false}) { return MouseRegion( cursor: SystemMouseCursors.click, child: InkWell( onTap: onTap, child: Container( padding: EdgeInsets.only(bottom: 2), decoration: isSelected ? BoxDecoration( border: Border( bottom: BorderSide( color: color, // underline color width: 2, // underline thickness ), ), ) : null, // no underline when not selected child: Text( label, style: GoogleFonts.poppins( fontSize: 12, fontWeight: FontWeight.w500, color: Colors.black), // style: TextStyle( // fontSize: 12, // fontWeight: FontWeight.w600, // color: color, // fontFamily: "Inter", // ), ), ), ), ); }