feat: implement navigation to order details with specific date for one-time and recurring orders

This commit is contained in:
Achintha Isuru
2026-02-21 20:03:49 -05:00
parent b2cfd93b8f
commit 71b5f743de
4 changed files with 160 additions and 84 deletions

View File

@@ -168,4 +168,16 @@ extension ClientNavigator on IModularNavigator {
void toCreateOrderPermanent() {
pushNamed(ClientPaths.createOrderPermanent);
}
// ==========================================================================
// VIEW ORDER
// ==========================================================================
/// Navigates to the order details page to a specific date.
void toOrdersSpecificDate(DateTime date) {
navigate(
ClientPaths.orders,
arguments: <String, DateTime>{'initialDate': date},
);
}
}

View File

@@ -24,8 +24,10 @@ class OneTimeOrderPage extends StatelessWidget {
create: (BuildContext context) => Modular.get<OneTimeOrderBloc>(),
child: BlocBuilder<OneTimeOrderBloc, OneTimeOrderState>(
builder: (BuildContext context, OneTimeOrderState state) {
final OneTimeOrderBloc bloc = BlocProvider.of<OneTimeOrderBloc>(context);
final OneTimeOrderBloc bloc = BlocProvider.of<OneTimeOrderBloc>(
context,
);
return OneTimeOrderView(
status: _mapStatus(state.status),
errorMessage: state.errorMessage,
@@ -33,16 +35,23 @@ class OneTimeOrderPage extends StatelessWidget {
selectedVendor: state.selectedVendor,
vendors: state.vendors,
date: state.date,
selectedHub: state.selectedHub != null ? _mapHub(state.selectedHub!) : null,
selectedHub: state.selectedHub != null
? _mapHub(state.selectedHub!)
: null,
hubs: state.hubs.map(_mapHub).toList(),
positions: state.positions.map(_mapPosition).toList(),
roles: state.roles.map(_mapRole).toList(),
isValid: state.isValid,
onEventNameChanged: (String val) => bloc.add(OneTimeOrderEventNameChanged(val)),
onVendorChanged: (Vendor val) => bloc.add(OneTimeOrderVendorChanged(val)),
onDateChanged: (DateTime val) => bloc.add(OneTimeOrderDateChanged(val)),
onEventNameChanged: (String val) =>
bloc.add(OneTimeOrderEventNameChanged(val)),
onVendorChanged: (Vendor val) =>
bloc.add(OneTimeOrderVendorChanged(val)),
onDateChanged: (DateTime val) =>
bloc.add(OneTimeOrderDateChanged(val)),
onHubChanged: (OrderHubUiModel val) {
final OneTimeOrderHubOption originalHub = state.hubs.firstWhere((OneTimeOrderHubOption h) => h.id == val.id);
final OneTimeOrderHubOption originalHub = state.hubs.firstWhere(
(OneTimeOrderHubOption h) => h.id == val.id,
);
bloc.add(OneTimeOrderHubChanged(originalHub));
},
onPositionAdded: () => bloc.add(const OneTimeOrderPositionAdded()),
@@ -57,16 +66,11 @@ class OneTimeOrderPage extends StatelessWidget {
);
bloc.add(OneTimeOrderPositionUpdated(index, updated));
},
onPositionRemoved: (int index) => bloc.add(OneTimeOrderPositionRemoved(index)),
onPositionRemoved: (int index) =>
bloc.add(OneTimeOrderPositionRemoved(index)),
onSubmit: () => bloc.add(const OneTimeOrderSubmitted()),
onDone: () => Modular.to.pushNamedAndRemoveUntil(
ClientPaths.orders,
(_) => false,
arguments: <String, dynamic>{
'initialDate': state.date.toIso8601String(),
},
),
onBack: () => Modular.to.navigate(ClientPaths.createOrder),
onDone: () => Modular.to.toOrdersSpecificDate(state.date),
onBack: () => Modular.to.toCreateOrder(),
);
},
),

View File

@@ -19,8 +19,10 @@ class PermanentOrderPage extends StatelessWidget {
create: (BuildContext context) => Modular.get<PermanentOrderBloc>(),
child: BlocBuilder<PermanentOrderBloc, PermanentOrderState>(
builder: (BuildContext context, PermanentOrderState state) {
final PermanentOrderBloc bloc = BlocProvider.of<PermanentOrderBloc>(context);
final PermanentOrderBloc bloc = BlocProvider.of<PermanentOrderBloc>(
context,
);
return PermanentOrderView(
status: _mapStatus(state.status),
errorMessage: state.errorMessage,
@@ -29,20 +31,29 @@ class PermanentOrderPage extends StatelessWidget {
vendors: state.vendors,
startDate: state.startDate,
permanentDays: state.permanentDays,
selectedHub: state.selectedHub != null ? _mapHub(state.selectedHub!) : null,
selectedHub: state.selectedHub != null
? _mapHub(state.selectedHub!)
: null,
hubs: state.hubs.map(_mapHub).toList(),
positions: state.positions.map(_mapPosition).toList(),
roles: state.roles.map(_mapRole).toList(),
isValid: state.isValid,
onEventNameChanged: (String val) => bloc.add(PermanentOrderEventNameChanged(val)),
onVendorChanged: (Vendor val) => bloc.add(PermanentOrderVendorChanged(val)),
onStartDateChanged: (DateTime val) => bloc.add(PermanentOrderStartDateChanged(val)),
onDayToggled: (int index) => bloc.add(PermanentOrderDayToggled(index)),
onEventNameChanged: (String val) =>
bloc.add(PermanentOrderEventNameChanged(val)),
onVendorChanged: (Vendor val) =>
bloc.add(PermanentOrderVendorChanged(val)),
onStartDateChanged: (DateTime val) =>
bloc.add(PermanentOrderStartDateChanged(val)),
onDayToggled: (int index) =>
bloc.add(PermanentOrderDayToggled(index)),
onHubChanged: (OrderHubUiModel val) {
final PermanentOrderHubOption originalHub = state.hubs.firstWhere((PermanentOrderHubOption h) => h.id == val.id);
final PermanentOrderHubOption originalHub = state.hubs.firstWhere(
(PermanentOrderHubOption h) => h.id == val.id,
);
bloc.add(PermanentOrderHubChanged(originalHub));
},
onPositionAdded: () => bloc.add(const PermanentOrderPositionAdded()),
onPositionAdded: () =>
bloc.add(const PermanentOrderPositionAdded()),
onPositionUpdated: (int index, OrderPositionUiModel val) {
final PermanentOrderPosition original = state.positions[index];
final PermanentOrderPosition updated = original.copyWith(
@@ -54,22 +65,19 @@ class PermanentOrderPage extends StatelessWidget {
);
bloc.add(PermanentOrderPositionUpdated(index, updated));
},
onPositionRemoved: (int index) => bloc.add(PermanentOrderPositionRemoved(index)),
onPositionRemoved: (int index) =>
bloc.add(PermanentOrderPositionRemoved(index)),
onSubmit: () => bloc.add(const PermanentOrderSubmitted()),
onDone: () {
final DateTime initialDate = _firstPermanentShiftDate(
state.startDate,
state.permanentDays,
);
Modular.to.pushNamedAndRemoveUntil(
ClientPaths.orders,
(_) => false,
arguments: <String, dynamic>{
'initialDate': initialDate.toIso8601String(),
},
);
// Navigate to orders page with the initial date set to the first recurring shift date
Modular.to.toOrdersSpecificDate(initialDate);
},
onBack: () => Modular.to.navigate(ClientPaths.createOrder),
onBack: () => Modular.to.toCreateOrder(),
);
},
),
@@ -80,10 +88,18 @@ class PermanentOrderPage extends StatelessWidget {
DateTime startDate,
List<String> permanentDays,
) {
final DateTime start = DateTime(startDate.year, startDate.month, startDate.day);
final DateTime start = DateTime(
startDate.year,
startDate.month,
startDate.day,
);
final DateTime end = start.add(const Duration(days: 29));
final Set<String> selected = permanentDays.toSet();
for (DateTime day = start; !day.isAfter(end); day = day.add(const Duration(days: 1))) {
for (
DateTime day = start;
!day.isAfter(end);
day = day.add(const Duration(days: 1))
) {
if (selected.contains(_weekdayLabel(day))) {
return day;
}
@@ -93,23 +109,35 @@ class PermanentOrderPage extends StatelessWidget {
String _weekdayLabel(DateTime date) {
switch (date.weekday) {
case DateTime.monday: return 'MON';
case DateTime.tuesday: return 'TUE';
case DateTime.wednesday: return 'WED';
case DateTime.thursday: return 'THU';
case DateTime.friday: return 'FRI';
case DateTime.saturday: return 'SAT';
case DateTime.sunday: return 'SUN';
default: return 'SUN';
case DateTime.monday:
return 'MON';
case DateTime.tuesday:
return 'TUE';
case DateTime.wednesday:
return 'WED';
case DateTime.thursday:
return 'THU';
case DateTime.friday:
return 'FRI';
case DateTime.saturday:
return 'SAT';
case DateTime.sunday:
return 'SUN';
default:
return 'SUN';
}
}
OrderFormStatus _mapStatus(PermanentOrderStatus status) {
switch (status) {
case PermanentOrderStatus.initial: return OrderFormStatus.initial;
case PermanentOrderStatus.loading: return OrderFormStatus.loading;
case PermanentOrderStatus.success: return OrderFormStatus.success;
case PermanentOrderStatus.failure: return OrderFormStatus.failure;
case PermanentOrderStatus.initial:
return OrderFormStatus.initial;
case PermanentOrderStatus.loading:
return OrderFormStatus.loading;
case PermanentOrderStatus.success:
return OrderFormStatus.success;
case PermanentOrderStatus.failure:
return OrderFormStatus.failure;
}
}

View File

@@ -19,8 +19,10 @@ class RecurringOrderPage extends StatelessWidget {
create: (BuildContext context) => Modular.get<RecurringOrderBloc>(),
child: BlocBuilder<RecurringOrderBloc, RecurringOrderState>(
builder: (BuildContext context, RecurringOrderState state) {
final RecurringOrderBloc bloc = BlocProvider.of<RecurringOrderBloc>(context);
final RecurringOrderBloc bloc = BlocProvider.of<RecurringOrderBloc>(
context,
);
return RecurringOrderView(
status: _mapStatus(state.status),
errorMessage: state.errorMessage,
@@ -30,21 +32,31 @@ class RecurringOrderPage extends StatelessWidget {
startDate: state.startDate,
endDate: state.endDate,
recurringDays: state.recurringDays,
selectedHub: state.selectedHub != null ? _mapHub(state.selectedHub!) : null,
selectedHub: state.selectedHub != null
? _mapHub(state.selectedHub!)
: null,
hubs: state.hubs.map(_mapHub).toList(),
positions: state.positions.map(_mapPosition).toList(),
roles: state.roles.map(_mapRole).toList(),
isValid: state.isValid,
onEventNameChanged: (String val) => bloc.add(RecurringOrderEventNameChanged(val)),
onVendorChanged: (Vendor val) => bloc.add(RecurringOrderVendorChanged(val)),
onStartDateChanged: (DateTime val) => bloc.add(RecurringOrderStartDateChanged(val)),
onEndDateChanged: (DateTime val) => bloc.add(RecurringOrderEndDateChanged(val)),
onDayToggled: (int index) => bloc.add(RecurringOrderDayToggled(index)),
onEventNameChanged: (String val) =>
bloc.add(RecurringOrderEventNameChanged(val)),
onVendorChanged: (Vendor val) =>
bloc.add(RecurringOrderVendorChanged(val)),
onStartDateChanged: (DateTime val) =>
bloc.add(RecurringOrderStartDateChanged(val)),
onEndDateChanged: (DateTime val) =>
bloc.add(RecurringOrderEndDateChanged(val)),
onDayToggled: (int index) =>
bloc.add(RecurringOrderDayToggled(index)),
onHubChanged: (OrderHubUiModel val) {
final RecurringOrderHubOption originalHub = state.hubs.firstWhere((RecurringOrderHubOption h) => h.id == val.id);
final RecurringOrderHubOption originalHub = state.hubs.firstWhere(
(RecurringOrderHubOption h) => h.id == val.id,
);
bloc.add(RecurringOrderHubChanged(originalHub));
},
onPositionAdded: () => bloc.add(const RecurringOrderPositionAdded()),
onPositionAdded: () =>
bloc.add(const RecurringOrderPositionAdded()),
onPositionUpdated: (int index, OrderPositionUiModel val) {
final RecurringOrderPosition original = state.positions[index];
final RecurringOrderPosition updated = original.copyWith(
@@ -56,27 +68,27 @@ class RecurringOrderPage extends StatelessWidget {
);
bloc.add(RecurringOrderPositionUpdated(index, updated));
},
onPositionRemoved: (int index) => bloc.add(RecurringOrderPositionRemoved(index)),
onPositionRemoved: (int index) =>
bloc.add(RecurringOrderPositionRemoved(index)),
onSubmit: () => bloc.add(const RecurringOrderSubmitted()),
onDone: () {
final DateTime maxEndDate = state.startDate.add(const Duration(days: 29));
final DateTime maxEndDate = state.startDate.add(
const Duration(days: 29),
);
final DateTime effectiveEndDate =
state.endDate.isAfter(maxEndDate) ? maxEndDate : state.endDate;
state.endDate.isAfter(maxEndDate)
? maxEndDate
: state.endDate;
final DateTime initialDate = _firstRecurringShiftDate(
state.startDate,
effectiveEndDate,
state.recurringDays,
);
Modular.to.pushNamedAndRemoveUntil(
ClientPaths.orders,
(_) => false,
arguments: <String, dynamic>{
'initialDate': initialDate.toIso8601String(),
},
);
// Navigate to orders page with the initial date set to the first recurring shift date
Modular.to.toOrdersSpecificDate(initialDate);
},
onBack: () => Modular.to.navigate(ClientPaths.createOrder),
onBack: () => Modular.to.toCreateOrder(),
);
},
),
@@ -88,10 +100,18 @@ class RecurringOrderPage extends StatelessWidget {
DateTime endDate,
List<String> recurringDays,
) {
final DateTime start = DateTime(startDate.year, startDate.month, startDate.day);
final DateTime start = DateTime(
startDate.year,
startDate.month,
startDate.day,
);
final DateTime end = DateTime(endDate.year, endDate.month, endDate.day);
final Set<String> selected = recurringDays.toSet();
for (DateTime day = start; !day.isAfter(end); day = day.add(const Duration(days: 1))) {
for (
DateTime day = start;
!day.isAfter(end);
day = day.add(const Duration(days: 1))
) {
if (selected.contains(_weekdayLabel(day))) {
return day;
}
@@ -101,23 +121,35 @@ class RecurringOrderPage extends StatelessWidget {
String _weekdayLabel(DateTime date) {
switch (date.weekday) {
case DateTime.monday: return 'MON';
case DateTime.tuesday: return 'TUE';
case DateTime.wednesday: return 'WED';
case DateTime.thursday: return 'THU';
case DateTime.friday: return 'FRI';
case DateTime.saturday: return 'SAT';
case DateTime.sunday: return 'SUN';
default: return 'SUN';
case DateTime.monday:
return 'MON';
case DateTime.tuesday:
return 'TUE';
case DateTime.wednesday:
return 'WED';
case DateTime.thursday:
return 'THU';
case DateTime.friday:
return 'FRI';
case DateTime.saturday:
return 'SAT';
case DateTime.sunday:
return 'SUN';
default:
return 'SUN';
}
}
OrderFormStatus _mapStatus(RecurringOrderStatus status) {
switch (status) {
case RecurringOrderStatus.initial: return OrderFormStatus.initial;
case RecurringOrderStatus.loading: return OrderFormStatus.loading;
case RecurringOrderStatus.success: return OrderFormStatus.success;
case RecurringOrderStatus.failure: return OrderFormStatus.failure;
case RecurringOrderStatus.initial:
return OrderFormStatus.initial;
case RecurringOrderStatus.loading:
return OrderFormStatus.loading;
case RecurringOrderStatus.success:
return OrderFormStatus.success;
case RecurringOrderStatus.failure:
return OrderFormStatus.failure;
}
}