feat: Add event name to order items and refactor navigation and shift data access to use direct object properties.
This commit is contained in:
@@ -138,7 +138,7 @@ extension ClientNavigator on IModularNavigator {
|
|||||||
///
|
///
|
||||||
/// This is the starting point for all order creation flows.
|
/// This is the starting point for all order creation flows.
|
||||||
void toCreateOrder({Object? arguments}) {
|
void toCreateOrder({Object? arguments}) {
|
||||||
pushNamed(ClientPaths.createOrder, arguments: arguments);
|
navigate(ClientPaths.createOrder, arguments: arguments);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Pushes the rapid order creation flow.
|
/// Pushes the rapid order creation flow.
|
||||||
@@ -175,9 +175,8 @@ extension ClientNavigator on IModularNavigator {
|
|||||||
|
|
||||||
/// Navigates to the order details page to a specific date.
|
/// Navigates to the order details page to a specific date.
|
||||||
void toOrdersSpecificDate(DateTime date) {
|
void toOrdersSpecificDate(DateTime date) {
|
||||||
pushNamedAndRemoveUntil(
|
navigate(
|
||||||
ClientPaths.orders,
|
ClientPaths.orders,
|
||||||
(_) => false,
|
|
||||||
arguments: <String, DateTime>{'initialDate': date},
|
arguments: <String, DateTime>{'initialDate': date},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -87,9 +87,10 @@ class ShiftsConnectorRepositoryImpl implements ShiftsConnectorRepository {
|
|||||||
final String orderTypeStr = sr.shift.order.orderType.stringValue
|
final String orderTypeStr = sr.shift.order.orderType.stringValue
|
||||||
.toUpperCase();
|
.toUpperCase();
|
||||||
|
|
||||||
final Map<String, dynamic> orderJson = sr.shift.order.toJson();
|
final dc.ListShiftRolesByVendorIdShiftRolesShiftOrder order =
|
||||||
final DateTime? startDate = _service.toDateTime(orderJson['startDate']);
|
sr.shift.order;
|
||||||
final DateTime? endDate = _service.toDateTime(orderJson['endDate']);
|
final DateTime? startDate = _service.toDateTime(order.startDate);
|
||||||
|
final DateTime? endDate = _service.toDateTime(order.endDate);
|
||||||
|
|
||||||
final String startTime = startDt != null
|
final String startTime = startDt != null
|
||||||
? DateFormat('HH:mm').format(startDt)
|
? DateFormat('HH:mm').format(startDt)
|
||||||
@@ -102,8 +103,8 @@ class ShiftsConnectorRepositoryImpl implements ShiftsConnectorRepository {
|
|||||||
orderType: orderTypeStr,
|
orderType: orderTypeStr,
|
||||||
startDate: startDate,
|
startDate: startDate,
|
||||||
endDate: endDate,
|
endDate: endDate,
|
||||||
recurringDays: sr.shift.order.recurringDays,
|
recurringDays: order.recurringDays,
|
||||||
permanentDays: sr.shift.order.permanentDays,
|
permanentDays: order.permanentDays,
|
||||||
startTime: startTime,
|
startTime: startTime,
|
||||||
endTime: endTime,
|
endTime: endTime,
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -23,6 +23,7 @@ class OrderItem extends Equatable {
|
|||||||
required this.filled,
|
required this.filled,
|
||||||
required this.workersNeeded,
|
required this.workersNeeded,
|
||||||
required this.hourlyRate,
|
required this.hourlyRate,
|
||||||
|
required this.eventName,
|
||||||
this.hours = 0,
|
this.hours = 0,
|
||||||
this.totalValue = 0,
|
this.totalValue = 0,
|
||||||
this.confirmedApps = const <Map<String, dynamic>>[],
|
this.confirmedApps = const <Map<String, dynamic>>[],
|
||||||
@@ -76,6 +77,9 @@ class OrderItem extends Equatable {
|
|||||||
/// Total value for the shift role.
|
/// Total value for the shift role.
|
||||||
final double totalValue;
|
final double totalValue;
|
||||||
|
|
||||||
|
/// Name of the event.
|
||||||
|
final String eventName;
|
||||||
|
|
||||||
/// List of confirmed worker applications.
|
/// List of confirmed worker applications.
|
||||||
final List<Map<String, dynamic>> confirmedApps;
|
final List<Map<String, dynamic>> confirmedApps;
|
||||||
|
|
||||||
@@ -97,6 +101,7 @@ class OrderItem extends Equatable {
|
|||||||
hourlyRate,
|
hourlyRate,
|
||||||
hours,
|
hours,
|
||||||
totalValue,
|
totalValue,
|
||||||
|
eventName,
|
||||||
confirmedApps,
|
confirmedApps,
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,10 +7,8 @@ import '../../domain/repositories/i_view_orders_repository.dart';
|
|||||||
|
|
||||||
/// Implementation of [IViewOrdersRepository] using Data Connect.
|
/// Implementation of [IViewOrdersRepository] using Data Connect.
|
||||||
class ViewOrdersRepositoryImpl implements IViewOrdersRepository {
|
class ViewOrdersRepositoryImpl implements IViewOrdersRepository {
|
||||||
|
ViewOrdersRepositoryImpl({required dc.DataConnectService service})
|
||||||
ViewOrdersRepositoryImpl({
|
: _service = service;
|
||||||
required dc.DataConnectService service,
|
|
||||||
}) : _service = service;
|
|
||||||
final dc.DataConnectService _service;
|
final dc.DataConnectService _service;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
@@ -21,34 +19,48 @@ class ViewOrdersRepositoryImpl implements IViewOrdersRepository {
|
|||||||
return _service.run(() async {
|
return _service.run(() async {
|
||||||
final String businessId = await _service.getBusinessId();
|
final String businessId = await _service.getBusinessId();
|
||||||
|
|
||||||
final fdc.Timestamp startTimestamp = _service.toTimestamp(_startOfDay(start));
|
final fdc.Timestamp startTimestamp = _service.toTimestamp(
|
||||||
|
_startOfDay(start),
|
||||||
|
);
|
||||||
final fdc.Timestamp endTimestamp = _service.toTimestamp(_endOfDay(end));
|
final fdc.Timestamp endTimestamp = _service.toTimestamp(_endOfDay(end));
|
||||||
final fdc.QueryResult<dc.ListShiftRolesByBusinessAndDateRangeData,
|
final fdc.QueryResult<
|
||||||
dc.ListShiftRolesByBusinessAndDateRangeVariables> result =
|
dc.ListShiftRolesByBusinessAndDateRangeData,
|
||||||
await _service.connector
|
dc.ListShiftRolesByBusinessAndDateRangeVariables
|
||||||
.listShiftRolesByBusinessAndDateRange(
|
>
|
||||||
businessId: businessId,
|
result = await _service.connector
|
||||||
start: startTimestamp,
|
.listShiftRolesByBusinessAndDateRange(
|
||||||
end: endTimestamp,
|
businessId: businessId,
|
||||||
)
|
start: startTimestamp,
|
||||||
.execute();
|
end: endTimestamp,
|
||||||
|
)
|
||||||
|
.execute();
|
||||||
debugPrint(
|
debugPrint(
|
||||||
'ViewOrders range start=${start.toIso8601String()} end=${end.toIso8601String()} shiftRoles=${result.data.shiftRoles.length}',
|
'ViewOrders range start=${start.toIso8601String()} end=${end.toIso8601String()} shiftRoles=${result.data.shiftRoles.length}',
|
||||||
);
|
);
|
||||||
|
|
||||||
final String businessName =
|
final String businessName =
|
||||||
dc.ClientSessionStore.instance.session?.business?.businessName ?? 'Your Company';
|
dc.ClientSessionStore.instance.session?.business?.businessName ??
|
||||||
|
'Your Company';
|
||||||
|
|
||||||
return result.data.shiftRoles.map((dc.ListShiftRolesByBusinessAndDateRangeShiftRoles shiftRole) {
|
return result.data.shiftRoles.map((
|
||||||
final DateTime? shiftDate = shiftRole.shift.date?.toDateTime().toLocal();
|
dc.ListShiftRolesByBusinessAndDateRangeShiftRoles shiftRole,
|
||||||
final String dateStr = shiftDate == null ? '' : DateFormat('yyyy-MM-dd').format(shiftDate);
|
) {
|
||||||
|
final DateTime? shiftDate = shiftRole.shift.date
|
||||||
|
?.toDateTime()
|
||||||
|
.toLocal();
|
||||||
|
final String dateStr = shiftDate == null
|
||||||
|
? ''
|
||||||
|
: DateFormat('yyyy-MM-dd').format(shiftDate);
|
||||||
final String startTime = _formatTime(shiftRole.startTime);
|
final String startTime = _formatTime(shiftRole.startTime);
|
||||||
final String endTime = _formatTime(shiftRole.endTime);
|
final String endTime = _formatTime(shiftRole.endTime);
|
||||||
final int filled = shiftRole.assigned ?? 0;
|
final int filled = shiftRole.assigned ?? 0;
|
||||||
final int workersNeeded = shiftRole.count;
|
final int workersNeeded = shiftRole.count;
|
||||||
final double hours = shiftRole.hours ?? 0;
|
final double hours = shiftRole.hours ?? 0;
|
||||||
final double totalValue = shiftRole.totalValue ?? 0;
|
final double totalValue = shiftRole.totalValue ?? 0;
|
||||||
final double hourlyRate = _hourlyRate(shiftRole.totalValue, shiftRole.hours);
|
final double hourlyRate = _hourlyRate(
|
||||||
|
shiftRole.totalValue,
|
||||||
|
shiftRole.hours,
|
||||||
|
);
|
||||||
// final String status = filled >= workersNeeded ? 'filled' : 'open';
|
// final String status = filled >= workersNeeded ? 'filled' : 'open';
|
||||||
final String status = shiftRole.shift.status?.stringValue ?? 'OPEN';
|
final String status = shiftRole.shift.status?.stringValue ?? 'OPEN';
|
||||||
|
|
||||||
@@ -58,13 +70,17 @@ class ViewOrdersRepositoryImpl implements IViewOrdersRepository {
|
|||||||
'end=${shiftRole.endTime?.toJson()} hours=$hours totalValue=$totalValue',
|
'end=${shiftRole.endTime?.toJson()} hours=$hours totalValue=$totalValue',
|
||||||
);
|
);
|
||||||
|
|
||||||
final String eventName = shiftRole.shift.order.eventName ?? shiftRole.shift.title;
|
final String eventName =
|
||||||
|
shiftRole.shift.order.eventName ?? shiftRole.shift.title;
|
||||||
|
|
||||||
return domain.OrderItem(
|
return domain.OrderItem(
|
||||||
id: _shiftRoleKey(shiftRole.shiftId, shiftRole.roleId),
|
id: _shiftRoleKey(shiftRole.shiftId, shiftRole.roleId),
|
||||||
orderId: shiftRole.shift.order.id,
|
orderId: shiftRole.shift.order.id,
|
||||||
orderType: domain.OrderType.fromString(shiftRole.shift.order.orderType.stringValue),
|
orderType: domain.OrderType.fromString(
|
||||||
title: '${shiftRole.role.name} - $eventName',
|
shiftRole.shift.order.orderType.stringValue,
|
||||||
|
),
|
||||||
|
title: shiftRole.role.name,
|
||||||
|
eventName: eventName,
|
||||||
clientName: businessName,
|
clientName: businessName,
|
||||||
status: status,
|
status: status,
|
||||||
date: dateStr,
|
date: dateStr,
|
||||||
@@ -92,28 +108,35 @@ class ViewOrdersRepositoryImpl implements IViewOrdersRepository {
|
|||||||
|
|
||||||
final fdc.Timestamp dayStart = _service.toTimestamp(_startOfDay(day));
|
final fdc.Timestamp dayStart = _service.toTimestamp(_startOfDay(day));
|
||||||
final fdc.Timestamp dayEnd = _service.toTimestamp(_endOfDay(day));
|
final fdc.Timestamp dayEnd = _service.toTimestamp(_endOfDay(day));
|
||||||
final fdc.QueryResult<dc.ListAcceptedApplicationsByBusinessForDayData,
|
final fdc.QueryResult<
|
||||||
dc.ListAcceptedApplicationsByBusinessForDayVariables> result =
|
dc.ListAcceptedApplicationsByBusinessForDayData,
|
||||||
await _service.connector
|
dc.ListAcceptedApplicationsByBusinessForDayVariables
|
||||||
.listAcceptedApplicationsByBusinessForDay(
|
>
|
||||||
businessId: businessId,
|
result = await _service.connector
|
||||||
dayStart: dayStart,
|
.listAcceptedApplicationsByBusinessForDay(
|
||||||
dayEnd: dayEnd,
|
businessId: businessId,
|
||||||
)
|
dayStart: dayStart,
|
||||||
.execute();
|
dayEnd: dayEnd,
|
||||||
|
)
|
||||||
|
.execute();
|
||||||
|
|
||||||
print(
|
print(
|
||||||
'ViewOrders day=${day.toIso8601String()} applications=${result.data.applications.length}',
|
'ViewOrders day=${day.toIso8601String()} applications=${result.data.applications.length}',
|
||||||
);
|
);
|
||||||
|
|
||||||
final Map<String, List<Map<String, dynamic>>> grouped = <String, List<Map<String, dynamic>>>{};
|
final Map<String, List<Map<String, dynamic>>> grouped =
|
||||||
for (final dc.ListAcceptedApplicationsByBusinessForDayApplications application
|
<String, List<Map<String, dynamic>>>{};
|
||||||
|
for (final dc.ListAcceptedApplicationsByBusinessForDayApplications
|
||||||
|
application
|
||||||
in result.data.applications) {
|
in result.data.applications) {
|
||||||
print(
|
print(
|
||||||
'ViewOrders app: shiftId=${application.shiftId} roleId=${application.roleId} '
|
'ViewOrders app: shiftId=${application.shiftId} roleId=${application.roleId} '
|
||||||
'checkIn=${application.checkInTime?.toJson()} checkOut=${application.checkOutTime?.toJson()}',
|
'checkIn=${application.checkInTime?.toJson()} checkOut=${application.checkOutTime?.toJson()}',
|
||||||
);
|
);
|
||||||
final String key = _shiftRoleKey(application.shiftId, application.roleId);
|
final String key = _shiftRoleKey(
|
||||||
|
application.shiftId,
|
||||||
|
application.roleId,
|
||||||
|
);
|
||||||
grouped.putIfAbsent(key, () => <Map<String, dynamic>>[]);
|
grouped.putIfAbsent(key, () => <Map<String, dynamic>>[]);
|
||||||
grouped[key]!.add(<String, dynamic>{
|
grouped[key]!.add(<String, dynamic>{
|
||||||
'id': application.id,
|
'id': application.id,
|
||||||
|
|||||||
@@ -85,11 +85,9 @@ class ViewOrdersCubit extends Cubit<ViewOrdersState>
|
|||||||
final DateTime? selectedDate = state.selectedDate;
|
final DateTime? selectedDate = state.selectedDate;
|
||||||
final DateTime updatedSelectedDate =
|
final DateTime updatedSelectedDate =
|
||||||
selectedDate != null &&
|
selectedDate != null &&
|
||||||
calendarDays.any(
|
calendarDays.any((DateTime day) => _isSameDay(day, selectedDate))
|
||||||
(DateTime day) => _isSameDay(day, selectedDate),
|
? selectedDate
|
||||||
)
|
: calendarDays.first;
|
||||||
? selectedDate
|
|
||||||
: calendarDays.first;
|
|
||||||
emit(
|
emit(
|
||||||
state.copyWith(
|
state.copyWith(
|
||||||
weekOffset: newWeekOffset,
|
weekOffset: newWeekOffset,
|
||||||
@@ -173,13 +171,15 @@ class ViewOrdersCubit extends Cubit<ViewOrdersState>
|
|||||||
}
|
}
|
||||||
|
|
||||||
final int filled = confirmed.length;
|
final int filled = confirmed.length;
|
||||||
final String status =
|
final String status = filled >= order.workersNeeded
|
||||||
filled >= order.workersNeeded ? 'FILLED' : order.status;
|
? 'FILLED'
|
||||||
|
: order.status;
|
||||||
return OrderItem(
|
return OrderItem(
|
||||||
id: order.id,
|
id: order.id,
|
||||||
orderId: order.orderId,
|
orderId: order.orderId,
|
||||||
orderType: order.orderType,
|
orderType: order.orderType,
|
||||||
title: order.title,
|
title: order.title,
|
||||||
|
eventName: order.eventName,
|
||||||
clientName: order.clientName,
|
clientName: order.clientName,
|
||||||
status: status,
|
status: status,
|
||||||
date: order.date,
|
date: order.date,
|
||||||
@@ -224,10 +224,9 @@ class ViewOrdersCubit extends Cubit<ViewOrdersState>
|
|||||||
).format(state.selectedDate!);
|
).format(state.selectedDate!);
|
||||||
|
|
||||||
// Filter by date
|
// Filter by date
|
||||||
final List<OrderItem> ordersOnDate =
|
final List<OrderItem> ordersOnDate = state.orders
|
||||||
state.orders
|
.where((OrderItem s) => s.date == selectedDateStr)
|
||||||
.where((OrderItem s) => s.date == selectedDateStr)
|
.toList();
|
||||||
.toList();
|
|
||||||
|
|
||||||
// Sort by start time
|
// Sort by start time
|
||||||
ordersOnDate.sort(
|
ordersOnDate.sort(
|
||||||
@@ -235,38 +234,35 @@ class ViewOrdersCubit extends Cubit<ViewOrdersState>
|
|||||||
);
|
);
|
||||||
|
|
||||||
if (state.filterTab == 'all') {
|
if (state.filterTab == 'all') {
|
||||||
final List<OrderItem> filtered =
|
final List<OrderItem> filtered = ordersOnDate
|
||||||
ordersOnDate
|
.where(
|
||||||
.where(
|
(OrderItem s) =>
|
||||||
(OrderItem s) =>
|
// TODO(orders): move PENDING to its own tab once available.
|
||||||
// TODO(orders): move PENDING to its own tab once available.
|
<String>[
|
||||||
<String>[
|
'OPEN',
|
||||||
'OPEN',
|
'FILLED',
|
||||||
'FILLED',
|
'CONFIRMED',
|
||||||
'CONFIRMED',
|
'PENDING',
|
||||||
'PENDING',
|
'ASSIGNED',
|
||||||
'ASSIGNED',
|
].contains(s.status),
|
||||||
].contains(s.status),
|
)
|
||||||
)
|
.toList();
|
||||||
.toList();
|
|
||||||
print(
|
print(
|
||||||
'ViewOrders tab=all statuses=${ordersOnDate.map((OrderItem s) => s.status).toList()} filtered=${filtered.length}',
|
'ViewOrders tab=all statuses=${ordersOnDate.map((OrderItem s) => s.status).toList()} filtered=${filtered.length}',
|
||||||
);
|
);
|
||||||
return filtered;
|
return filtered;
|
||||||
} else if (state.filterTab == 'active') {
|
} else if (state.filterTab == 'active') {
|
||||||
final List<OrderItem> filtered =
|
final List<OrderItem> filtered = ordersOnDate
|
||||||
ordersOnDate
|
.where((OrderItem s) => s.status == 'IN_PROGRESS')
|
||||||
.where((OrderItem s) => s.status == 'IN_PROGRESS')
|
.toList();
|
||||||
.toList();
|
|
||||||
print(
|
print(
|
||||||
'ViewOrders tab=active statuses=${ordersOnDate.map((OrderItem s) => s.status).toList()} filtered=${filtered.length}',
|
'ViewOrders tab=active statuses=${ordersOnDate.map((OrderItem s) => s.status).toList()} filtered=${filtered.length}',
|
||||||
);
|
);
|
||||||
return filtered;
|
return filtered;
|
||||||
} else if (state.filterTab == 'completed') {
|
} else if (state.filterTab == 'completed') {
|
||||||
final List<OrderItem> filtered =
|
final List<OrderItem> filtered = ordersOnDate
|
||||||
ordersOnDate
|
.where((OrderItem s) => s.status == 'COMPLETED')
|
||||||
.where((OrderItem s) => s.status == 'COMPLETED')
|
.toList();
|
||||||
.toList();
|
|
||||||
print(
|
print(
|
||||||
'ViewOrders tab=completed statuses=${ordersOnDate.map((OrderItem s) => s.status).toList()} filtered=${filtered.length}',
|
'ViewOrders tab=completed statuses=${ordersOnDate.map((OrderItem s) => s.status).toList()} filtered=${filtered.length}',
|
||||||
);
|
);
|
||||||
@@ -322,4 +318,3 @@ class ViewOrdersCubit extends Cubit<ViewOrdersState>
|
|||||||
.length;
|
.length;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -149,6 +149,7 @@ class _ShiftDetailsPageState extends State<ShiftDetailsPage> {
|
|||||||
const Divider(height: 1, thickness: 0.5),
|
const Divider(height: 1, thickness: 0.5),
|
||||||
ShiftDateTimeSection(
|
ShiftDateTimeSection(
|
||||||
date: displayShift.date,
|
date: displayShift.date,
|
||||||
|
endDate: displayShift.endDate,
|
||||||
startTime: displayShift.startTime,
|
startTime: displayShift.startTime,
|
||||||
endTime: displayShift.endTime,
|
endTime: displayShift.endTime,
|
||||||
shiftDateLabel: i18n.shift_date,
|
shiftDateLabel: i18n.shift_date,
|
||||||
|
|||||||
@@ -172,13 +172,6 @@ class _MyShiftCardState extends State<MyShiftCard> {
|
|||||||
color: UiColors.white,
|
color: UiColors.white,
|
||||||
borderRadius: UiConstants.radiusLg,
|
borderRadius: UiConstants.radiusLg,
|
||||||
border: Border.all(color: UiColors.border),
|
border: Border.all(color: UiColors.border),
|
||||||
boxShadow: [
|
|
||||||
BoxShadow(
|
|
||||||
color: UiColors.black.withValues(alpha: 0.05),
|
|
||||||
blurRadius: 2,
|
|
||||||
offset: const Offset(0, 1),
|
|
||||||
),
|
|
||||||
],
|
|
||||||
),
|
),
|
||||||
child: Padding(
|
child: Padding(
|
||||||
padding: const EdgeInsets.all(UiConstants.space4),
|
padding: const EdgeInsets.all(UiConstants.space4),
|
||||||
|
|||||||
@@ -7,6 +7,9 @@ class ShiftDateTimeSection extends StatelessWidget {
|
|||||||
/// The ISO string of the date.
|
/// The ISO string of the date.
|
||||||
final String date;
|
final String date;
|
||||||
|
|
||||||
|
/// The end date string (ISO).
|
||||||
|
final String? endDate;
|
||||||
|
|
||||||
/// The start time string (HH:mm).
|
/// The start time string (HH:mm).
|
||||||
final String startTime;
|
final String startTime;
|
||||||
|
|
||||||
@@ -26,6 +29,7 @@ class ShiftDateTimeSection extends StatelessWidget {
|
|||||||
const ShiftDateTimeSection({
|
const ShiftDateTimeSection({
|
||||||
super.key,
|
super.key,
|
||||||
required this.date,
|
required this.date,
|
||||||
|
required this.endDate,
|
||||||
required this.startTime,
|
required this.startTime,
|
||||||
required this.endTime,
|
required this.endTime,
|
||||||
required this.shiftDateLabel,
|
required this.shiftDateLabel,
|
||||||
@@ -63,21 +67,57 @@ class ShiftDateTimeSection extends StatelessWidget {
|
|||||||
child: Column(
|
child: Column(
|
||||||
crossAxisAlignment: CrossAxisAlignment.start,
|
crossAxisAlignment: CrossAxisAlignment.start,
|
||||||
children: [
|
children: [
|
||||||
Text(
|
Column(
|
||||||
shiftDateLabel,
|
crossAxisAlignment: CrossAxisAlignment.start,
|
||||||
style: UiTypography.titleUppercase4b.textSecondary,
|
|
||||||
),
|
|
||||||
const SizedBox(height: UiConstants.space2),
|
|
||||||
Row(
|
|
||||||
children: [
|
children: [
|
||||||
const Icon(UiIcons.calendar, size: 20, color: UiColors.primary),
|
|
||||||
const SizedBox(width: UiConstants.space2),
|
|
||||||
Text(
|
Text(
|
||||||
_formatDate(date),
|
shiftDateLabel,
|
||||||
style: UiTypography.headline5m.textPrimary,
|
style: UiTypography.titleUppercase4b.textSecondary,
|
||||||
|
),
|
||||||
|
const SizedBox(height: UiConstants.space2),
|
||||||
|
Row(
|
||||||
|
children: [
|
||||||
|
const Icon(
|
||||||
|
UiIcons.calendar,
|
||||||
|
size: 20,
|
||||||
|
color: UiColors.primary,
|
||||||
|
),
|
||||||
|
const SizedBox(width: UiConstants.space2),
|
||||||
|
Text(
|
||||||
|
_formatDate(date),
|
||||||
|
style: UiTypography.headline5m.textPrimary,
|
||||||
|
),
|
||||||
|
],
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
|
if (endDate != null) ...[
|
||||||
|
const SizedBox(height: UiConstants.space4),
|
||||||
|
Column(
|
||||||
|
crossAxisAlignment: CrossAxisAlignment.start,
|
||||||
|
children: [
|
||||||
|
Text(
|
||||||
|
shiftDateLabel,
|
||||||
|
style: UiTypography.titleUppercase4b.textSecondary,
|
||||||
|
),
|
||||||
|
const SizedBox(height: UiConstants.space2),
|
||||||
|
Row(
|
||||||
|
children: [
|
||||||
|
const Icon(
|
||||||
|
UiIcons.calendar,
|
||||||
|
size: 20,
|
||||||
|
color: UiColors.primary,
|
||||||
|
),
|
||||||
|
const SizedBox(width: UiConstants.space2),
|
||||||
|
Text(
|
||||||
|
_formatDate(endDate!),
|
||||||
|
style: UiTypography.headline5m.textPrimary,
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
],
|
||||||
const SizedBox(height: UiConstants.space4),
|
const SizedBox(height: UiConstants.space4),
|
||||||
Row(
|
Row(
|
||||||
children: [
|
children: [
|
||||||
|
|||||||
Reference in New Issue
Block a user