diff --git a/assets/images/comment_send.svg b/assets/images/comment_send.svg
new file mode 100644
index 00000000..a332cc45
--- /dev/null
+++ b/assets/images/comment_send.svg
@@ -0,0 +1,3 @@
+
diff --git a/flutter_gen.yaml b/flutter_gen.yaml
new file mode 100644
index 00000000..17c1af22
--- /dev/null
+++ b/flutter_gen.yaml
@@ -0,0 +1,2 @@
+assets:
+ - assets/images/
diff --git a/lib/extensions/text_extensions.dart b/lib/extensions/text_extensions.dart
index b6767296..7a08a656 100644
--- a/lib/extensions/text_extensions.dart
+++ b/lib/extensions/text_extensions.dart
@@ -46,7 +46,6 @@ abstract class AppTextStyles {
static final TextStyle heading1 = TextStyle(
fontSize: 54.toScreenWidth,
fontWeight: FontWeight.w500,
- height: 0.89,
letterSpacing: -0.81,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
@@ -55,7 +54,6 @@ abstract class AppTextStyles {
static final TextStyle heading2 = TextStyle(
fontSize: 28.toScreenWidth,
fontWeight: FontWeight.w700,
- height: 1.5,
letterSpacing: -0.56,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
@@ -64,7 +62,6 @@ abstract class AppTextStyles {
static final TextStyle heading3 = TextStyle(
fontSize: 24.toScreenWidth,
fontWeight: FontWeight.w700,
- height: 1.5,
letterSpacing: -0.12,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
@@ -73,7 +70,6 @@ abstract class AppTextStyles {
static final TextStyle heading4 = TextStyle(
fontSize: 21.toScreenWidth,
fontWeight: FontWeight.w500,
- height: 1.48,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
);
@@ -81,7 +77,6 @@ abstract class AppTextStyles {
static final TextStyle heading5 = TextStyle(
fontSize: 19.toScreenWidth,
fontWeight: FontWeight.w500,
- //height: 1.47,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
);
@@ -89,7 +84,6 @@ abstract class AppTextStyles {
static final TextStyle heading6 = TextStyle(
fontSize: 16.toScreenWidth,
fontWeight: FontWeight.w500,
- height: 1.5,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
);
@@ -97,7 +91,6 @@ abstract class AppTextStyles {
static final TextStyle bodyText = TextStyle(
fontSize: 14.toScreenWidth,
fontWeight: FontWeight.w500,
- height: 1.5,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
);
@@ -105,7 +98,6 @@ abstract class AppTextStyles {
static final TextStyle bodyText2 = TextStyle(
fontSize: 12.toScreenWidth,
fontWeight: FontWeight.w500,
- height: 1.5,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
);
@@ -113,7 +105,6 @@ abstract class AppTextStyles {
static final TextStyle tinyFont = TextStyle(
fontSize: 11.toScreenWidth,
fontWeight: FontWeight.w500,
- height: 1.45,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
);
@@ -121,7 +112,6 @@ abstract class AppTextStyles {
static final TextStyle overline = TextStyle(
fontSize: 9.toScreenWidth,
fontWeight: FontWeight.w500,
- height: 1.56,
letterSpacing: 0.05,
fontStyle: FontStyle.normal,
decoration: TextDecoration.none,
diff --git a/lib/l10n/app_ar.arb b/lib/l10n/app_ar.arb
index a07a6771..e3e12807 100644
--- a/lib/l10n/app_ar.arb
+++ b/lib/l10n/app_ar.arb
@@ -251,5 +251,6 @@
"model" : "الطراز",
"serialNumber" : "الرقم التسلسلي",
"device" : "الجهاز",
- "pickAsset" : "إختر جهاز"
+ "pickAsset" : "إختر جهاز",
+ "firstAction" : "First Action"
}
\ No newline at end of file
diff --git a/lib/l10n/app_en.arb b/lib/l10n/app_en.arb
index 57522750..ec5fbcf8 100644
--- a/lib/l10n/app_en.arb
+++ b/lib/l10n/app_en.arb
@@ -251,5 +251,8 @@
"model" : "Model",
"serialNumber" : "Serial Number",
"device" : "Device",
- "pickAsset" : "Pick Asset"
+ "pickAsset" : "Pick Asset",
+ "firstAction" : "First Action",
+ "workOrder" : "Work Orders",
+ "viewWorkOrder" : "View All Work Order"
}
\ No newline at end of file
diff --git a/lib/main.dart b/lib/main.dart
index 110f3295..ddcac114 100644
--- a/lib/main.dart
+++ b/lib/main.dart
@@ -67,6 +67,7 @@ import 'package:test_sa/views/pages/user/report_issues_page.dart';
import 'package:test_sa/views/pages/user/requests/create_request.dart';
import 'package:test_sa/views/pages/user/requests/future_request_service_details.dart';
import 'package:test_sa/views/pages/user/requests/requests_page.dart';
+import 'package:test_sa/views/pages/user/requests/work_order/work_orders_list_page.dart';
import 'package:test_sa/views/pages/user/visits/preventive_maintenance_visits_page.dart';
import 'package:test_sa/views/pages/user/visits/regular_visits_page.dart';
import 'package:test_sa/views/widgets/departments/single_department_picker.dart';
@@ -197,6 +198,7 @@ class MyApp extends StatelessWidget {
TrackDeviceTransferPage.id: (_) => const TrackDeviceTransferPage(),
SearchSubWorkOrderPage.id: (_) => const SearchSubWorkOrderPage(),
CreateSubWorkOrderPage.id: (_) => const CreateSubWorkOrderPage(),
+ WorkOrderListPage.id: (_) => WorkOrderListPage(),
},
),
),
diff --git a/lib/new_views/app_style/app_text_style.dart b/lib/new_views/app_style/app_text_style.dart
index 436ec40d..6ebea2eb 100644
--- a/lib/new_views/app_style/app_text_style.dart
+++ b/lib/new_views/app_style/app_text_style.dart
@@ -68,7 +68,7 @@ class AppTextStyle {
decoration: TextDecoration.none,
);
static final TextStyle tiny = TextStyle(
- height: 1.5,
+ //height: 1.5,
fontSize: 11.toScreenWidth,
letterSpacing: 0,
fontFamily: fontFamily,
diff --git a/lib/views/pages/user/requests/future_request_service_details.dart b/lib/views/pages/user/requests/future_request_service_details.dart
index fc98bda9..27096f9c 100644
--- a/lib/views/pages/user/requests/future_request_service_details.dart
+++ b/lib/views/pages/user/requests/future_request_service_details.dart
@@ -7,7 +7,7 @@ import 'package:test_sa/controllers/providers/settings/setting_provider.dart';
import 'package:test_sa/extensions/context_extension.dart';
import 'package:test_sa/models/service_request/service_request.dart';
import 'package:test_sa/models/subtitle.dart';
-import 'package:test_sa/views/pages/user/requests/request_details.dart';
+import 'package:test_sa/views/pages/user/requests/service_request_details.dart';
import 'package:test_sa/views/widgets/loaders/app_loading.dart';
import 'package:test_sa/views/widgets/loaders/failed_loading.dart';
@@ -40,7 +40,7 @@ class _FutureRequestServiceDetailsState extends State(context);
- SettingProvider _settingProvider = Provider.of(context);
- List workOrders = [];
- ServiceRequestsProvider _serviceRequestsProvider = Provider.of(context);
- _serviceRequestsProvider.getServiceRequestObjectById(requestId: serviceRequest.id);
-
- Widget informationCard() {
- return Container(
- decoration: ShapeDecoration(
- color: Colors.white,
- shape: RoundedRectangleBorder(
- borderRadius: BorderRadius.circular(20),
- ),
- shadows: const [BoxShadow(color: Color(0x07000000), blurRadius: 14, offset: Offset(0, 0), spreadRadius: 0)],
- ),
- child: Column(
- children: [
- Column(
- mainAxisSize: MainAxisSize.min,
- crossAxisAlignment: CrossAxisAlignment.start,
- children: [
- Row(
- crossAxisAlignment: CrossAxisAlignment.start,
- children: [
- StatusLabel(
- label: serviceRequest.priority.name,
- id: serviceRequest.priority.id,
- textColor: AColors.getPriorityStatusTextColor(serviceRequest.priority.id),
- backgroundColor: AColors.getPriorityStatusColor(serviceRequest.priority.id)),
- 8.width,
- StatusLabel(
- label: serviceRequest.statusLabel,
- textColor: AColors.getRequestStatusTextColor(serviceRequest.statusValue),
- backgroundColor: AColors.getRequestStatusColor(serviceRequest.statusValue)),
- 1.width.expanded,
- Text(serviceRequest.date.toServiceRequestCardFormat, textAlign: TextAlign.end, style: AppTextStyles.tinyFont.copyWith(color: const Color(0xFF3B3D4A))),
- ],
- ),
- 8.height,
- Text(serviceRequest.deviceEnName, style: AppTextStyles.heading5.copyWith(color: const Color(0xFF3B3D4A))),
- Text(
- '${context.translation.assetNumber}: ${serviceRequest.device.assetNumber}',
- style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
- ),
- Text(
- 'Request Type: ${serviceRequest.type.name}',
- style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
- ),
- Text(
- 'Request No: ${serviceRequest.requestCode}',
- style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
- ),
- 8.height,
- const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
- 8.height,
- Text(
- 'Manufacture: ${serviceRequest.device.modelDefinition.manufacturerName}',
- style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
- ),
- Text(
- 'Model: ${serviceRequest.device.modelDefinition.modelName}',
- style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
- ),
- 8.height,
- const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
- 8.height,
- if ((serviceRequest.callComments ?? "").isNotEmpty) ...[
- Text(
- serviceRequest.callComments,
- style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
- ),
- 8.height,
- const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
- ],
- if (serviceRequest.devicePhotos.isNotEmpty) ...[
- FilesList(images: serviceRequest.devicePhotos),
- const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
- ],
- if (serviceRequest.audio?.isNotEmpty == true) ...[
- 16.height,
- ASoundPlayer(
- audio: serviceRequest.audio,
- ),
- 16.height,
- const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
- ],
- Row(
- mainAxisSize: MainAxisSize.min,
- children: [
- Text(
- 'View Comments',
- style: AppTextStyles.bodyText.copyWith(color: const Color(0xFF4A8DB7)),
- ),
- 4.width,
- const Icon(
- Icons.arrow_forward,
- color: Color(0xFF4A8DB7),
- size: 14,
- )
- ],
- ),
- ],
- ).paddingAll(16),
- ],
- ),
- );
- }
-
- return DefaultTabController(
- length: 2,
- child: Scaffold(
- appBar: DefaultAppBar(title: context.translation.serviceRequest),
- backgroundColor: const Color(0xfff8f9fb),
- body: SafeArea(
- child: FutureBuilder(
- future: _serviceRequestsProvider.getServiceRequestObjectById(requestId: serviceRequest.id),
- builder: (context, snap) {
- if (snap.connectionState == ConnectionState.waiting) {
- return const ALoading();
- } else if (snap.hasData) {
- serviceRequest = snap.data;
- return Column(
- children: [
- Container(
- color: AColors.primaryColor,
- padding: const EdgeInsets.symmetric(horizontal: 0, vertical: 4),
- child: Row(
- children: [
- ABackButton(),
- Expanded(
- child: Center(
- child: Text(
- context.translation.details,
- style: Theme.of(context).textTheme.headline6.copyWith(color: AColors.white, fontStyle: FontStyle.italic),
- ),
- ),
- ),
- _userProvider.user.type == UsersTypes.normal_user
- ?
- // AIconButton(
- // iconData: Icons.warning_amber_rounded,
- // color: AColors.white,
- // buttonSize: 42,
- // backgroundColor: AColors.deepOrange,
- // onPressed: (){
- // Navigator.of(context).push(
- // MaterialPageRoute(
- // builder: (_) => ReportIssuesPage(serviceRequest: serviceRequest,)
- // )
- // );
- // },
- // )
- const SizedBox(
- width: 48,
- )
- : AIconButton(
- iconData: Icons.edit,
- color: AColors.white,
- buttonSize: 42,
- backgroundColor: AColors.green,
- onPressed: (serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3)
- ? null
- : () async {
- Navigator.of(context).push(
- MaterialPageRoute(builder: (_) => CreateRequestPage(serviceRequest: serviceRequest)),
- );
- // showModalBottomSheet(
- // context: context,
- // builder: (context) {
- // return ServiceRequestsUpdateDialog(
- // request: serviceRequest,
- // );
- // });
- // DateTime picked = await showDatePicker(
- // context: context,
- // initialDate: DateTime.now(),
- // firstDate: DateTime.now(),
- // lastDate: DateTime.now().add(Duration(days: 182))
- // );
- // if(picked == null){return;}
- // showDialog(
- // context: context,
- // barrierDismissible: false,
- // builder: (BuildContext context) {
- // return CupertinoAlertDialog(
- // title: Text(context.translation.updatingDots),
- // content: Center(child: CircularProgressIndicator()),
- // );
- // },
- // );
- // int status = await _serviceRequestsProvider.updateDate(
- // user: _userProvider.user,
- // host: _settingProvider.host,
- // request: serviceRequest,
- // newDate: picked.toString().split(" ").first
- // );
- // Navigator.of(context).pop();
- // Fluttertoast.showToast(
- // msg: HttpStatusManger.getStatusMessage(status: status, subtitle: context.translation),
- // );
- },
- ),
- SizedBox(
- width: 16,
- )
- ],
- ),
- ),
- serviceRequest.devicePhotos.isEmpty
- ? const SizedBox.shrink()
- : SizedBox(
- height: 60 * AppStyle.getScaleFactor(context),
- child: FilesList(
- images: serviceRequest.devicePhotos,
- ),
- ).paddingOnly(top: 4, bottom: 4),
- TabBar(labelColor: AColors.primaryColor, tabs: [
- Tab(
- text: context.translation.general,
- ),
- Tab(
- text: context.translation.serviceRequestInformation,
- ),
- ]),
- SizedBox(
- height: 8,
- ),
- Expanded(
- child: TabBarView(
- children: [
- Column(
- children: [
- ListView(
- padding: const EdgeInsets.all(16),
- children: [
- informationCard(),
- RequestInfoRow(
- title: context.translation.callId,
- info: serviceRequest.requestCode,
- ),
- RequestInfoRow(
- title: "Asset Number",
- info: serviceRequest.deviceNumber,
- ),
- RequestInfoRow(
- title: context.translation.assetName,
- info: serviceRequest.deviceEnName,
- ),
- RequestInfoRow(
- title: context.translation.deviceModel,
- info: serviceRequest.deviceModel,
- ),
- RequestInfoRow(
- title: context.translation.engineerName,
- info: serviceRequest.engineerName,
- ),
- RequestInfoRow(
- title: context.translation.engineerPhone,
- info: serviceRequest.engineerMobile,
- ),
- RequestInfoRow(
- title: context.translation.date,
- info: serviceRequest.date,
- ),
- serviceRequest.nextVisitDate == null
- ? SizedBox.shrink()
- : RequestInfoRow(
- title: context.translation.next,
- info: DateFormat('EE dd/MM/yyyy').format(serviceRequest.nextVisitDate),
- ),
- Row(
- children: [
- Expanded(
- child: Text(
- "${context.translation.status} : ",
- style: Theme.of(context).textTheme.subtitle1,
- textScaleFactor: AppStyle.getScaleFactor(context),
- ),
- ),
- StatusLabel(label: serviceRequest.statusLabel, backgroundColor: AColors.getRequestStatusColor(serviceRequest.statusValue)),
- ],
- ),
- Divider(
- color: Theme.of(context).primaryColor,
- ),
- RequestInfoRow(
- title: context.translation.hospital,
- info: serviceRequest.hospitalName,
- ),
- RequestInfoRow(
- title: context.translation.unite,
- info: serviceRequest.departmentName,
- ),
- // RequestInfoRow(
- // title: context.translation.deviceArName,
- // content: serviceRequest.deviceArName,
- // ),
- // RequestInfoRow(
- // title: context.translation.deviceName,
- // content: serviceRequest.deviceEnName,
- // ),
- RequestInfoRow(
- title: context.translation.maintenanceIssue,
- content: serviceRequest.callComments,
- ),
- if (serviceRequest.audio?.isNotEmpty == true)
- ASoundPlayer(
- audio: serviceRequest.audio,
- ),
- //
- // Center(
- // child: Padding(
- // padding: EdgeInsets.all(32),
- // child: AButton(
- // text: context.translation.duplicateRequest,
- // onPressed: () async {
- // bool result = await showDialog(
- // context: context,
- // builder: (_) => AAlertDialog(
- // title: context.translation.duplicateAlert,
- // content: context.translation.duplicateAlertMessage,
- // )
- // );
- // if(result == true){
- // showDialog(
- // context: context,
- // builder: (context){
- // return Center(child: CircularProgressIndicator());
- // }
- // );
- // int status = await _serviceRequestsProvider.createDuplicatedReport(
- // host: _settingProvider.host,
- // user: _userProvider.user,
- // request: serviceRequest
- // );
- // Navigator.of(context).pop();
- // ScaffoldMessenger.of(context).showSnackBar(
- // SnackBar(
- // content: Text(
- // HttpStatusManger.getStatusMessage(status: status, subtitle: context.translation)
- // )
- // )
- // );
- // }
- // },
- // ),
- // ),
- // )
- ],
- ).expanded,
- AppFilledButton(label: context.translation.login, maxWidth: true, onPressed: () {}).paddingOnly(start: 16, end: 16, bottom: 24),
- ],
- ),
- // workOrders.isEmpty ?
- FutureBuilder(
- future: _serviceRequestsProvider.searchWorkOrders(callId: serviceRequest.requestCode),
- builder: (context, snap) {
- workOrders = snap.data as List;
- if (snap.connectionState == ConnectionState.waiting) return Center(child: CircularProgressIndicator());
- if (snap.connectionState == ConnectionState.done && (snap.data?.length ?? 0) != 0) {
- return SingleChildScrollView(
- child: Column(
- children: [
- ListView.separated(
- shrinkWrap: true,
- physics: const NeverScrollableScrollPhysics(),
- padding: EdgeInsets.all(21),
- itemCount: workOrders.length,
- separatorBuilder: (czt, index) => 21.height,
- itemBuilder: (context, index) {
- Color itemColor = index % 2 == 0 ? Theme.of(context).colorScheme.primary : Theme.of(context).colorScheme.onPrimary;
- Color onItemColor = index % 2 != 0 ? Theme.of(context).colorScheme.primary : Theme.of(context).colorScheme.onPrimary;
-
- return ElevatedButton(
- style: ElevatedButton.styleFrom(
- padding: EdgeInsets.symmetric(vertical: 8, horizontal: 8),
- primary: itemColor.withOpacity(.7),
- shape: RoundedRectangleBorder(
- borderRadius: BorderRadius.circular(AppStyle.getBorderRadius(context)),
- ),
- ),
- //padding: EdgeInsets.symmetric(vertical: 8,horizontal: 8),
- onPressed: () {
- // onPressed(request);
- },
- child: Column(
- children: [
- RequestInfoRow(
- title: context.translation.callId,
- content: serviceRequest.requestCode,
- ),
- RequestInfoRow(
- title: context.translation.orderWorkNumber,
- info: workOrders[index].workOrderNo.toString(),
- ),
- RequestInfoRow(
- title: context.translation.visitDate,
- info: workOrders[index].visitDate,
- ),
- RequestInfoRow(title: context.translation.assignedEmployee, info: workOrders[index].assignedEmployee?.name ?? ""),
- RequestInfoRow(
- title: context.translation.assetSN,
- info: workOrders[index].callRequest.asset.assetSerialNo,
- ),
- RequestInfoRow(
- title: context.translation.assetName,
- info: workOrders[index].callRequest.asset.modelDefinition.assetName,
- ),
- RequestInfoRow(
- title: context.translation.assetNumber,
- info: workOrders[index].callRequest.asset.assetNumber,
- ),
- RequestInfoRow(
- title: context.translation.model,
- info: workOrders[index].callRequest.asset.modelDefinition.modelName,
- ),
- RequestInfoRow(
- title: context.translation.site,
- info: workOrders[index].callRequest.asset.site.custName,
- ),
- RequestInfoRow(
- title: "Call last Situation",
- info: workOrders[index].currentSituation.name ?? '',
- ),
- _userProvider.user.type == UsersTypes.engineer && workOrders[index].workOrderNo != null
- ? Padding(
- padding: EdgeInsets.all(32),
- child: AButton(
- text: context.translation.editServiceReport,
- onPressed: serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3
- ? null
- : () {
- Navigator.of(context).push(
- MaterialPageRoute(
- builder: (_) => FutureServiceReport(
- request: serviceRequest,
- workOrder: workOrders[index],
- )),
- );
- },
- ),
- )
- : SizedBox.shrink(),
- ],
- ),
- );
- },
- ),
- if (_userProvider.user.type == UsersTypes.engineer)
- Center(
- child: Padding(
- padding: const EdgeInsets.all(32),
- child: AButton(
- text: "Create Work Order",
- onPressed: serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3
- ? null
- : () {
- Navigator.of(context).push(MaterialPageRoute(builder: (_) => CreateServiceReport(request: serviceRequest)));
- },
- ),
- ),
- ),
- ],
- ),
- );
- } else {
- return Column(
- children: [
- Expanded(
- child: Center(
- child: ASubTitle(context.translation.dataNotFound),
- ),
- ),
- if (_userProvider.user.type == UsersTypes.engineer)
- Center(
- child: Padding(
- padding: const EdgeInsets.all(32),
- child: AButton(
- text: "Create Work Order",
- onPressed: serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3
- ? null
- : () {
- Navigator.of(context).push(MaterialPageRoute(builder: (_) => CreateServiceReport(request: serviceRequest)));
- },
- ),
- ),
- ),
- ],
- );
- }
- },
- ),
- ],
- ),
- ),
- ],
- );
- }
- return const SizedBox();
- }),
- ),
- ),
- );
- }
-}
diff --git a/lib/views/pages/user/requests/service_request_details.dart b/lib/views/pages/user/requests/service_request_details.dart
new file mode 100644
index 00000000..86f83c4f
--- /dev/null
+++ b/lib/views/pages/user/requests/service_request_details.dart
@@ -0,0 +1,228 @@
+import 'package:flutter/material.dart';
+import 'package:flutter_svg/flutter_svg.dart';
+import 'package:intl/intl.dart';
+import 'package:provider/provider.dart';
+import 'package:test_sa/controllers/localization/localization.dart';
+import 'package:test_sa/controllers/providers/api/service_requests_provider.dart';
+import 'package:test_sa/controllers/providers/api/user_provider.dart';
+import 'package:test_sa/controllers/providers/settings/setting_provider.dart';
+import 'package:test_sa/extensions/context_extension.dart';
+import 'package:test_sa/extensions/int_extensions.dart';
+import 'package:test_sa/extensions/string_extensions.dart';
+import 'package:test_sa/extensions/text_extensions.dart';
+import 'package:test_sa/extensions/widget_extensions.dart';
+import 'package:test_sa/models/enums/translation_keys.dart';
+import 'package:test_sa/models/enums/user_types.dart';
+import 'package:test_sa/models/service_request/service_request.dart';
+import 'package:test_sa/models/subtitle.dart';
+import 'package:test_sa/new_views/app_style/app_color.dart';
+import 'package:test_sa/new_views/common_widgets/app_filled_button.dart';
+import 'package:test_sa/new_views/common_widgets/default_app_bar.dart';
+import 'package:test_sa/views/app_style/colors.dart';
+import 'package:test_sa/views/app_style/sizing.dart';
+import 'package:test_sa/views/pages/user/requests/create_request.dart';
+import 'package:test_sa/views/pages/user/requests/work_order/create_service_report.dart';
+import 'package:test_sa/views/pages/user/requests/work_order/future_service_report.dart';
+import 'package:test_sa/views/pages/user/requests/work_order/work_orders_list_page.dart';
+import 'package:test_sa/views/widgets/buttons/app_back_button.dart';
+import 'package:test_sa/views/widgets/buttons/app_button.dart';
+import 'package:test_sa/views/widgets/buttons/app_icon_button.dart';
+import 'package:test_sa/views/widgets/images/files_list.dart';
+import 'package:test_sa/views/widgets/loaders/app_loading.dart';
+import 'package:test_sa/views/widgets/requests/info_row.dart';
+import 'package:test_sa/views/widgets/requests/request_status.dart';
+import 'package:test_sa/views/widgets/sound/sound_player.dart';
+import 'package:test_sa/views/widgets/titles/app_sub_title.dart';
+import '../../../../models/service_request/search_work_order.dart';
+
+class ServiceRequestDetailsPage extends StatelessWidget {
+ static const String id = "/call-details";
+ ServiceRequest serviceRequest;
+
+ ServiceRequestDetailsPage({Key key, this.serviceRequest}) : super(key: key);
+
+ @override
+ Widget build(BuildContext context) {
+ UserProvider _userProvider = Provider.of(context);
+ ServiceRequestsProvider _serviceRequestsProvider = Provider.of(context);
+ // _serviceRequestsProvider.getServiceRequestObjectById(requestId: serviceRequest.id);
+
+ Widget informationCard() {
+ return Container(
+ decoration: ShapeDecoration(
+ color: Colors.white,
+ shape: RoundedRectangleBorder(
+ borderRadius: BorderRadius.circular(20),
+ ),
+ shadows: const [BoxShadow(color: Color(0x07000000), blurRadius: 14, offset: Offset(0, 0), spreadRadius: 0)],
+ ),
+ child: Column(
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ Column(
+ mainAxisSize: MainAxisSize.min,
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ Row(
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ StatusLabel(
+ label: serviceRequest.priority.name,
+ id: serviceRequest.priority.id,
+ textColor: AColors.getPriorityStatusTextColor(serviceRequest.priority.id),
+ backgroundColor: AColors.getPriorityStatusColor(serviceRequest.priority.id)),
+ 8.width,
+ StatusLabel(
+ label: serviceRequest.statusLabel,
+ textColor: AColors.getRequestStatusTextColor(serviceRequest.statusValue),
+ backgroundColor: AColors.getRequestStatusColor(serviceRequest.statusValue)),
+ 1.width.expanded,
+ Text(serviceRequest.date.toServiceRequestCardFormat, textAlign: TextAlign.end, style: AppTextStyles.tinyFont.copyWith(color: const Color(0xFF3B3D4A))),
+ ],
+ ),
+ 8.height,
+ Text(serviceRequest.deviceEnName, style: AppTextStyles.heading5.copyWith(color: const Color(0xFF3B3D4A))),
+ Text(
+ '${context.translation.assetNumber}: ${serviceRequest.device.assetNumber}',
+ style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
+ ),
+ Text(
+ 'Request Type: ${serviceRequest.type.name}',
+ style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
+ ),
+ Text(
+ 'Request No: ${serviceRequest.requestCode}',
+ style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
+ ),
+ 8.height,
+ const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
+ 8.height,
+ Text(
+ 'Manufacture: ${serviceRequest.device.modelDefinition.manufacturerName}',
+ style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
+ ),
+ Text(
+ 'Model: ${serviceRequest.device.modelDefinition.modelName}',
+ style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
+ ),
+ 8.height,
+ if ((serviceRequest.callComments ?? "").isNotEmpty) ...[
+ const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
+ 8.height,
+ Text(
+ serviceRequest.callComments,
+ style: AppTextStyles.bodyText.copyWith(color: Color(0xFF757575)),
+ ),
+ ],
+ if (serviceRequest.devicePhotos.isNotEmpty) ...[
+ 8.height,
+ const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
+ FilesList(images: serviceRequest.devicePhotos),
+ ],
+ if (serviceRequest.audio?.isNotEmpty ?? false) ...[
+ const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
+ 16.height,
+ ASoundPlayer(audio: serviceRequest.audio),
+ ],
+ ],
+ ).paddingAll(16),
+ (_userProvider.user.type == UsersTypes.normal_user
+ ? Container(
+ height: 50,
+ padding: const EdgeInsets.only(left: 16, right: 16),
+ alignment: Alignment.center,
+ width: double.infinity,
+ decoration: const ShapeDecoration(
+ color: Color(0xFFEAF1F4),
+ shape: RoundedRectangleBorder(
+ borderRadius: BorderRadius.only(
+ bottomLeft: Radius.circular(20),
+ bottomRight: Radius.circular(20),
+ ),
+ ),
+ ),
+ child: Row(
+ children: [
+ Text(
+ 'Comment here...',
+ style: AppTextStyles.heading6.copyWith(
+ color: AppColor.neutral50.withOpacity(.6),
+ ),
+ ).expanded,
+ SvgPicture.asset("assets/images/comment_send.svg", width: 24 * AppStyle.getScaleFactor(context), height: 24 * AppStyle.getScaleFactor(context), color: AppColor.primary70),
+ ],
+ ),
+ )
+ : Column(
+ mainAxisSize: MainAxisSize.min,
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ const Divider(color: Color(0xFFEAF1F4), height: 1, thickness: 1),
+ 16.height,
+ Row(
+ mainAxisSize: MainAxisSize.min,
+ children: [
+ Text(
+ 'View Comments',
+ style: AppTextStyles.bodyText.copyWith(color: const Color(0xFF4A8DB7)),
+ ),
+ 4.width,
+ const Icon(
+ Icons.arrow_forward,
+ color: Color(0xFF4A8DB7),
+ size: 14,
+ )
+ ],
+ ),
+ ],
+ ).paddingOnly(bottom: 16, start: 16, end: 16))
+ .onPress(() {
+ // todo 'sikander' add comment bottom sheet
+ }),
+ ],
+ ),
+ );
+ }
+
+ return Scaffold(
+ appBar: DefaultAppBar(title: context.translation.serviceRequest),
+ backgroundColor: const Color(0xfff8f9fb),
+ body: SafeArea(
+ child: FutureBuilder(
+ future: _serviceRequestsProvider.getServiceRequestObjectById(requestId: serviceRequest.id),
+ builder: (context, snap) {
+ if (snap.connectionState == ConnectionState.waiting) {
+ return const ALoading();
+ } else if (snap.hasData) {
+ serviceRequest = snap.data;
+ return Column(
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ SingleChildScrollView(
+ padding: const EdgeInsets.all(16),
+ child: informationCard(),
+ ).expanded,
+ if (_userProvider.user.type != UsersTypes.engineer || (serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3))
+ (serviceRequest.firstAction == null
+ ? AppFilledButton(
+ label: context.translation.firstAction,
+ maxWidth: true,
+ onPressed: () {
+ Navigator.of(context).push(
+ MaterialPageRoute(builder: (_) => CreateRequestPage(serviceRequest: serviceRequest)),
+ );
+ })
+ : AppFilledButton(
+ label: context.translation.viewWorkOrder,
+ maxWidth: true,
+ onPressed: () {
+ Navigator.of(context).pushNamed(WorkOrderListPage.id, arguments: serviceRequest);
+ }))
+ .paddingOnly(start: 16, end: 16, bottom: 24),
+ ],
+ );
+ }
+ return const SizedBox();
+ })));
+ }
+}
diff --git a/lib/views/pages/user/requests/report/create_service_report.dart b/lib/views/pages/user/requests/work_order/create_service_report.dart
similarity index 100%
rename from lib/views/pages/user/requests/report/create_service_report.dart
rename to lib/views/pages/user/requests/work_order/create_service_report.dart
diff --git a/lib/views/pages/user/requests/report/edit_service_report.dart b/lib/views/pages/user/requests/work_order/edit_service_report.dart
similarity index 100%
rename from lib/views/pages/user/requests/report/edit_service_report.dart
rename to lib/views/pages/user/requests/work_order/edit_service_report.dart
diff --git a/lib/views/pages/user/requests/report/future_service_report.dart b/lib/views/pages/user/requests/work_order/future_service_report.dart
similarity index 100%
rename from lib/views/pages/user/requests/report/future_service_report.dart
rename to lib/views/pages/user/requests/work_order/future_service_report.dart
diff --git a/lib/views/pages/user/requests/work_order/work_orders_list_page.dart b/lib/views/pages/user/requests/work_order/work_orders_list_page.dart
new file mode 100644
index 00000000..a2dce886
--- /dev/null
+++ b/lib/views/pages/user/requests/work_order/work_orders_list_page.dart
@@ -0,0 +1,179 @@
+import 'package:flutter/material.dart';
+import 'package:provider/provider.dart';
+import 'package:test_sa/controllers/providers/api/service_requests_provider.dart';
+import 'package:test_sa/controllers/providers/api/user_provider.dart';
+import 'package:test_sa/extensions/context_extension.dart';
+import 'package:test_sa/extensions/int_extensions.dart';
+import 'package:test_sa/models/enums/user_types.dart';
+import 'package:test_sa/models/service_request/search_work_order.dart';
+import 'package:test_sa/models/service_request/service_request.dart';
+import 'package:test_sa/new_views/common_widgets/default_app_bar.dart';
+import 'package:test_sa/views/app_style/sizing.dart';
+import 'package:test_sa/views/pages/user/requests/work_order/create_service_report.dart';
+import 'package:test_sa/views/pages/user/requests/work_order/future_service_report.dart';
+import 'package:test_sa/views/widgets/buttons/app_button.dart';
+import 'package:test_sa/views/widgets/requests/info_row.dart';
+import 'package:test_sa/views/widgets/titles/app_sub_title.dart';
+
+class WorkOrderListPage extends StatelessWidget {
+ static const String id = "/work-order-list";
+ ServiceRequest serviceRequest;
+
+ WorkOrderListPage({Key key, this.serviceRequest}) : super(key: key);
+
+ @override
+ Widget build(BuildContext context) {
+ // UserProvider _userProvider = Provider.of(context);
+ // SettingProvider _settingProvider = Provider.of(context);
+ List workOrders = [];
+ ServiceRequestsProvider serviceRequestsProvider;
+ UserProvider _userProvider = Provider.of(context);
+ if (serviceRequestsProvider == null) {
+ serviceRequestsProvider = Provider.of(context);
+ serviceRequest = ModalRoute.of(context).settings.arguments;
+ }
+
+ return Scaffold(
+ appBar: DefaultAppBar(title: context.translation.workOrder),
+ backgroundColor: const Color(0xfff8f9fb),
+ body: SafeArea(
+ child: FutureBuilder(
+ future: serviceRequestsProvider.searchWorkOrders(callId: serviceRequest.requestCode),
+ builder: (context, snap) {
+ workOrders = snap.data as List;
+ if (snap.connectionState == ConnectionState.waiting) return Center(child: CircularProgressIndicator());
+ if (snap.connectionState == ConnectionState.done && (snap.data?.length ?? 0) != 0) {
+ return SingleChildScrollView(
+ child: Column(
+ children: [
+ ListView.separated(
+ shrinkWrap: true,
+ physics: const NeverScrollableScrollPhysics(),
+ padding: EdgeInsets.all(21),
+ itemCount: workOrders.length,
+ separatorBuilder: (czt, index) => 21.height,
+ itemBuilder: (context, index) {
+ Color itemColor = index % 2 == 0 ? Theme.of(context).colorScheme.primary : Theme.of(context).colorScheme.onPrimary;
+ Color onItemColor = index % 2 != 0 ? Theme.of(context).colorScheme.primary : Theme.of(context).colorScheme.onPrimary;
+
+ return ElevatedButton(
+ style: ElevatedButton.styleFrom(
+ padding: EdgeInsets.symmetric(vertical: 8, horizontal: 8),
+ primary: itemColor.withOpacity(.7),
+ shape: RoundedRectangleBorder(
+ borderRadius: BorderRadius.circular(AppStyle.getBorderRadius(context)),
+ ),
+ ),
+ //padding: EdgeInsets.symmetric(vertical: 8,horizontal: 8),
+ onPressed: () {
+ // onPressed(request);
+ },
+ child: Column(
+ children: [
+ RequestInfoRow(
+ title: context.translation.callId,
+ content: serviceRequest.requestCode,
+ ),
+ RequestInfoRow(
+ title: context.translation.orderWorkNumber,
+ info: workOrders[index].workOrderNo.toString(),
+ ),
+ RequestInfoRow(
+ title: context.translation.visitDate,
+ info: workOrders[index].visitDate,
+ ),
+ RequestInfoRow(title: context.translation.assignedEmployee, info: workOrders[index].assignedEmployee?.name ?? ""),
+ RequestInfoRow(
+ title: context.translation.assetSN,
+ info: workOrders[index].callRequest.asset.assetSerialNo,
+ ),
+ RequestInfoRow(
+ title: context.translation.assetName,
+ info: workOrders[index].callRequest.asset.modelDefinition.assetName,
+ ),
+ RequestInfoRow(
+ title: context.translation.assetNumber,
+ info: workOrders[index].callRequest.asset.assetNumber,
+ ),
+ RequestInfoRow(
+ title: context.translation.model,
+ info: workOrders[index].callRequest.asset.modelDefinition.modelName,
+ ),
+ RequestInfoRow(
+ title: context.translation.site,
+ info: workOrders[index].callRequest.asset.site.custName,
+ ),
+ RequestInfoRow(
+ title: "Call last Situation",
+ info: workOrders[index].currentSituation.name ?? '',
+ ),
+ _userProvider.user.type == UsersTypes.engineer && workOrders[index].workOrderNo != null
+ ? Padding(
+ padding: EdgeInsets.all(32),
+ child: AButton(
+ text: context.translation.editServiceReport,
+ onPressed: serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3
+ ? null
+ : () {
+ Navigator.of(context).push(
+ MaterialPageRoute(
+ builder: (_) => FutureServiceReport(
+ request: serviceRequest,
+ workOrder: workOrders[index],
+ )),
+ );
+ },
+ ),
+ )
+ : SizedBox.shrink(),
+ ],
+ ),
+ );
+ },
+ ),
+ if (_userProvider.user.type == UsersTypes.engineer)
+ Center(
+ child: Padding(
+ padding: const EdgeInsets.all(32),
+ child: AButton(
+ text: "Create Work Order",
+ onPressed: serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3
+ ? null
+ : () {
+ Navigator.of(context).push(MaterialPageRoute(builder: (_) => CreateServiceReport(request: serviceRequest)));
+ },
+ ),
+ ),
+ ),
+ ],
+ ),
+ );
+ } else {
+ return Column(
+ children: [
+ Expanded(
+ child: Center(
+ child: ASubTitle(context.translation.dataNotFound),
+ ),
+ ),
+ if (_userProvider.user.type == UsersTypes.engineer)
+ Center(
+ child: Padding(
+ padding: const EdgeInsets.all(32),
+ child: AButton(
+ text: "Create Work Order",
+ onPressed: serviceRequest.statusValue == 5 || serviceRequest.statusValue == 3
+ ? null
+ : () {
+ Navigator.of(context).push(MaterialPageRoute(builder: (_) => CreateServiceReport(request: serviceRequest)));
+ },
+ ),
+ ),
+ ),
+ ],
+ );
+ }
+ },
+ )));
+ }
+}
diff --git a/lib/views/widgets/requests/service_request_list.dart b/lib/views/widgets/requests/service_request_list.dart
index b8b24d47..53307445 100644
--- a/lib/views/widgets/requests/service_request_list.dart
+++ b/lib/views/widgets/requests/service_request_list.dart
@@ -4,7 +4,7 @@ import 'package:test_sa/extensions/context_extension.dart';
import 'package:test_sa/extensions/int_extensions.dart';
import 'package:test_sa/models/service_request/service_request.dart';
import 'package:test_sa/models/subtitle.dart';
-import 'package:test_sa/views/pages/user/requests/request_details.dart';
+import 'package:test_sa/views/pages/user/requests/service_request_details.dart';
import 'package:test_sa/views/widgets/loaders/lazy_loading.dart';
import 'package:test_sa/views/widgets/loaders/no_item_found.dart';
import 'package:test_sa/views/widgets/requests/service_request_item.dart';
@@ -37,7 +37,7 @@ class ServiceRequestsList extends StatelessWidget {
request: requests[itemIndex],
onPressed: (request) {
Navigator.of(context).push(MaterialPageRoute(
- builder: (_) => RequestDetailsPage(
+ builder: (_) => ServiceRequestDetailsPage(
serviceRequest: request,
)));
},
diff --git a/lib/views/widgets/sound/sound_player.dart b/lib/views/widgets/sound/sound_player.dart
index 74cf2571..0598ceed 100644
--- a/lib/views/widgets/sound/sound_player.dart
+++ b/lib/views/widgets/sound/sound_player.dart
@@ -1,5 +1,8 @@
import 'package:audioplayers/audioplayers.dart';
import 'package:flutter/material.dart';
+import 'package:test_sa/extensions/widget_extensions.dart';
+import 'package:test_sa/new_views/app_style/app_color.dart';
+import 'package:test_sa/new_views/app_style/app_text_style.dart';
import 'package:test_sa/views/app_style/sizing.dart';
import '../../app_style/colors.dart';
@@ -23,64 +26,73 @@ class _ASoundPlayerState extends State {
bool _failedToLoad = false;
AudioPlayer _audioPlayer;
+ Widget audioPlayerButton(IconData icon, VoidCallback onpress) {
+ return Container(
+ width: 48,
+ height: 48,
+ decoration: ShapeDecoration(
+ color: Colors.white,
+ shape: RoundedRectangleBorder(
+ side: const BorderSide(width: 1, color: Color(0xFFEAF1F4)),
+ borderRadius: BorderRadius.circular(32),
+ ),
+ ),
+ child: Icon(
+ icon,
+ color: const Color(0xff163A51).withOpacity(0.5),
+ ),
+ ).onPress(onpress);
+ }
+
Widget _getAudioButton() {
switch (_audioPlayer.state) {
case PlayerState.playing:
- return IconButton(
- icon: const Icon(Icons.pause_rounded),
- onPressed: () async {
- _failedToLoad = false;
- await _audioPlayer.pause();
- rebuild();
- });
+ return audioPlayerButton(Icons.pause_rounded, () async {
+ _failedToLoad = false;
+ await _audioPlayer.pause();
+ rebuild();
+ });
case PlayerState.paused:
- return IconButton(
- icon: const Icon(Icons.play_arrow_rounded),
- onPressed: () async {
- _failedToLoad = false;
- await _audioPlayer.resume();
- rebuild();
- });
+ return audioPlayerButton(Icons.play_arrow_rounded, () async {
+ _failedToLoad = false;
+ await _audioPlayer.resume();
+ rebuild();
+ });
case PlayerState.completed:
- return IconButton(
- icon: const Icon(Icons.replay_rounded),
- onPressed: () async {
- _failedToLoad = false;
- await _audioPlayer.stop();
- await _audioPlayer.resume();
- rebuild();
- });
+ return audioPlayerButton(Icons.replay_rounded, () async {
+ _failedToLoad = false;
+ await _audioPlayer.stop();
+ await _audioPlayer.resume();
+ rebuild();
+ });
case PlayerState.stopped:
- return IconButton(
- icon: Icon(_isLocalFile ? Icons.play_circle_fill_outlined : Icons.download_rounded),
- onPressed: () async {
- _failedToLoad = false;
- try {
- await _audioPlayer.play(
- _isLocalFile ? DeviceFileSource(_audio) : UrlSource(_audio),
- );
- rebuild();
- } on Exception catch (e) {
- _failedToLoad = true;
- }
- });
+ return audioPlayerButton(_isLocalFile ? Icons.play_circle_fill_outlined : Icons.download_rounded, () async {
+ _failedToLoad = false;
+ try {
+ await _audioPlayer.play(
+ _isLocalFile ? DeviceFileSource(_audio) : UrlSource(_audio),
+ );
+ rebuild();
+ } on Exception catch (e) {
+ _failedToLoad = true;
+ }
+ });
+
default:
- return IconButton(
- icon: const Icon(Icons.replay_rounded),
- onPressed: () async {
- _failedToLoad = false;
+ return audioPlayerButton(Icons.replay_rounded, () async {
+ _failedToLoad = false;
- try {
- _audioPlayer.seek(const Duration(milliseconds: 0));
- _audioPlayer.stop();
- await _audioPlayer.play(
- _isLocalFile ? DeviceFileSource(_audio) : UrlSource(_audio),
- );
- rebuild();
- } on Exception catch (e) {
- _failedToLoad = true;
- }
- });
+ try {
+ _audioPlayer.seek(const Duration(milliseconds: 0));
+ _audioPlayer.stop();
+ await _audioPlayer.play(
+ _isLocalFile ? DeviceFileSource(_audio) : UrlSource(_audio),
+ );
+ rebuild();
+ } on Exception catch (e) {
+ _failedToLoad = true;
+ }
+ });
}
}
@@ -163,12 +175,15 @@ class _ASoundPlayerState extends State {
children: [
Row(
children: [
- Material(color: Colors.transparent, child: _getAudioButton()),
- Expanded(
+ _getAudioButton(),
+ SliderTheme(
+ data: SliderTheme.of(context).copyWith(trackHeight: 2.0, thumbShape: const RoundSliderThumbShape(enabledThumbRadius: 6.0), overlayShape: SliderComponentShape.noOverlay),
child: Slider(
value: _audioPosition?.inMilliseconds?.toDouble() ?? 0.0,
min: 0,
max: _audioTime?.inMilliseconds?.toDouble() ?? 60.0,
+ activeColor: AppColor.primary70,
+ inactiveColor: AppColor.neutral30,
onChangeStart: (value) {
_sliderMoving = true;
},
@@ -181,35 +196,12 @@ class _ASoundPlayerState extends State {
_audioPlayer.seek(Duration(milliseconds: value.round()));
rebuild();
}),
- ),
+ ).paddingOnly(start: 8, end: 8).expanded,
+ _failedToLoad
+ ? Text("Failed to load", style: AppTextStyle.tiny.copyWith(color: AppColor.red60))
+ : Text("${format(_audioPosition)}/${format(_audioTime)}", style: AppTextStyle.tiny.copyWith(color: AppColor.neutral50)),
],
),
- Row(
- children: [
- Expanded(
- child: Visibility(
- visible: _failedToLoad,
- child: Row(
- children: [
- Text(
- "Failed to load",
- style: Theme.of(context).textTheme.overline.copyWith(color: AColors.red),
- textScaleFactor: AppStyle.getScaleFactor(context),
- ),
- ],
- ),
- ),
- ),
- Visibility(
- visible: _audioPlayer.state != PlayerState.stopped,
- child: Text(
- "${format(_audioPosition)}/${format(_audioTime)}",
- style: Theme.of(context).textTheme.overline,
- textScaleFactor: AppStyle.getScaleFactor(context),
- ),
- ),
- ],
- )
],
);
}