diff --git a/assets/icons/account_setting.svg b/assets/icons/account_setting.svg
new file mode 100644
index 00000000..0b27b849
--- /dev/null
+++ b/assets/icons/account_setting.svg
@@ -0,0 +1,6 @@
+
diff --git a/assets/icons/logo-grey.svg b/assets/icons/logo-grey.svg
new file mode 100644
index 00000000..4f835d2d
--- /dev/null
+++ b/assets/icons/logo-grey.svg
@@ -0,0 +1,4 @@
+
diff --git a/assets/icons/settings.svg b/assets/icons/settings.svg
new file mode 100644
index 00000000..c626454d
--- /dev/null
+++ b/assets/icons/settings.svg
@@ -0,0 +1,4 @@
+
diff --git a/assets/icons/sign_out.svg b/assets/icons/sign_out.svg
new file mode 100644
index 00000000..5980d13e
--- /dev/null
+++ b/assets/icons/sign_out.svg
@@ -0,0 +1,3 @@
+
diff --git a/lib/pages/access_management/view/access_management.dart b/lib/pages/access_management/view/access_management.dart
index 8a6fa022..caa5fe28 100644
--- a/lib/pages/access_management/view/access_management.dart
+++ b/lib/pages/access_management/view/access_management.dart
@@ -15,8 +15,8 @@ import 'package:syncrow_web/utils/color_manager.dart';
import 'package:syncrow_web/utils/constants/app_enum.dart';
import 'package:syncrow_web/utils/constants/assets.dart';
import 'package:syncrow_web/utils/extension/build_context_x.dart';
-import 'package:syncrow_web/utils/style.dart';
import 'package:syncrow_web/utils/helpers/responsice_layout_helper/responsive_layout_helper.dart';
+import 'package:syncrow_web/utils/style.dart';
import 'package:syncrow_web/web_layout/web_scaffold.dart';
class AccessManagementPage extends StatelessWidget with HelperResponsiveLayout {
@@ -183,6 +183,14 @@ class AccessManagementPage extends StatelessWidget with HelperResponsiveLayout {
isRequired: false,
textFieldName: 'Name',
description: '',
+ onSubmitted: (value) {
+ accessBloc.add(FilterDataEvent(
+ emailAuthorizer: accessBloc.emailAuthorizer.text.toLowerCase(),
+ selectedTabIndex: BlocProvider.of(context).selectedIndex,
+ passwordName: accessBloc.passwordName.text.toLowerCase(),
+ startTime: accessBloc.effectiveTimeTimeStamp,
+ endTime: accessBloc.expirationTimeTimeStamp));
+ },
),
),
const SizedBox(width: 15),
@@ -194,6 +202,14 @@ class AccessManagementPage extends StatelessWidget with HelperResponsiveLayout {
isRequired: false,
textFieldName: 'Authorizer',
description: '',
+ onSubmitted: (value) {
+ accessBloc.add(FilterDataEvent(
+ emailAuthorizer: accessBloc.emailAuthorizer.text.toLowerCase(),
+ selectedTabIndex: BlocProvider.of(context).selectedIndex,
+ passwordName: accessBloc.passwordName.text.toLowerCase(),
+ startTime: accessBloc.effectiveTimeTimeStamp,
+ endTime: accessBloc.expirationTimeTimeStamp));
+ },
),
),
const SizedBox(width: 15),
@@ -239,12 +255,19 @@ class AccessManagementPage extends StatelessWidget with HelperResponsiveLayout {
SizedBox(
width: 300,
child: CustomWebTextField(
- controller: accessBloc.passwordName,
- isRequired: true,
- height: 40,
- textFieldName: 'Name',
- description: '',
- ),
+ controller: accessBloc.passwordName,
+ isRequired: true,
+ height: 40,
+ textFieldName: 'Name',
+ description: '',
+ onSubmitted: (value) {
+ accessBloc.add(FilterDataEvent(
+ emailAuthorizer: accessBloc.emailAuthorizer.text.toLowerCase(),
+ selectedTabIndex: BlocProvider.of(context).selectedIndex,
+ passwordName: accessBloc.passwordName.text.toLowerCase(),
+ startTime: accessBloc.effectiveTimeTimeStamp,
+ endTime: accessBloc.expirationTimeTimeStamp));
+ }),
),
DateTimeWebWidget(
icon: Assets.calendarIcon,
diff --git a/lib/pages/common/curtain_toggle.dart b/lib/pages/common/curtain_toggle.dart
index 305ede03..7b1551c5 100644
--- a/lib/pages/common/curtain_toggle.dart
+++ b/lib/pages/common/curtain_toggle.dart
@@ -26,9 +26,12 @@ class CurtainToggle extends StatelessWidget {
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
+ const SizedBox(
+ height: 10,
+ ),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
- crossAxisAlignment: CrossAxisAlignment.center,
+ crossAxisAlignment: CrossAxisAlignment.start,
children: [
ClipOval(
child: Container(
@@ -41,6 +44,9 @@ class CurtainToggle extends StatelessWidget {
),
),
),
+ const SizedBox(
+ width: 20,
+ ),
SizedBox(
height: 20,
width: 35,
diff --git a/lib/pages/common/custom_table.dart b/lib/pages/common/custom_table.dart
index 5b6692ae..10171c33 100644
--- a/lib/pages/common/custom_table.dart
+++ b/lib/pages/common/custom_table.dart
@@ -4,6 +4,7 @@ import 'package:flutter_svg/flutter_svg.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/bloc/device_managment_bloc.dart';
import 'package:syncrow_web/utils/color_manager.dart';
import 'package:syncrow_web/utils/constants/assets.dart';
+import 'package:syncrow_web/utils/extension/build_context_x.dart';
class DynamicTable extends StatefulWidget {
final List headers;
@@ -45,6 +46,8 @@ class DynamicTable extends StatefulWidget {
class _DynamicTableState extends State {
late List _selectedRows;
bool _selectAll = false;
+ final ScrollController _verticalScrollController = ScrollController();
+ final ScrollController _horizontalScrollController = ScrollController();
@override
void initState() {
@@ -102,68 +105,78 @@ class _DynamicTableState extends State {
Widget build(BuildContext context) {
return Container(
decoration: widget.cellDecoration,
- child: SingleChildScrollView(
- scrollDirection: Axis.horizontal,
- child: SizedBox(
- width: widget.size.width,
- child: Column(
- children: [
- Container(
- decoration: widget.headerDecoration ?? BoxDecoration(color: Colors.grey[200]),
- child: Row(
+ child: Scrollbar(
+ controller: _verticalScrollController,
+ thumbVisibility: true,
+ trackVisibility: true,
+ child: Scrollbar(
+ controller: _horizontalScrollController,
+ thumbVisibility: false,
+ trackVisibility: false,
+ notificationPredicate: (notif) => notif.depth == 1,
+ child: SingleChildScrollView(
+ controller: _verticalScrollController,
+ child: SingleChildScrollView(
+ controller: _horizontalScrollController,
+ scrollDirection: Axis.horizontal,
+ child: SizedBox(
+ width: widget.size.width,
+ child: Column(
children: [
- if (widget.withCheckBox) _buildSelectAllCheckbox(),
- ...widget.headers.map((header) => _buildTableHeaderCell(header)),
- ],
- ),
- ),
- widget.isEmpty
- ? Expanded(
- child: Column(
- mainAxisAlignment: MainAxisAlignment.center,
+ Container(
+ decoration: widget.headerDecoration ??
+ const BoxDecoration(
+ color: ColorsManager.boxColor,
+ ),
+ child: Row(
children: [
- Row(
- crossAxisAlignment: CrossAxisAlignment.center,
+ if (widget.withCheckBox) _buildSelectAllCheckbox(),
+ ...widget.headers.map((header) => _buildTableHeaderCell(header)),
+ ],
+ ),
+ ),
+ widget.isEmpty
+ ? Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
- Column(
+ Row(
+ crossAxisAlignment: CrossAxisAlignment.center,
+ mainAxisAlignment: MainAxisAlignment.center,
children: [
- SvgPicture.asset(Assets.emptyTable),
- const SizedBox(
- height: 15,
+ Column(
+ children: [
+ SvgPicture.asset(Assets.emptyTable),
+ const SizedBox(
+ height: 15,
+ ),
+ Text(
+ widget.tableName == 'AccessManagement' ? 'No Password ' : 'No Devices',
+ style: Theme.of(context)
+ .textTheme
+ .bodySmall!
+ .copyWith(color: ColorsManager.grayColor),
+ )
+ ],
),
- Text(
- // no password
- widget.tableName == 'AccessManagement' ? 'No Password ' : 'No Devices',
- style:
- Theme.of(context).textTheme.bodySmall!.copyWith(color: ColorsManager.grayColor),
- )
],
),
],
+ )
+ : Column(
+ children: List.generate(widget.data.length, (index) {
+ final row = widget.data[index];
+ return Row(
+ children: [
+ if (widget.withCheckBox) _buildRowCheckbox(index, widget.size.height * 0.08),
+ ...row.map((cell) => _buildTableCell(cell.toString(), widget.size.height * 0.08)),
+ ],
+ );
+ }),
),
- ],
- ),
- )
- : Expanded(
- child: Container(
- color: Colors.white,
- child: ListView.builder(
- shrinkWrap: true,
- itemCount: widget.data.length,
- itemBuilder: (context, index) {
- final row = widget.data[index];
- return Row(
- children: [
- if (widget.withCheckBox) _buildRowCheckbox(index, widget.size.height * 0.10),
- ...row.map((cell) => _buildTableCell(cell.toString(), widget.size.height * 0.10)),
- ],
- );
- },
- ),
- ),
- ),
- ],
+ ],
+ ),
+ ),
+ ),
),
),
),
@@ -173,7 +186,6 @@ class _DynamicTableState extends State {
Widget _buildSelectAllCheckbox() {
return Container(
width: 50,
- padding: const EdgeInsets.all(8.0),
decoration: const BoxDecoration(
border: Border.symmetric(
vertical: BorderSide(color: ColorsManager.boxDivider),
@@ -198,6 +210,7 @@ class _DynamicTableState extends State {
width: 1.0,
),
),
+ color: ColorsManager.whiteColors,
),
alignment: Alignment.centerLeft,
child: Center(
@@ -219,15 +232,16 @@ class _DynamicTableState extends State {
vertical: BorderSide(color: ColorsManager.boxDivider),
),
),
+ constraints: const BoxConstraints.expand(height: 40),
alignment: Alignment.centerLeft,
child: Padding(
- padding: const EdgeInsets.all(8.0),
+ padding: const EdgeInsets.symmetric(horizontal: 8.0, vertical: 4),
child: Text(
title,
- style: const TextStyle(
+ style: context.textTheme.titleSmall!.copyWith(
+ color: ColorsManager.grayColor,
+ fontSize: 12,
fontWeight: FontWeight.w400,
- fontSize: 13,
- color: Color(0xFF999999),
),
maxLines: 2,
),
@@ -276,6 +290,7 @@ class _DynamicTableState extends State {
width: 1.0,
),
),
+ color: Colors.white,
),
alignment: Alignment.centerLeft,
child: Text(
@@ -286,7 +301,7 @@ class _DynamicTableState extends State {
: (batteryLevel != null && batteryLevel > 20)
? ColorsManager.green
: statusColor,
- fontSize: 10,
+ fontSize: 13,
fontWeight: FontWeight.w400),
maxLines: 2,
),
diff --git a/lib/pages/common/text_field/custom_web_textfield.dart b/lib/pages/common/text_field/custom_web_textfield.dart
index 756463e2..d5c64e8d 100644
--- a/lib/pages/common/text_field/custom_web_textfield.dart
+++ b/lib/pages/common/text_field/custom_web_textfield.dart
@@ -13,6 +13,7 @@ class CustomWebTextField extends StatelessWidget {
this.validator,
this.hintText,
this.height,
+ this.onSubmitted,
});
final bool isRequired;
@@ -22,6 +23,7 @@ class CustomWebTextField extends StatelessWidget {
final String? Function(String?)? validator;
final String? hintText;
final double? height;
+ final ValueChanged? onSubmitted;
@override
Widget build(BuildContext context) {
@@ -32,33 +34,29 @@ class CustomWebTextField extends StatelessWidget {
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
-
- Row(
- children: [
- if (isRequired)
- Text('* ',
- style: Theme.of(context)
- .textTheme.bodyMedium!
- .copyWith(color: Colors.red),
- ),
+ Row(
+ children: [
+ if (isRequired)
Text(
- textFieldName,
- style: Theme.of(context)
- .textTheme.bodySmall!
- .copyWith(color: Colors.black, fontSize: 13),
+ '* ',
+ style: Theme.of(context).textTheme.bodyMedium!.copyWith(color: Colors.red),
),
- ],
- ),
+ Text(
+ textFieldName,
+ style: Theme.of(context).textTheme.bodySmall!.copyWith(color: Colors.black, fontSize: 13),
+ ),
+ ],
+ ),
const SizedBox(
width: 10,
),
Expanded(
child: Text(
description ?? '',
- style: Theme.of(context).textTheme.bodySmall!.copyWith(
- fontSize: 9,
- fontWeight: FontWeight.w400,
- color: ColorsManager.textGray),
+ style: Theme.of(context)
+ .textTheme
+ .bodySmall!
+ .copyWith(fontSize: 9, fontWeight: FontWeight.w400, color: ColorsManager.textGray),
),
),
],
@@ -68,26 +66,23 @@ class CustomWebTextField extends StatelessWidget {
),
Container(
height: height ?? 35,
- decoration: containerDecoration.copyWith(
- color: const Color(0xFFF5F6F7),
- boxShadow: [
+ decoration: containerDecoration.copyWith(color: const Color(0xFFF5F6F7), boxShadow: [
BoxShadow(
color: Colors.grey.withOpacity(0.3),
spreadRadius: 2,
blurRadius: 3,
offset: const Offset(1, 1), // changes position of shadow
),
- ]
- ),
+ ]),
child: TextFormField(
validator: validator,
controller: controller,
style: const TextStyle(color: Colors.black),
decoration: textBoxDecoration()!.copyWith(
errorStyle: const TextStyle(height: 0),
- hintStyle: context.textTheme.titleSmall!
- .copyWith(color: Colors.grey, fontSize: 12),
+ hintStyle: context.textTheme.titleSmall!.copyWith(color: Colors.grey, fontSize: 12),
hintText: hintText ?? 'Please enter'),
+ onFieldSubmitted: onSubmitted,
),
),
],
diff --git a/lib/pages/device_managment/ac/view/ac_device_control.dart b/lib/pages/device_managment/ac/view/ac_device_control.dart
index 37d3a402..5197d722 100644
--- a/lib/pages/device_managment/ac/view/ac_device_control.dart
+++ b/lib/pages/device_managment/ac/view/ac_device_control.dart
@@ -40,7 +40,7 @@ class AcDeviceControlsView extends StatelessWidget with HelperResponsiveLayout {
: 1,
mainAxisExtent: 140,
crossAxisSpacing: 12,
- mainAxisSpacing: 12,
+ mainAxisSpacing: 16,
),
children: [
ToggleWidget(
@@ -81,6 +81,7 @@ class AcDeviceControlsView extends StatelessWidget with HelperResponsiveLayout {
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
IconButton(
+ padding: const EdgeInsets.all(0),
onPressed: () {},
icon: const Icon(
Icons.remove,
@@ -108,6 +109,7 @@ class AcDeviceControlsView extends StatelessWidget with HelperResponsiveLayout {
),
Text('m', style: context.textTheme.bodySmall!.copyWith(color: ColorsManager.blackColor)),
IconButton(
+ padding: const EdgeInsets.all(0),
onPressed: () {},
icon: const Icon(
Icons.add,
@@ -127,7 +129,7 @@ class AcDeviceControlsView extends StatelessWidget with HelperResponsiveLayout {
deviceId: device.uuid!,
code: 'child_lock',
value: state.status.childLock,
- label: 'Child Lock',
+ label: 'Lock',
icon: state.status.childLock ? Assets.acLock : Assets.unlock,
onChange: (value) {
context.read().add(
diff --git a/lib/pages/device_managment/all_devices/widgets/device_managment_body.dart b/lib/pages/device_managment/all_devices/widgets/device_managment_body.dart
index 2787c7b9..366775bf 100644
--- a/lib/pages/device_managment/all_devices/widgets/device_managment_body.dart
+++ b/lib/pages/device_managment/all_devices/widgets/device_managment_body.dart
@@ -8,7 +8,6 @@ import 'package:syncrow_web/pages/device_managment/all_devices/models/devices_mo
import 'package:syncrow_web/pages/device_managment/all_devices/widgets/device_search_filters.dart';
import 'package:syncrow_web/pages/device_managment/shared/device_batch_control_dialog.dart';
import 'package:syncrow_web/pages/device_managment/shared/device_control_dialog.dart';
-import 'package:syncrow_web/utils/extension/build_context_x.dart';
import 'package:syncrow_web/utils/format_date_time.dart';
import 'package:syncrow_web/utils/helpers/responsice_layout_helper/responsive_layout_helper.dart';
import 'package:syncrow_web/utils/style.dart';
@@ -132,7 +131,7 @@ class DeviceManagementBody extends StatelessWidget with HelperResponsiveLayout {
context.read().add(SelectDevice(selectedDevice));
},
withCheckBox: true,
- size: context.screenSize,
+ size: MediaQuery.of(context).size,
uuidIndex: 2,
headers: const [
'Device Name',
diff --git a/lib/pages/device_managment/gateway/view/gateway_view.dart b/lib/pages/device_managment/gateway/view/gateway_view.dart
index 2bfc6822..d674e4d8 100644
--- a/lib/pages/device_managment/gateway/view/gateway_view.dart
+++ b/lib/pages/device_managment/gateway/view/gateway_view.dart
@@ -5,6 +5,7 @@ import 'package:syncrow_web/pages/device_managment/gateway/bloc/gate_way_bloc.da
import 'package:syncrow_web/pages/device_managment/shared/device_controls_container.dart';
import 'package:syncrow_web/pages/visitor_password/model/device_model.dart';
import 'package:syncrow_web/utils/color_manager.dart';
+import 'package:syncrow_web/utils/extension/build_context_x.dart';
import 'package:syncrow_web/utils/helpers/responsice_layout_helper/responsive_layout_helper.dart';
class GateWayControlsView extends StatelessWidget with HelperResponsiveLayout {
@@ -25,25 +26,61 @@ class GateWayControlsView extends StatelessWidget with HelperResponsiveLayout {
if (state is GatewayLoadingState) {
return const Center(child: CircularProgressIndicator());
} else if (state is UpdateGatewayState) {
- return GridView.builder(
- padding: const EdgeInsets.symmetric(horizontal: 50),
- shrinkWrap: true,
- physics: const NeverScrollableScrollPhysics(),
- gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
- crossAxisCount: isLarge || isExtraLarge
- ? 3
- : isMedium
- ? 2
- : 1,
- mainAxisExtent: 140,
- crossAxisSpacing: 12,
- mainAxisSpacing: 12,
- ),
- itemCount: state.list.length,
- itemBuilder: (context, index) {
- final device = state.list[index];
- return _DeviceItem(device: device);
- },
+ return Column(
+ mainAxisSize: MainAxisSize.min,
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ Container(
+ padding: const EdgeInsets.symmetric(horizontal: 50),
+ child: Column(
+ crossAxisAlignment: CrossAxisAlignment.start,
+ mainAxisSize: MainAxisSize.min,
+ children: [
+ Text(
+ "Bluetooth Devices:",
+ style: context.textTheme.bodyMedium!.copyWith(
+ color: ColorsManager.grayColor,
+ ),
+ ),
+ const SizedBox(height: 12),
+ Text(
+ "No devices found",
+ style: context.textTheme.bodySmall!.copyWith(
+ color: ColorsManager.blackColor,
+ ),
+ ),
+ const SizedBox(height: 30),
+ Text(
+ "ZigBee Devices:",
+ style: context.textTheme.bodyMedium!.copyWith(
+ color: ColorsManager.grayColor,
+ ),
+ ),
+ ],
+ ),
+ ),
+ const SizedBox(height: 12),
+ GridView.builder(
+ padding: const EdgeInsets.symmetric(horizontal: 50),
+ shrinkWrap: true,
+ physics: const NeverScrollableScrollPhysics(),
+ gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
+ crossAxisCount: isLarge || isExtraLarge
+ ? 3
+ : isMedium
+ ? 2
+ : 1,
+ mainAxisExtent: 140,
+ crossAxisSpacing: 12,
+ mainAxisSpacing: 12,
+ ),
+ itemCount: state.list.length,
+ itemBuilder: (context, index) {
+ final device = state.list[index];
+ return _DeviceItem(device: device);
+ },
+ ),
+ ],
);
} else {
return const Center(child: Text('Error fetching status'));
diff --git a/lib/pages/device_managment/shared/device_control_dialog.dart b/lib/pages/device_managment/shared/device_control_dialog.dart
index 14878a46..d7c592d6 100644
--- a/lib/pages/device_managment/shared/device_control_dialog.dart
+++ b/lib/pages/device_managment/shared/device_control_dialog.dart
@@ -1,6 +1,7 @@
import 'package:flutter/material.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/helper/route_controls_based_code.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/models/devices_model.dart';
+import 'package:syncrow_web/pages/device_managment/shared/device_batch_control_dialog.dart';
import 'package:syncrow_web/utils/color_manager.dart';
import 'package:syncrow_web/utils/format_date_time.dart';
@@ -31,7 +32,7 @@ class DeviceControlDialog extends StatelessWidget with RouteControlsBasedCode {
children: [
const SizedBox(),
Text(
- device.productName ?? 'Device Control',
+ getBatchDialogName(device),
style: TextStyle(
fontWeight: FontWeight.bold,
fontSize: 22,
@@ -64,7 +65,7 @@ class DeviceControlDialog extends StatelessWidget with RouteControlsBasedCode {
),
const SizedBox(height: 20),
_buildDeviceInfoSection(),
- const SizedBox(height: 20),
+ //const SizedBox(height: 20),
//// BUILD DEVICE CONTROLS
///
//// ROUTE TO SPECIFIC CONTROL VIEW BASED ON DEVICE CATEGORY
diff --git a/lib/pages/device_managment/shared/device_controls_container.dart b/lib/pages/device_managment/shared/device_controls_container.dart
index 4f1dea59..888563da 100644
--- a/lib/pages/device_managment/shared/device_controls_container.dart
+++ b/lib/pages/device_managment/shared/device_controls_container.dart
@@ -1,5 +1,4 @@
import 'package:flutter/material.dart';
-import 'package:syncrow_web/utils/color_manager.dart';
class DeviceControlsContainer extends StatelessWidget {
const DeviceControlsContainer({required this.child, this.padding, super.key});
@@ -8,21 +7,21 @@ class DeviceControlsContainer extends StatelessWidget {
@override
Widget build(BuildContext context) {
- return Container(
- decoration: BoxDecoration(
+ return Card(
+ shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(20),
- color: ColorsManager.greyColor.withOpacity(0.2),
-
- // boxShadow: [
- // BoxShadow(
- // color: ColorsManager.blackColor.withOpacity(0.05),
- // blurRadius: 6.0,
- // offset: const Offset(0, 5),
- // spreadRadius: 0)
- // ],
),
- padding: EdgeInsets.all(padding ?? 12),
- child: child,
+ elevation: 3,
+ surfaceTintColor: Colors.transparent,
+ child: Container(
+ decoration: BoxDecoration(
+ color: Colors.grey.shade100,
+ borderRadius: BorderRadius.circular(20),
+ ),
+ padding:
+ EdgeInsets.symmetric(vertical: padding ?? 10, horizontal: padding ?? 16), //EdgeInsets.all(padding ?? 12),
+ child: child,
+ ),
);
}
}
diff --git a/lib/utils/constants/assets.dart b/lib/utils/constants/assets.dart
index 4ac64bb6..14f7a15e 100644
--- a/lib/utils/constants/assets.dart
+++ b/lib/utils/constants/assets.dart
@@ -168,4 +168,16 @@ class Assets {
//assets/icons/2gang.svg
static const String twoGang = 'assets/icons/2gang.svg';
+
+ //assets/icons/account_setting.svg
+ static const String accountSetting = 'assets/icons/account_setting.svg';
+
+ //assets/icons/settings.svg
+ static const String settings = 'assets/icons/settings.svg';
+
+ //assets/icons/sign_out.svg
+ static const String signOut = 'assets/icons/sign_out.svg';
+
+ //assets/icons/logo_grey.svg
+ static const String logoGrey = 'assets/icons/logo-grey.svg';
}
diff --git a/lib/utils/theme/theme.dart b/lib/utils/theme/theme.dart
index 413f3243..5ac61afa 100644
--- a/lib/utils/theme/theme.dart
+++ b/lib/utils/theme/theme.dart
@@ -3,6 +3,7 @@ import 'package:syncrow_web/utils/color_manager.dart';
final myTheme = ThemeData(
fontFamily: 'Aftika',
+ useMaterial3: true,
textTheme: const TextTheme(
bodySmall: TextStyle(
fontSize: 13,
diff --git a/lib/utils/user_drop_down_menu.dart b/lib/utils/user_drop_down_menu.dart
new file mode 100644
index 00000000..3a0c4194
--- /dev/null
+++ b/lib/utils/user_drop_down_menu.dart
@@ -0,0 +1,239 @@
+import 'package:flutter/material.dart';
+import 'package:flutter_svg/svg.dart';
+import 'package:go_router/go_router.dart';
+import 'package:syncrow_web/pages/auth/bloc/auth_bloc.dart';
+import 'package:syncrow_web/pages/auth/model/user_model.dart';
+import 'package:syncrow_web/pages/common/buttons/default_button.dart';
+import 'package:syncrow_web/utils/color_manager.dart';
+import 'package:syncrow_web/utils/constants/assets.dart';
+import 'package:syncrow_web/utils/constants/routes_const.dart';
+import 'package:syncrow_web/utils/extension/build_context_x.dart';
+
+class UserDropdownMenu extends StatefulWidget {
+ const UserDropdownMenu({super.key, required this.user});
+ final UserModel? user;
+
+ @override
+ _UserDropdownMenuState createState() => _UserDropdownMenuState();
+}
+
+class _UserDropdownMenuState extends State {
+ bool _isDropdownOpen = false;
+
+ void _toggleDropdown() {
+ setState(() {
+ _isDropdownOpen = !_isDropdownOpen;
+ });
+ }
+
+ @override
+ Widget build(BuildContext context) {
+ return Column(
+ mainAxisSize: MainAxisSize.min,
+ children: [
+ GestureDetector(
+ onTap: () async {
+ _toggleDropdown();
+ await _showPopupMenu(context);
+ setState(() {
+ _isDropdownOpen = false;
+ });
+ },
+ child: Transform.rotate(
+ angle: _isDropdownOpen ? -1.5708 : 1.5708,
+ child: const Icon(
+ Icons.arrow_forward_ios,
+ color: Colors.white,
+ size: 16,
+ ),
+ ),
+ ),
+ ],
+ );
+ }
+
+ Future _showPopupMenu(BuildContext context) async {
+ final RenderBox overlay = Overlay.of(context).context.findRenderObject() as RenderBox;
+ final RelativeRect position = RelativeRect.fromRect(
+ Rect.fromLTRB(
+ overlay.size.width,
+ 75,
+ 0,
+ overlay.size.height,
+ ),
+ Offset.zero & overlay.size,
+ );
+
+ await showMenu(
+ context: context,
+ position: position,
+ color: ColorsManager.whiteColors,
+ shape: const RoundedRectangleBorder(
+ borderRadius: BorderRadius.only(
+ bottomRight: Radius.circular(10),
+ bottomLeft: Radius.circular(10),
+ ),
+ ),
+ items: [
+ PopupMenuItem(
+ onTap: () {},
+ child: ListTile(
+ leading: SvgPicture.asset(Assets.accountSetting),
+ title: Text(
+ "Account Settings",
+ style: context.textTheme.bodyMedium,
+ ),
+ ),
+ ),
+ PopupMenuItem(
+ onTap: () {},
+ child: ListTile(
+ leading: SvgPicture.asset(Assets.settings),
+ title: Text(
+ "Settings",
+ style: context.textTheme.bodyMedium,
+ ),
+ ),
+ ),
+ PopupMenuItem(
+ onTap: () {
+ showDialog(
+ context: context,
+ builder: (BuildContext context) {
+ final size = MediaQuery.of(context).size;
+ return AlertDialog(
+ alignment: Alignment.center,
+ content: SizedBox(
+ height: 200,
+ width: 400,
+ child: Padding(
+ padding: const EdgeInsets.only(top: 24, left: 24, right: 24),
+ child: Column(
+ mainAxisAlignment: MainAxisAlignment.start,
+ children: [
+ Image.asset(
+ Assets.blackLogo,
+ height: 40,
+ width: 200,
+ ),
+ Padding(
+ padding: const EdgeInsets.only(top: 16),
+ child: Text(
+ 'Log out of your Syncrow account',
+ style: Theme.of(context).textTheme.bodyMedium!.copyWith(
+ fontSize: 14,
+ fontWeight: FontWeight.w400,
+ color: Colors.black,
+ ),
+ ),
+ ),
+ const SizedBox(
+ height: 16,
+ ),
+ Row(
+ children: [
+ SizedBox.square(
+ dimension: 80,
+ child: CircleAvatar(
+ backgroundColor: ColorsManager.whiteColors,
+ child: SizedBox.square(
+ dimension: 78,
+ child: SvgPicture.asset(
+ Assets.logoGrey,
+ fit: BoxFit.fitHeight,
+ height: 80,
+ ),
+ ),
+ ),
+ ),
+ const SizedBox(
+ width: 16,
+ ),
+ Expanded(
+ child: Column(
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ Text(
+ '${widget.user?.firstName ?? ''} ${widget.user?.lastName}',
+ style: Theme.of(context).textTheme.titleMedium!.copyWith(
+ color: Colors.black,
+ fontWeight: FontWeight.bold,
+ fontSize: 20,
+ ),
+ ),
+ Text(
+ ' ${widget.user?.email}',
+ style: Theme.of(context).textTheme.bodySmall!.copyWith(
+ color: Colors.black,
+ ),
+ ),
+ ],
+ ),
+ ),
+ ],
+ ),
+ ],
+ ),
+ ),
+ ),
+ actionsAlignment: MainAxisAlignment.center,
+ actions: [
+ SizedBox(
+ width: 200,
+ child: GestureDetector(
+ onTap: () {
+ context.pop();
+ },
+ child: DefaultButton(
+ backgroundColor: ColorsManager.boxColor,
+ elevation: 1,
+ child: Text(
+ 'Cancel',
+ style: Theme.of(context).textTheme.bodyMedium!.copyWith(
+ fontSize: 12,
+ color: Colors.black,
+ ),
+ ),
+ ),
+ ),
+ ),
+ const SizedBox(
+ height: 10,
+ ),
+ GestureDetector(
+ onTap: () {
+ AuthBloc.logout();
+ context.go(RoutesConst.auth);
+ },
+ child: SizedBox(
+ width: 200,
+ child: DefaultButton(
+ elevation: 1,
+ child: Text(
+ 'Logout',
+ style:
+ Theme.of(context).textTheme.bodyMedium!.copyWith(fontSize: 12, color: Colors.white),
+ ),
+ ),
+ ),
+ ),
+ ]);
+ },
+ );
+ },
+ child: ListTile(
+ leading: SvgPicture.asset(Assets.signOut),
+ title: Text(
+ "Log Out",
+ style: context.textTheme.bodyMedium,
+ ),
+ ),
+ ),
+ ],
+ ).then((value) {
+ setState(() {
+ _isDropdownOpen = false;
+ });
+ });
+ }
+}
diff --git a/lib/web_layout/web_app_bar.dart b/lib/web_layout/web_app_bar.dart
index 1052a23d..777b0931 100644
--- a/lib/web_layout/web_app_bar.dart
+++ b/lib/web_layout/web_app_bar.dart
@@ -1,14 +1,12 @@
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
-import 'package:go_router/go_router.dart';
-import 'package:syncrow_web/pages/auth/bloc/auth_bloc.dart';
-import 'package:syncrow_web/pages/common/buttons/default_button.dart';
-import 'package:syncrow_web/pages/common/custom_dialog.dart';
+import 'package:flutter_svg/flutter_svg.dart';
import 'package:syncrow_web/pages/home/bloc/home_bloc.dart';
import 'package:syncrow_web/pages/home/bloc/home_state.dart';
import 'package:syncrow_web/utils/color_manager.dart';
-import 'package:syncrow_web/utils/constants/routes_const.dart';
+import 'package:syncrow_web/utils/constants/assets.dart';
import 'package:syncrow_web/utils/helpers/responsice_layout_helper/responsive_layout_helper.dart';
+import 'package:syncrow_web/utils/user_drop_down_menu.dart';
class WebAppBar extends StatefulWidget {
final Widget? title;
@@ -58,15 +56,15 @@ class _WebAppBarState extends State with HelperResponsiveLayout {
if (widget.rightBody != null) widget.rightBody!,
Row(
children: [
- const SizedBox.square(
+ SizedBox.square(
dimension: 40,
child: CircleAvatar(
- backgroundColor: Colors.white,
+ backgroundColor: ColorsManager.whiteColors,
child: SizedBox.square(
dimension: 35,
- child: CircleAvatar(
- backgroundColor: Colors.grey,
- child: FlutterLogo(),
+ child: SvgPicture.asset(
+ Assets.logoGrey,
+ fit: BoxFit.cover,
),
),
),
@@ -112,15 +110,15 @@ class _WebAppBarState extends State with HelperResponsiveLayout {
const SizedBox(
width: 10,
),
- const SizedBox.square(
+ SizedBox.square(
dimension: 40,
child: CircleAvatar(
- backgroundColor: Colors.white,
+ backgroundColor: ColorsManager.whiteColors,
child: SizedBox.square(
dimension: 35,
- child: CircleAvatar(
- backgroundColor: Colors.grey,
- child: FlutterLogo(),
+ child: SvgPicture.asset(
+ Assets.logoGrey,
+ fit: BoxFit.cover,
),
),
),
@@ -136,54 +134,55 @@ class _WebAppBarState extends State with HelperResponsiveLayout {
const SizedBox(
width: 10,
),
- GestureDetector(
- onTap: () {
- showCustomDialog(
- context: context,
- barrierDismissible: true,
- title: 'Logout',
- message: 'Are you sure you want to logout?',
- actions: [
- GestureDetector(
- onTap: () {
- AuthBloc.logout();
- context.go(RoutesConst.auth);
- },
- child: DefaultButton(
- child: Text(
- 'Ok',
- style: Theme.of(context)
- .textTheme
- .bodyMedium!
- .copyWith(fontSize: 12, color: Colors.white),
- ),
- ),
- ),
- const SizedBox(
- height: 10,
- ),
- GestureDetector(
- onTap: () {
- context.pop();
- },
- child: DefaultButton(
- child: Text(
- 'Cancel',
- style: Theme.of(context)
- .textTheme
- .bodyMedium!
- .copyWith(fontSize: 12, color: Colors.white),
- ),
- ),
- ),
- ],
- );
- },
- child: const Icon(
- Icons.logout,
- color: ColorsManager.whiteColors,
- ),
- )
+ UserDropdownMenu(user: user),
+ // GestureDetector(
+ // onTap: () {
+ // showCustomDialog(
+ // context: context,
+ // barrierDismissible: true,
+ // title: 'Logout',
+ // message: 'Are you sure you want to logout?',
+ // actions: [
+ // GestureDetector(
+ // onTap: () {
+ // AuthBloc.logout();
+ // context.go(RoutesConst.auth);
+ // },
+ // child: DefaultButton(
+ // child: Text(
+ // 'Ok',
+ // style: Theme.of(context)
+ // .textTheme
+ // .bodyMedium!
+ // .copyWith(fontSize: 12, color: Colors.white),
+ // ),
+ // ),
+ // ),
+ // const SizedBox(
+ // height: 10,
+ // ),
+ // GestureDetector(
+ // onTap: () {
+ // context.pop();
+ // },
+ // child: DefaultButton(
+ // child: Text(
+ // 'Cancel',
+ // style: Theme.of(context)
+ // .textTheme
+ // .bodyMedium!
+ // .copyWith(fontSize: 12, color: Colors.white),
+ // ),
+ // ),
+ // ),
+ // ],
+ // );
+ // },
+ // child: const Icon(
+ // Icons.logout,
+ // color: ColorsManager.whiteColors,
+ // ),
+ // )
],
),
],