forked from eatvio/eatvio_app
feat(order info): added order info screen
This commit is contained in:
@@ -5,12 +5,12 @@ import 'package:flutter/material.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
|
||||
class AboutOrderButton extends StatelessWidget {
|
||||
const AboutOrderButton({super.key});
|
||||
|
||||
const AboutOrderButton({super.key, required this.onTap});
|
||||
final void Function() onTap;
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return GestureDetector(
|
||||
onTap: () {},
|
||||
onTap: onTap,
|
||||
child: Container(
|
||||
height: 44,
|
||||
decoration: BoxDecoration(
|
||||
@@ -20,13 +20,13 @@ class AboutOrderButton extends StatelessWidget {
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
SizedBox.shrink(),
|
||||
const SizedBox.shrink(),
|
||||
Text(
|
||||
S.current.more_about_order,
|
||||
style: TextStyles.textSMedium.copyWith(color: appTheme.black),
|
||||
),
|
||||
Container(
|
||||
margin: EdgeInsets.only(right: 4),
|
||||
margin: const EdgeInsets.only(right: 4),
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
|
||||
@@ -27,7 +27,7 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final size = MediaQuery.sizeOf(context);
|
||||
return Container(
|
||||
return SizedBox(
|
||||
width: size.width,
|
||||
child: Padding(
|
||||
padding: EdgeInsets.fromLTRB(isCurrentUser ? 64 : 16, 10, isCurrentUser ? 16 : 64, 4),
|
||||
@@ -41,7 +41,7 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
padding: const EdgeInsets.only(right: 4, bottom: 4),
|
||||
child: Text(
|
||||
sendTime.format('hh:mm'),
|
||||
style: TextStyle(
|
||||
style: const TextStyle(
|
||||
color: Color(0xFF7B8794),
|
||||
height: 1,
|
||||
fontSize: 10,
|
||||
@@ -52,16 +52,16 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
constraints: BoxConstraints(maxWidth: size.width * 0.7),
|
||||
decoration: BoxDecoration(
|
||||
color: isCurrentUser ? appTheme.gray50 : appTheme.gray60004,
|
||||
borderRadius: mediaData.length > 0
|
||||
borderRadius: mediaData.isNotEmpty
|
||||
? BorderRadius.circular(24)
|
||||
: BorderRadius.horizontal(
|
||||
left: isCurrentUser ? Radius.circular(32) : Radius.circular(16),
|
||||
right: isCurrentUser ? Radius.circular(16) : Radius.circular(24),
|
||||
left: isCurrentUser ? const Radius.circular(32) : const Radius.circular(16),
|
||||
right: isCurrentUser ? const Radius.circular(16) : const Radius.circular(24),
|
||||
),
|
||||
),
|
||||
child: Padding(
|
||||
padding:
|
||||
mediaData.isNotEmpty ? EdgeInsets.all(8) : EdgeInsets.only(top: 8, bottom: 8, left: isCurrentUser ? 16 : 8, right: isCurrentUser ? 8 : 16),
|
||||
mediaData.isNotEmpty ? const EdgeInsets.all(8) : EdgeInsets.only(top: 8, bottom: 8, left: isCurrentUser ? 16 : 8, right: isCurrentUser ? 8 : 16),
|
||||
child: Column(
|
||||
crossAxisAlignment: isCurrentUser ? CrossAxisAlignment.end : CrossAxisAlignment.start,
|
||||
children: [
|
||||
@@ -70,7 +70,7 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
width: size.width * 0.7,
|
||||
child: CustomScrollView(
|
||||
shrinkWrap: true,
|
||||
physics: NeverScrollableScrollPhysics(),
|
||||
physics: const NeverScrollableScrollPhysics(),
|
||||
slivers: [
|
||||
SliverList.separated(
|
||||
itemBuilder: (BuildContext context, int index) {
|
||||
@@ -78,25 +78,25 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
!mediaData[index].toString().contains('.jpg') &&
|
||||
!mediaData[index].toString().contains('.jpeg')) {
|
||||
return ListTile(
|
||||
contentPadding: EdgeInsets.all(4),
|
||||
contentPadding: const EdgeInsets.all(4),
|
||||
horizontalTitleGap: 8,
|
||||
onTap: () async {
|
||||
if (!await launchUrl(Uri.parse(baseUrl + '/storage/' + mediaData[index].toString()))) {
|
||||
if (!await launchUrl(Uri.parse('$baseUrl/storage/${mediaData[index]}'))) {
|
||||
throw Exception('Could not launch ${mediaData[index].toString()}');
|
||||
}
|
||||
},
|
||||
leading: Icon(
|
||||
leading: const Icon(
|
||||
Icons.file_copy_outlined,
|
||||
color: Colors.white,
|
||||
),
|
||||
trailing: Icon(
|
||||
trailing: const Icon(
|
||||
Icons.download_outlined,
|
||||
color: Colors.white,
|
||||
),
|
||||
title: Text(
|
||||
mediaData[index].toString().replaceAll('chat_files/', ''),
|
||||
maxLines: 2,
|
||||
style: TextStyle(
|
||||
style: const TextStyle(
|
||||
color: Colors.white,
|
||||
fontSize: 12,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
@@ -108,18 +108,18 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
onTap: () {
|
||||
context.pushTransparentRoute(
|
||||
PhotoViewScreen(
|
||||
imageUrls: mediaData.map((e) => baseUrl + '/storage/' + e.toString()).toList(),
|
||||
imageUrls: mediaData.map((e) => '$baseUrl/storage/$e').toList(),
|
||||
index: index,
|
||||
),
|
||||
);
|
||||
},
|
||||
child: Hero(
|
||||
tag: baseUrl + '/storage/' + '${mediaData[index]}',
|
||||
tag: '$baseUrl/storage/${mediaData[index]}',
|
||||
transitionOnUserGestures: true,
|
||||
child: ClipRRect(
|
||||
borderRadius: BorderRadius.circular(16),
|
||||
child: CachedNetworkImage(
|
||||
imageUrl: baseUrl + '/storage/' + '${mediaData[index]}',
|
||||
imageUrl: '$baseUrl/storage/${mediaData[index]}',
|
||||
),
|
||||
),
|
||||
),
|
||||
@@ -131,7 +131,7 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
],
|
||||
),
|
||||
),
|
||||
if (mediaData.isNotEmpty && text.isNotEmpty) SizedBox(height: 8),
|
||||
if (mediaData.isNotEmpty && text.isNotEmpty) const SizedBox(height: 8),
|
||||
if (text.isNotEmpty)
|
||||
Text(
|
||||
text,
|
||||
@@ -146,7 +146,7 @@ class ChatBubbleWidget extends StatelessWidget {
|
||||
padding: const EdgeInsets.only(left: 4, bottom: 4),
|
||||
child: Text(
|
||||
sendTime.format('hh:mm'),
|
||||
style: TextStyle(
|
||||
style: const TextStyle(
|
||||
color: Color(0xFF7B8794),
|
||||
height: 1,
|
||||
fontSize: 10,
|
||||
|
||||
@@ -8,7 +8,7 @@ import 'package:go_router/go_router.dart';
|
||||
class ChatEntryWidget extends StatefulWidget {
|
||||
final ChatRoom chatRoom;
|
||||
|
||||
ChatEntryWidget({
|
||||
const ChatEntryWidget({
|
||||
required this.chatRoom,
|
||||
super.key,
|
||||
});
|
||||
@@ -29,10 +29,10 @@ class _ChatEntryWidgetState extends State<ChatEntryWidget> {
|
||||
},
|
||||
),
|
||||
child: Ink(
|
||||
padding: EdgeInsets.all(12),
|
||||
padding: const EdgeInsets.all(12),
|
||||
decoration: BoxDecoration(
|
||||
borderRadius: BorderRadius.circular(16),
|
||||
color: Color(0xFFF6FAFF),
|
||||
color: const Color(0xFFF6FAFF),
|
||||
),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
@@ -52,10 +52,10 @@ class _ChatEntryWidgetState extends State<ChatEntryWidget> {
|
||||
Text(
|
||||
widget.chatRoom.users.toChatUser.name.length <= 20
|
||||
? widget.chatRoom.users.toChatUser.name
|
||||
: widget.chatRoom.users.toChatUser.name.substring(0, 20) + '...',
|
||||
: '${widget.chatRoom.users.toChatUser.name.substring(0, 20)}...',
|
||||
style: theme.textTheme.titleMedium,
|
||||
),
|
||||
SizedBox(height: 8),
|
||||
const SizedBox(height: 8),
|
||||
if (widget.chatRoom.lastMessage != null)
|
||||
SizedBox(
|
||||
width: MediaQuery.sizeOf(context).width * 0.5,
|
||||
@@ -68,22 +68,22 @@ class _ChatEntryWidgetState extends State<ChatEntryWidget> {
|
||||
),
|
||||
],
|
||||
),
|
||||
Spacer(),
|
||||
const Spacer(),
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.end,
|
||||
children: [
|
||||
if (widget.chatRoom.lastMessage != null)
|
||||
Padding(
|
||||
padding: EdgeInsets.only(left: 8),
|
||||
padding: const EdgeInsets.only(left: 8),
|
||||
child: Text(
|
||||
widget.chatRoom.lastMessage!.updatedAt.format('dd MMM', 'ru'),
|
||||
style: theme.textTheme.bodyMedium,
|
||||
),
|
||||
),
|
||||
SizedBox(height: 4),
|
||||
const SizedBox(height: 4),
|
||||
if (widget.chatRoom.unreadMessagesCount > 0)
|
||||
Container(
|
||||
padding: EdgeInsets.symmetric(horizontal: 8, vertical: 6),
|
||||
padding: const EdgeInsets.symmetric(horizontal: 8, vertical: 6),
|
||||
decoration: BoxDecoration(
|
||||
shape: BoxShape.circle,
|
||||
color: appTheme.blueA400,
|
||||
|
||||
@@ -3,8 +3,8 @@ import 'package:eatvio_app/core/theme/theme_helper.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class ChatSearchBarWidget extends StatelessWidget {
|
||||
ChatSearchBarWidget({
|
||||
Key? key,
|
||||
const ChatSearchBarWidget({
|
||||
super.key,
|
||||
this.alignment,
|
||||
this.width,
|
||||
this.scrollPadding,
|
||||
@@ -27,7 +27,7 @@ class ChatSearchBarWidget extends StatelessWidget {
|
||||
this.validator,
|
||||
this.onChanged,
|
||||
required this.onSuffixIconTap,
|
||||
}) : super(key: key);
|
||||
});
|
||||
|
||||
final Alignment? alignment;
|
||||
|
||||
@@ -107,7 +107,7 @@ class ChatSearchBarWidget extends StatelessWidget {
|
||||
hintText: hintText ?? "",
|
||||
hintStyle: hintStyle ?? CustomTextStyles.bodySmallMulishBluegray800,
|
||||
prefixIcon: prefix ??
|
||||
Padding(
|
||||
const Padding(
|
||||
padding: EdgeInsets.only(left: 12),
|
||||
child: Icon(
|
||||
Icons.search,
|
||||
@@ -126,7 +126,7 @@ class ChatSearchBarWidget extends StatelessWidget {
|
||||
),
|
||||
),
|
||||
isDense: true,
|
||||
contentPadding: EdgeInsets.all(16),
|
||||
contentPadding: const EdgeInsets.all(16),
|
||||
fillColor: fillColor ?? appTheme.gray100,
|
||||
filled: filled,
|
||||
border: borderDecoration ??
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
import 'package:eatvio_app/core/utils/toasts.dart';
|
||||
import 'package:eatvio_app/core/widgets/bottom_sheet_handler_bar.dart';
|
||||
import 'package:eatvio_app/core/widgets/custom_divider.dart';
|
||||
import 'package:eatvio_app/features/chat/presentation/bloc/chat_room_cubit/chat_room_cubit.dart';
|
||||
import 'package:eatvio_app/features/chat/presentation/bloc/chat_room_cubit/chat_room_state.dart';
|
||||
import 'package:eatvio_app/features/diets/presentation/widgets/calendar_widget.dart';
|
||||
import 'package:eatvio_app/generated/l10n.dart';
|
||||
import 'package:eatvio_app/core/theme/custom_text_style.dart';
|
||||
import 'package:eatvio_app/core/theme/theme_helper.dart';
|
||||
import 'package:eatvio_app/core/widgets/custom_outlined_button.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class ChosePlanDateWidget extends StatefulWidget {
|
||||
const ChosePlanDateWidget({super.key, required this.chatCubit});
|
||||
final ChatRoomCubit chatCubit;
|
||||
|
||||
@override
|
||||
State<ChosePlanDateWidget> createState() => _ChosePlanDateWidget();
|
||||
}
|
||||
|
||||
class _ChosePlanDateWidget extends State<ChosePlanDateWidget> {
|
||||
final startDate = [DateTime.now()];
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final s = S.of(context);
|
||||
String? planName;
|
||||
if (widget.chatCubit.state is ChatRoomStateLoaded) {
|
||||
planName = (widget.chatCubit.state as ChatRoomStateLoaded).chatRoom.chosenPlan?.plan.name;
|
||||
}
|
||||
return Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
const SizedBox(height: 4),
|
||||
const BottomSheetHandlerBar(),
|
||||
const SizedBox(height: 12),
|
||||
Text(
|
||||
planName ?? '',
|
||||
style: TextStyles.headingXLSemibold.copyWith(
|
||||
color: appTheme.black,
|
||||
),
|
||||
),
|
||||
const SizedBox(height: 12),
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 25.0),
|
||||
child: Text(
|
||||
s.chose_plan_start_date_2,
|
||||
textAlign: TextAlign.center,
|
||||
style: TextStyles.textMMedium.copyWith(
|
||||
color: appTheme.black,
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(height: 12),
|
||||
const Padding(
|
||||
padding: EdgeInsets.symmetric(horizontal: 16.0),
|
||||
child: CustomDivider(),
|
||||
),
|
||||
CalendarWidget(
|
||||
startDate: startDate,
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(left: 16, right: 16, top: 16, bottom: 28),
|
||||
child: CustomOutlinedButton(
|
||||
onPressed: () async {
|
||||
final result = await widget.chatCubit.choseStartPlanDate(startDate[0]);
|
||||
if (result) {
|
||||
showSuccessToast('Дата установлена');
|
||||
if (!context.mounted) return;
|
||||
Navigator.pop(context);
|
||||
} else {
|
||||
showErrorToast('Не удалось установить дату');
|
||||
if (!context.mounted) return;
|
||||
Navigator.pop(context);
|
||||
}
|
||||
},
|
||||
height: 60,
|
||||
text: s.confirm,
|
||||
buttonTextStyle: TextStyles.textLSemibold.copyWith(
|
||||
color: appTheme.whiteA700,
|
||||
),
|
||||
buttonStyle: ButtonStyle(
|
||||
backgroundColor: WidgetStatePropertyAll(appTheme.blueA400),
|
||||
side: const WidgetStatePropertyAll(BorderSide.none),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -1,8 +1,13 @@
|
||||
import 'package:eatvio_app/core/theme/custom_text_style.dart';
|
||||
import 'package:eatvio_app/core/theme/theme_helper.dart';
|
||||
import 'package:eatvio_app/features/chat/presentation/bloc/chat_room_cubit/chat_room_cubit.dart';
|
||||
import 'package:eatvio_app/features/chat/presentation/pages/payment_screen.dart';
|
||||
import 'package:eatvio_app/features/chat/presentation/widgets/chose_plan_date_widget.dart';
|
||||
import 'package:eatvio_app/generated/l10n.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:go_router/go_router.dart';
|
||||
|
||||
class NotificationBanner extends StatelessWidget {
|
||||
const NotificationBanner({super.key, required this.bannerType});
|
||||
@@ -32,38 +37,52 @@ class NotificationBanner extends StatelessWidget {
|
||||
BannerType.date => [
|
||||
SizedBox(
|
||||
width: size.width * 0.6,
|
||||
child: Text(s.can_not_choose_start_date, style: TextStyles.textMMedium.copyWith(color: appTheme.black)),
|
||||
child: Text(s.choose_plan_start_date, style: TextStyles.textMMedium.copyWith(color: appTheme.black)),
|
||||
),
|
||||
SizedBox(height: 12),
|
||||
const SizedBox(height: 12),
|
||||
GestureDetector(
|
||||
onTap: () {},
|
||||
child: Text(s.add_card, style: TextStyles.textLSemibold.copyWith(color: appTheme.blueA400)),
|
||||
onTap: () {
|
||||
final cubit = context.read<ChatRoomCubit>();
|
||||
showModalBottomSheet(
|
||||
context: context,
|
||||
builder: (context) => ChosePlanDateWidget(
|
||||
chatCubit: cubit,
|
||||
),
|
||||
);
|
||||
},
|
||||
child: Text(s.choose_date, style: TextStyles.textLSemibold.copyWith(color: appTheme.blueA400)),
|
||||
),
|
||||
SizedBox(height: 16),
|
||||
const SizedBox(height: 16),
|
||||
],
|
||||
BannerType.card => [
|
||||
SizedBox(
|
||||
width: size.width * 0.6,
|
||||
child: Text(s.can_not_choose_start_date, style: TextStyles.textMMedium.copyWith(color: appTheme.black)),
|
||||
),
|
||||
SizedBox(height: 12),
|
||||
const SizedBox(height: 12),
|
||||
GestureDetector(
|
||||
onTap: () {},
|
||||
child: Text(s.add_card, style: TextStyles.textLSemibold.copyWith(color: appTheme.blueA400)),
|
||||
),
|
||||
SizedBox(height: 16),
|
||||
const SizedBox(height: 16),
|
||||
],
|
||||
BannerType.payment => [
|
||||
SizedBox(
|
||||
width: size.width * 0.6,
|
||||
child: Text(s.can_not_choose_start_date, style: TextStyles.textMMedium.copyWith(color: appTheme.black)),
|
||||
child: Text(s.tap_on_link_to_pay, style: TextStyles.textMMedium.copyWith(color: appTheme.black)),
|
||||
),
|
||||
SizedBox(height: 12),
|
||||
const SizedBox(height: 12),
|
||||
GestureDetector(
|
||||
onTap: () {},
|
||||
child: Text(s.add_card, style: TextStyles.textLSemibold.copyWith(color: appTheme.blueA400)),
|
||||
onTap: () async {
|
||||
final paymentLink = await context.read<ChatRoomCubit>().getPaymentLink();
|
||||
if (paymentLink != null) {
|
||||
if (!context.mounted) return;
|
||||
GoRouter.of(context).push(PaymentScreen.path, extra: paymentLink);
|
||||
}
|
||||
},
|
||||
child: Text(s.pay, style: TextStyles.textLSemibold.copyWith(color: appTheme.blueA400)),
|
||||
),
|
||||
SizedBox(height: 16),
|
||||
const SizedBox(height: 16),
|
||||
],
|
||||
},
|
||||
),
|
||||
|
||||
@@ -33,8 +33,8 @@ class _OrderCardState extends State<OrderCard> {
|
||||
};
|
||||
final s = S.of(context);
|
||||
return Container(
|
||||
margin: EdgeInsets.symmetric(horizontal: 16),
|
||||
padding: EdgeInsets.only(top: 8, bottom: 12, left: 8, right: 8),
|
||||
margin: const EdgeInsets.symmetric(horizontal: 16),
|
||||
padding: const EdgeInsets.only(top: 8, bottom: 12, left: 8, right: 8),
|
||||
decoration: BoxDecoration(borderRadius: BorderRadius.circular(12), color: appTheme.gray60004),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
@@ -47,7 +47,7 @@ class _OrderCardState extends State<OrderCard> {
|
||||
ClipRRect(
|
||||
borderRadius: BorderRadius.circular(12),
|
||||
child: Image.network(
|
||||
baseUrl + '/storage/' + widget.plan.image,
|
||||
'$baseUrl/storage/${widget.plan.image}',
|
||||
width: double.infinity,
|
||||
fit: BoxFit.cover,
|
||||
),
|
||||
@@ -59,7 +59,7 @@ class _OrderCardState extends State<OrderCard> {
|
||||
padding: const EdgeInsets.symmetric(horizontal: 10, vertical: 5),
|
||||
decoration: BoxDecoration(
|
||||
color: appTheme.blueA400,
|
||||
borderRadius: BorderRadius.only(
|
||||
borderRadius: const BorderRadius.only(
|
||||
topRight: Radius.circular(12),
|
||||
bottomRight: Radius.circular(12),
|
||||
),
|
||||
@@ -77,7 +77,7 @@ class _OrderCardState extends State<OrderCard> {
|
||||
padding: const EdgeInsets.symmetric(horizontal: 10, vertical: 5),
|
||||
decoration: BoxDecoration(
|
||||
color: appTheme.greenA700,
|
||||
borderRadius: BorderRadius.only(
|
||||
borderRadius: const BorderRadius.only(
|
||||
topRight: Radius.circular(12),
|
||||
bottomRight: Radius.circular(12),
|
||||
),
|
||||
@@ -91,17 +91,17 @@ class _OrderCardState extends State<OrderCard> {
|
||||
],
|
||||
),
|
||||
),
|
||||
SizedBox(height: 12),
|
||||
const SizedBox(height: 12),
|
||||
Text(
|
||||
'${widget.plan.name}',
|
||||
widget.plan.name,
|
||||
style: TextStyles.headingXLSemibold.copyWith(color: appTheme.black),
|
||||
),
|
||||
SizedBox(height: 12),
|
||||
const SizedBox(height: 12),
|
||||
Text(
|
||||
'${s.option}: ${option?.short ?? ''}',
|
||||
style: TextStyles.textMSemibold.copyWith(color: appTheme.black),
|
||||
),
|
||||
SizedBox(height: 8),
|
||||
const SizedBox(height: 8),
|
||||
if (option != null)
|
||||
...option.items
|
||||
.map(
|
||||
@@ -114,11 +114,11 @@ class _OrderCardState extends State<OrderCard> {
|
||||
),
|
||||
),
|
||||
)
|
||||
.toList(),
|
||||
,
|
||||
if (widget.isCustomerView) ...[
|
||||
SizedBox(height: 8),
|
||||
const SizedBox(height: 8),
|
||||
isLoading
|
||||
? Loader()
|
||||
? const Loader()
|
||||
: GestureDetector(
|
||||
onTap: () async {
|
||||
setState(() => isLoading = true);
|
||||
@@ -126,7 +126,7 @@ class _OrderCardState extends State<OrderCard> {
|
||||
setState(() => isLoading = false);
|
||||
},
|
||||
child: Text(
|
||||
'${s.cancel_order}',
|
||||
s.cancel_order,
|
||||
style: TextStyles.textSMedium.copyWith(color: appTheme.strongRed),
|
||||
),
|
||||
),
|
||||
|
||||
Reference in New Issue
Block a user