Skip to content

Commit 70981e8

Browse files
committed
show request shipping tracking links if available
1 parent 1b9d281 commit 70981e8

3 files changed

Lines changed: 90 additions & 19 deletions

File tree

lib/pages/shopinbit/shopinbit_ticket_detail.dart

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,10 @@ import '../../utilities/util.dart';
2424
import '../../widgets/background.dart';
2525
import '../../widgets/conditional_parent.dart';
2626
import '../../widgets/custom_buttons/app_bar_icon_button.dart';
27+
import '../../widgets/custom_buttons/blue_text_button.dart';
2728
import '../../widgets/desktop/desktop_dialog_close_button.dart';
2829
import '../../widgets/desktop/primary_button.dart';
30+
import '../../widgets/detail_item.dart';
2931
import '../../widgets/dialogs/s_dialog.dart';
3032
import '../../widgets/loading_indicator.dart';
3133
import '../../widgets/refresh_control.dart';
@@ -220,6 +222,8 @@ class _ShopInBitTicketDetailState extends ConsumerState<ShopInBitTicketDetail>
220222
final isCarResearch = ticket?.category == ShopInBitCategory.car;
221223
final messages = <TicketMessage>[...?ticket?.messages, ..._pending];
222224

225+
final trackingLinks = splitTrackingLinks(ticket?.trackingLink).toList();
226+
223227
final statusBar = Padding(
224228
padding: .only(bottom: isDesktop ? 12 : 8),
225229
child: RoundedWhiteContainer(
@@ -452,6 +456,11 @@ class _ShopInBitTicketDetailState extends ConsumerState<ShopInBitTicketDetail>
452456
statusBar,
453457
offerBanner,
454458
requestDetailsSection,
459+
if (trackingLinks.isNotEmpty)
460+
Padding(
461+
padding: EdgeInsets.only(bottom: isDesktop ? 12 : 8),
462+
child: _TrackingLinks(trackingLinks: trackingLinks),
463+
),
455464
chatArea,
456465
SizedBox(height: isDesktop ? 12 : 8),
457466
inputBar,
@@ -927,3 +936,53 @@ class _AttachmentImageFallback extends StatelessWidget {
927936
);
928937
}
929938
}
939+
940+
class _TrackingLinks extends StatelessWidget {
941+
const _TrackingLinks({super.key, required this.trackingLinks});
942+
943+
final List<String> trackingLinks;
944+
945+
@override
946+
Widget build(BuildContext context) {
947+
return DetailItemBase(
948+
horizontal: true,
949+
expandDetail: true,
950+
crossAxisAlignment: .start,
951+
title: Text(
952+
"Tracking link(s)",
953+
style: Util.isDesktop
954+
? STextStyles.desktopTextSmall(context)
955+
: STextStyles.titleBold12(context),
956+
),
957+
detail: Column(
958+
mainAxisSize: .min,
959+
crossAxisAlignment: .start,
960+
children: [
961+
...trackingLinks.map(
962+
(e) => CustomTextButton(
963+
text: e,
964+
overflow: .ellipsis,
965+
onTap: () async {
966+
try {
967+
await launchUrl(
968+
Uri.parse(e),
969+
mode: LaunchMode.externalApplication,
970+
);
971+
} catch (e, s) {
972+
Logging.instance.e(
973+
"Failed to open shipping tracking link",
974+
error: e,
975+
stackTrace: s,
976+
);
977+
}
978+
},
979+
),
980+
),
981+
],
982+
),
983+
borderColor: Util.isDesktop
984+
? Theme.of(context).extension<StackColors>()!.textFieldDefaultBG
985+
: null,
986+
);
987+
}
988+
}

lib/widgets/custom_buttons/blue_text_button.dart

Lines changed: 23 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010

1111
import 'package:flutter/gestures.dart';
1212
import 'package:flutter/material.dart';
13+
1314
import '../../themes/stack_colors.dart';
1415
import '../../utilities/text_styles.dart';
1516
import '../../utilities/util.dart';
@@ -25,6 +26,7 @@ class _CustomTextButton extends StatefulWidget {
2526
this.onTap,
2627
this.enabled = true,
2728
this.textSize,
29+
required this.overflow,
2830
});
2931

3032
final String text;
@@ -33,6 +35,7 @@ class _CustomTextButton extends StatefulWidget {
3335
final double? textSize;
3436
final Color enabledColor;
3537
final Color disabledColor;
38+
final TextOverflow overflow;
3639

3740
@override
3841
State<_CustomTextButton> createState() => _CustomTextButtonState();
@@ -103,22 +106,22 @@ class _CustomTextButtonState extends State<_CustomTextButton>
103106
},
104107
child: RichText(
105108
textAlign: TextAlign.center,
109+
overflow: widget.overflow,
106110
text: TextSpan(
107111
text: widget.text,
108112
style: widget.textSize == null
109-
? STextStyles.link2(context).copyWith(
110-
color: color,
111-
)
112-
: STextStyles.link2(context).copyWith(
113-
color: color,
114-
fontSize: widget.textSize,
115-
),
113+
? STextStyles.link2(context).copyWith(color: color)
114+
: STextStyles.link2(
115+
context,
116+
).copyWith(color: color, fontSize: widget.textSize),
116117
recognizer: widget.enabled
117118
? (TapGestureRecognizer()
118-
..onTap = () {
119-
widget.onTap?.call();
120-
controller?.forward().then((value) => controller?.reverse());
121-
})
119+
..onTap = () {
120+
widget.onTap?.call();
121+
controller?.forward().then(
122+
(value) => controller?.reverse(),
123+
);
124+
})
122125
: null,
123126
),
124127
),
@@ -133,26 +136,29 @@ class CustomTextButton extends StatelessWidget {
133136
this.onTap,
134137
this.enabled = true,
135138
this.textSize,
139+
this.overflow = .clip,
136140
});
137141

138142
final String text;
139143
final VoidCallback? onTap;
140144
final bool enabled;
141145
final double? textSize;
146+
final TextOverflow overflow;
142147

143148
@override
144149
Widget build(BuildContext context) {
145150
return _CustomTextButton(
146151
key: UniqueKey(),
147152
text: text,
148-
enabledColor: Theme.of(context)
149-
.extension<StackColors>()!
150-
.customTextButtonEnabledText,
151-
disabledColor: Theme.of(context)
152-
.extension<StackColors>()!
153-
.customTextButtonDisabledText,
153+
enabledColor: Theme.of(
154+
context,
155+
).extension<StackColors>()!.customTextButtonEnabledText,
156+
disabledColor: Theme.of(
157+
context,
158+
).extension<StackColors>()!.customTextButtonDisabledText,
154159
enabled: enabled,
155160
textSize: textSize,
161+
overflow: overflow,
156162
onTap: onTap,
157163
);
158164
}

lib/widgets/detail_item.dart

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,8 @@ class DetailItemBase extends StatelessWidget {
8282
this.borderColor,
8383
this.expandDetail = false,
8484
this.noPadding = false,
85+
this.crossAxisAlignment,
86+
this.mainAxisAlignment,
8587
});
8688

8789
final Widget title;
@@ -91,6 +93,8 @@ class DetailItemBase extends StatelessWidget {
9193
final Color? borderColor;
9294
final bool expandDetail;
9395
final bool noPadding;
96+
final CrossAxisAlignment? crossAxisAlignment;
97+
final MainAxisAlignment? mainAxisAlignment;
9498

9599
@override
96100
Widget build(BuildContext context) {
@@ -113,7 +117,8 @@ class DetailItemBase extends StatelessWidget {
113117
),
114118
child: horizontal
115119
? Row(
116-
mainAxisAlignment: MainAxisAlignment.spaceBetween,
120+
mainAxisAlignment: mainAxisAlignment ?? .spaceBetween,
121+
crossAxisAlignment: crossAxisAlignment ?? .center,
117122
children: [
118123
title,
119124
if (expandDetail) const SizedBox(width: 16),
@@ -125,7 +130,8 @@ class DetailItemBase extends StatelessWidget {
125130
],
126131
)
127132
: Column(
128-
crossAxisAlignment: CrossAxisAlignment.start,
133+
mainAxisAlignment: mainAxisAlignment ?? .start,
134+
crossAxisAlignment: crossAxisAlignment ?? .start,
129135
children: [
130136
Row(
131137
mainAxisAlignment: MainAxisAlignment.spaceBetween,

0 commit comments

Comments
 (0)