From 4922f517ad60116aec07a2c62b3ebe96be1c973c Mon Sep 17 00:00:00 2001 From: Seyed Amir Hossein Mosavi Date: Tue, 5 Sep 2023 16:40:20 +0330 Subject: [PATCH 1/4] fixed bugs in the comments section --- lib/views/home/comments/comments_state.dart | 39 ++++--- lib/views/home/comments/widgets/comment.dart | 108 ++++++++++--------- 2 files changed, 74 insertions(+), 73 deletions(-) diff --git a/lib/views/home/comments/comments_state.dart b/lib/views/home/comments/comments_state.dart index a817171..4a0594c 100644 --- a/lib/views/home/comments/comments_state.dart +++ b/lib/views/home/comments/comments_state.dart @@ -32,6 +32,7 @@ class CommentsState extends CoreProvier { ); await service.httpGet(); if (service.isSuccess) { + comments.clear(); final messages = service.result['comments']; for (var i = 0; i < messages.length; i++) { comments.add(CommentData.fromJson(messages[i])); @@ -126,9 +127,6 @@ class CommentsState extends CoreProvier { ); } - _count++; - onCommentsChanged(_count); - final body = {}; if (commentId != null) { @@ -175,36 +173,35 @@ class CommentsState extends CoreProvier { ); } - void deleteComment(int id, int? rootId) { + void deleteComment(int id, int status, int? rootId) async { final service = RequestService(RequestHelper.deleteComment(id)); service.delete(); if (rootId == null) { final comment = comments.firstWhere((element) => element.id == id); if (comment.replies.isNotEmpty) { - comments.insertAll( - comments.indexOf(comment), - comment.replies.map( - (rep) => CommentData( - id: rep.id, - text: rep.text, - createdAt: rep.createdAt, - liked: rep.liked, - disliked: rep.disliked, - feedback: rep.feedback, - user: rep.user, - replies: [], - status: 2, - ), - ), - ); + _count = 0; + await getComments(); + onCommentsChanged(_count); + } else { + comments.remove(comment); + + if (status != 2) { + _count--; + onCommentsChanged(_count); + } } - comments.remove(comment); } else { comments .firstWhere((element) => element.id == rootId) .replies .removeWhere((element) => element.id == id); + + if (status != 2) { + _count--; + onCommentsChanged(_count); + } } + notifyListeners(); } } diff --git a/lib/views/home/comments/widgets/comment.dart b/lib/views/home/comments/widgets/comment.dart index 8ca602c..44ee164 100644 --- a/lib/views/home/comments/widgets/comment.dart +++ b/lib/views/home/comments/widgets/comment.dart @@ -141,64 +141,67 @@ class CommentState extends State { ], ), const SizedBox(height: 8), - Row( - children: [ - InkWrapper( - onPressed: () { - state.commentId = _comment.id; - state.replyingTo = comment.user; - state.showReplyBox = true; - state.update(); - widget.focusNode.requestFocus(); - }, - child: DidvanText( - 'پاسخ', - style: Theme.of(context).textTheme.bodyLarge, - color: Theme.of(context).colorScheme.primary, - ), - ), - if (!isReply) const SizedBox(width: 20), - if (!isReply && comment.replies.isNotEmpty) + if (_comment.status != 2) + Row( + children: [ InkWrapper( - onPressed: () => setState( - () => _showSubComments = !_showSubComments, + onPressed: () { + state.commentId = _comment.id; + state.replyingTo = comment.user; + state.showReplyBox = true; + state.update(); + widget.focusNode.requestFocus(); + }, + child: DidvanText( + 'پاسخ', + style: Theme.of(context).textTheme.bodyLarge, + color: Theme.of(context).colorScheme.primary, ), - child: Row( - children: [ - DidvanText( - 'پاسخ‌ها(${comment.replies.length})', - style: Theme.of(context).textTheme.bodyLarge, - color: Theme.of(context).colorScheme.primary, - ), - AnimatedRotation( - duration: DesignConfig.lowAnimationDuration, - turns: _showSubComments ? 0.5 : 0, - child: Icon( - DidvanIcons.angle_down_regular, + ), + if (!isReply) const SizedBox(width: 20), + if (!isReply && comment.replies.isNotEmpty) + InkWrapper( + onPressed: () => setState( + () => _showSubComments = !_showSubComments, + ), + child: Row( + children: [ + DidvanText( + 'پاسخ‌ها(${comment.replies.length})', + style: Theme.of(context).textTheme.bodyLarge, color: Theme.of(context).colorScheme.primary, ), - ), - ], + AnimatedRotation( + duration: DesignConfig.lowAnimationDuration, + turns: _showSubComments ? 0.5 : 0, + child: Icon( + DidvanIcons.angle_down_regular, + color: + Theme.of(context).colorScheme.primary, + ), + ), + ], + ), + ), + const Spacer(), + _FeedbackButtons( + likeCount: comment.feedback.like, + dislikeCount: comment.feedback.dislike, + likeValue: comment.liked, + dislikeValue: comment.disliked, + onFeedback: + (like, dislike, likeCount, dislikeCount) => + state.feedback( + id: _comment.id, + like: like, + dislike: dislike, + likeCount: likeCount, + dislikeCount: dislikeCount, + replyId: isReply ? comment.id : null, ), ), - const Spacer(), - _FeedbackButtons( - likeCount: comment.feedback.like, - dislikeCount: comment.feedback.dislike, - likeValue: comment.liked, - dislikeValue: comment.disliked, - onFeedback: (like, dislike, likeCount, dislikeCount) => - state.feedback( - id: _comment.id, - like: like, - dislike: dislike, - likeCount: likeCount, - dislikeCount: dislikeCount, - replyId: isReply ? comment.id : null, - ), - ), - ], - ), + ], + ), ], ), ), @@ -228,6 +231,7 @@ class CommentState extends State { onTap: () { state.deleteComment( comment.id, + comment.status, comment.runtimeType == Reply ? _comment.id : null, ); ActionSheetUtils.pop(); From 6c55a79d2d1e6a2aaa49896a96d3d875548636d9 Mon Sep 17 00:00:00 2001 From: Seyed Amir Hossein Mosavi Date: Tue, 5 Sep 2023 16:51:47 +0330 Subject: [PATCH 2/4] fixed a bug in alert display --- lib/utils/action_sheet.dart | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/lib/utils/action_sheet.dart b/lib/utils/action_sheet.dart index 1c550dd..7fdaab2 100644 --- a/lib/utils/action_sheet.dart +++ b/lib/utils/action_sheet.dart @@ -194,17 +194,19 @@ class ActionSheetUtils { Row( mainAxisSize: MainAxisSize.min, children: [ - GestureDetector( - onTap: () => Navigator.of(context).pop(), - child: Icon( - data.titleIcon, - size: 20, - color: data.titleColor, + if (data.titleIcon != null) + GestureDetector( + onTap: () => Navigator.of(context).pop(), + child: Icon( + data.titleIcon, + size: 20, + color: data.titleColor, + ), + ), + if (data.titleIcon != null) + const SizedBox( + width: 8, ), - ), - const SizedBox( - width: 8, - ), Expanded( child: DidvanText( data.title!, From 5bd556e691d6e4791f8b8cb0e3408d3c104ec14f Mon Sep 17 00:00:00 2001 From: Seyed Amir Hossein Mosavi Date: Tue, 5 Sep 2023 16:53:52 +0330 Subject: [PATCH 3/4] Fixed bugs in font changes --- .../home/settings/general_settings/settings.dart | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/lib/views/home/settings/general_settings/settings.dart b/lib/views/home/settings/general_settings/settings.dart index 169b095..4f6f0c4 100644 --- a/lib/views/home/settings/general_settings/settings.dart +++ b/lib/views/home/settings/general_settings/settings.dart @@ -31,8 +31,8 @@ class GeneralSettings extends StatefulWidget { } class _GeneralSettingsState extends State { - String get _fontScaleSuffix { - final fontScale = DesignConfig.fontScale; + String fontScaleSuffix(double fontSizeScale) { + final fontScale = fontSizeScale; if (fontScale == 1) return 'متوسط'; if (fontScale == 1.15) return 'بزرگ'; return 'کوچک'; @@ -70,15 +70,14 @@ class _GeneralSettingsState extends State { child: Column( children: [ MenuOption( - suffix: DesignConfig.fontFamily == 'Dana-FA' - ? 'دانا' - : 'ایران سنس', + suffix: + state.fontFamily == 'Dana-FA' ? 'دانا' : 'ایران سنس', title: 'فونت برنامه', onTap: _showFontFamilyBottomSheet, ), const DidvanDivider(), MenuOption( - suffix: _fontScaleSuffix, + suffix: fontScaleSuffix(state.fontSizeScale), title: 'اندازه متن', onTap: _showFontScaleBottomSheet, ), From bb7f683389c1dcb3e33bc2d85e4b9fa1fd582b44 Mon Sep 17 00:00:00 2001 From: Seyed Amir Hossein Mosavi Date: Mon, 18 Sep 2023 08:04:40 +0330 Subject: [PATCH 4/4] add bug report section to news --- lib/models/message_data/message_data.dart | 6 ++ lib/models/message_data/news_attachment.dart | 30 ++++++ lib/views/home/direct/direct.dart | 8 +- lib/views/home/direct/direct_state.dart | 11 ++ lib/views/home/direct/widgets/message.dart | 65 +++++++++++- .../home/direct/widgets/message_box.dart | 8 +- .../home/widgets/floating_navigation_bar.dart | 100 ++++++++++-------- 7 files changed, 177 insertions(+), 51 deletions(-) create mode 100644 lib/models/message_data/news_attachment.dart diff --git a/lib/models/message_data/message_data.dart b/lib/models/message_data/message_data.dart index 1778abc..cc9f81f 100644 --- a/lib/models/message_data/message_data.dart +++ b/lib/models/message_data/message_data.dart @@ -1,6 +1,7 @@ import 'dart:convert'; import 'dart:io'; +import 'news_attachment.dart'; import 'radar_attachment.dart'; class MessageData { @@ -10,6 +11,7 @@ class MessageData { final bool writedByAdmin; final bool readed; final String createdAt; + final NewsAttachment? news; final RadarAttachment? radar; final File? audioFile; final int? audioDuration; @@ -21,6 +23,7 @@ class MessageData { required this.createdAt, this.text, this.audio, + this.news, this.radar, this.audioFile, this.audioDuration, @@ -39,6 +42,8 @@ class MessageData { radar: json['radar'] == null ? null : RadarAttachment.fromJson(json['radar']), + news: + json['news'] == null ? null : NewsAttachment.fromJson(json['news']), ); Map toJson() => { @@ -48,6 +53,7 @@ class MessageData { 'writedByAdmin': writedByAdmin, 'readed': readed, 'createdAt': createdAt, + 'news': news?.toJson(), 'radar': radar?.toJson(), }; } diff --git a/lib/models/message_data/news_attachment.dart b/lib/models/message_data/news_attachment.dart new file mode 100644 index 0000000..15f8e26 --- /dev/null +++ b/lib/models/message_data/news_attachment.dart @@ -0,0 +1,30 @@ +class NewsAttachment { + final int id; + final String title; + final String description; + final String image; + final String createdAt; + + const NewsAttachment({ + required this.id, + required this.title, + required this.description, + required this.image, + required this.createdAt, + }); + + factory NewsAttachment.fromJson(Map json) => NewsAttachment( + id: json['id'], + title: json['title'], + description: json['description'], + image: json['image'], + createdAt: json['createdAt'], + ); + + Map toJson() => { + 'id': id, + 'title': title, + 'description': description, + 'image': image, + }; +} diff --git a/lib/views/home/direct/direct.dart b/lib/views/home/direct/direct.dart index 915d3c0..3eec029 100644 --- a/lib/views/home/direct/direct.dart +++ b/lib/views/home/direct/direct.dart @@ -28,6 +28,7 @@ class _DirectState extends State { @override void initState() { final state = context.read(); + state.replyNews = widget.pageData['newsAttachment']; state.replyRadar = widget.pageData['radarAttachment']; final typeId = ServerDataProvider.labelToTypeId(widget.pageData['type']); state.typeId = typeId; @@ -68,9 +69,10 @@ class _DirectState extends State { slivers: [ if (state.appState != AppState.busy) SliverPadding( - padding: state.replyRadar == null - ? EdgeInsets.zero - : const EdgeInsets.only(bottom: 68), + padding: + state.replyRadar == null && state.replyNews == null + ? EdgeInsets.zero + : const EdgeInsets.only(bottom: 68), sliver: SliverStateHandler( itemPadding: const EdgeInsets.only(bottom: 12), state: state, diff --git a/lib/views/home/direct/direct_state.dart b/lib/views/home/direct/direct_state.dart index 3b33748..9a0d28c 100644 --- a/lib/views/home/direct/direct_state.dart +++ b/lib/views/home/direct/direct_state.dart @@ -2,6 +2,7 @@ import 'dart:io'; import 'package:didvan/models/enums.dart'; import 'package:didvan/models/message_data/message_data.dart'; +import 'package:didvan/models/message_data/news_attachment.dart'; import 'package:didvan/models/message_data/radar_attachment.dart'; import 'package:didvan/providers/core.dart'; import 'package:didvan/services/media/media.dart'; @@ -19,6 +20,7 @@ class DirectState extends CoreProvier { final List deletionQueue = []; String? text; + NewsAttachment? replyNews; RadarAttachment? replyRadar; File? recordedFile; int? audioDuration; @@ -116,21 +118,30 @@ class DirectState extends CoreProvier { audio: null, audioFile: recordedFile, radar: replyRadar, + news: replyNews, audioDuration: audioDuration, ), ); _addToDailyGrouped(messages.first); final body = {}; + if (text != null) { body.addAll({'text': text}); } + if (replyRadar != null) { body.addAll({'radarId': replyRadar!.id}); } + + if (replyNews != null) { + body.addAll({'newsId': replyNews!.id}); + } + final uploadFile = recordedFile; text = null; recordedFile = null; replyRadar = null; + replyNews = null; notifyListeners(); final service = RequestService(RequestHelper.sendDirectMessage(typeId), body: body); diff --git a/lib/views/home/direct/widgets/message.dart b/lib/views/home/direct/widgets/message.dart index 1f2476e..9c45b3b 100644 --- a/lib/views/home/direct/widgets/message.dart +++ b/lib/views/home/direct/widgets/message.dart @@ -89,11 +89,16 @@ class Message extends StatelessWidget { audioUrl: message.audio, id: message.id, ), - if (message.radar != null) const DidvanDivider(), - if (message.radar != null) const SizedBox(height: 4), + if (message.radar != null || message.news != null) + const DidvanDivider(), + if (message.radar != null || message.news != null) + const SizedBox(height: 4), if (message.radar != null) _ReplyRadarOverview(message: message), - if (message.radar != null) const SizedBox(height: 4), + if (message.news != null) + _ReplyNewsOverview(message: message), + if (message.radar != null || message.news != null) + const SizedBox(height: 4), ], ), ), @@ -168,7 +173,59 @@ class _ReplyRadarOverview extends StatelessWidget { color: Theme.of(context).colorScheme.focusedBorder, style: Theme.of(context).textTheme.labelSmall, ), - // DidvanText('text'), + ], + ), + ], + ), + ), + ), + ], + ); + } +} + +class _ReplyNewsOverview extends StatelessWidget { + final MessageData message; + const _ReplyNewsOverview({Key? key, required this.message}) : super(key: key); + + @override + Widget build(BuildContext context) { + return Row( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + SkeletonImage( + imageUrl: message.news!.image, + height: 52, + width: 52, + ), + const SizedBox(width: 8), + Expanded( + child: SizedBox( + height: 52, + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + DidvanText( + message.news!.title, + style: Theme.of(context).textTheme.bodyLarge, + maxLines: 1, + overflow: TextOverflow.ellipsis, + color: Theme.of(context).colorScheme.focusedBorder, + ), + Row( + children: [ + DidvanText( + 'خبر', + style: Theme.of(context).textTheme.labelSmall, + color: Theme.of(context).colorScheme.focusedBorder, + ), + const Spacer(), + DidvanText( + DateTimeUtils.momentGenerator(message.news!.createdAt), + color: Theme.of(context).colorScheme.focusedBorder, + style: Theme.of(context).textTheme.labelSmall, + ), ], ), ], diff --git a/lib/views/home/direct/widgets/message_box.dart b/lib/views/home/direct/widgets/message_box.dart index 8cbcdd3..23829fc 100644 --- a/lib/views/home/direct/widgets/message_box.dart +++ b/lib/views/home/direct/widgets/message_box.dart @@ -17,7 +17,8 @@ class MessageBox extends StatelessWidget { return Column( children: [ Consumer( - builder: (context, state, child) => state.replyRadar != null + builder: (context, state, child) => state.replyRadar != null || + state.replyNews != null ? _MessageBoxContainer( isMessage: false, child: Padding( @@ -32,7 +33,9 @@ class MessageBox extends StatelessWidget { 'لینک به مطلب:', ), DidvanText( - state.replyRadar!.title, + state.replyRadar != null + ? state.replyRadar!.title + : state.replyNews!.title, overflow: TextOverflow.ellipsis, maxLines: 1, color: Theme.of(context).colorScheme.primary, @@ -45,6 +48,7 @@ class MessageBox extends StatelessWidget { gestureSize: 24, onPressed: () { state.replyRadar = null; + state.replyNews = null; state.update(); }, ), diff --git a/lib/views/home/widgets/floating_navigation_bar.dart b/lib/views/home/widgets/floating_navigation_bar.dart index c3d8122..00ddb32 100644 --- a/lib/views/home/widgets/floating_navigation_bar.dart +++ b/lib/views/home/widgets/floating_navigation_bar.dart @@ -1,6 +1,7 @@ import 'package:didvan/config/design_config.dart'; import 'package:didvan/config/theme_data.dart'; import 'package:didvan/constants/app_icons.dart'; +import 'package:didvan/models/message_data/news_attachment.dart'; import 'package:didvan/models/message_data/radar_attachment.dart'; import 'package:didvan/models/view/action_sheet_data.dart'; import 'package:didvan/routes/routes.dart'; @@ -102,23 +103,22 @@ class _FloatingNavigationBarState extends State { ), ), const Spacer(), - if (widget.isRadar) - BookmarkButton( - itemId: widget.item.id, - type: 'radar', - color: DesignConfig.isDark - ? Theme.of(context).colorScheme.focusedBorder - : Theme.of(context).colorScheme.focused, - askForConfirmation: widget.hasUnmarkConfirmation, - value: widget.item.marked, - onMarkChanged: (value) { - widget.onMarkChanged(value); - if (widget.hasUnmarkConfirmation && !value) { - Navigator.of(context).pop(); - } - }, - gestureSize: 32, - ), + BookmarkButton( + itemId: widget.item.id, + type: widget.isRadar ? 'radar' : 'news', + color: DesignConfig.isDark + ? Theme.of(context).colorScheme.focusedBorder + : Theme.of(context).colorScheme.focused, + askForConfirmation: widget.hasUnmarkConfirmation, + value: widget.item.marked, + onMarkChanged: (value) { + widget.onMarkChanged(value); + if (widget.hasUnmarkConfirmation && !value) { + Navigator.of(context).pop(); + } + }, + gestureSize: 32, + ), SizedBox( width: 60, child: Row( @@ -145,30 +145,12 @@ class _FloatingNavigationBarState extends State { ], ), ), - if (!widget.isRadar) const SizedBox(width: 12), - if (!widget.isRadar) - BookmarkButton( - itemId: widget.item.id, - type: 'news', - color: DesignConfig.isDark - ? Theme.of(context).colorScheme.focusedBorder - : Theme.of(context).colorScheme.focused, - askForConfirmation: widget.hasUnmarkConfirmation, - value: widget.item.marked, - onMarkChanged: (value) { - widget.onMarkChanged(value); - if (widget.hasUnmarkConfirmation && !value) { - Navigator.of(context).pop(); - } - }, - gestureSize: 32, - ), - if (widget.isRadar) - DidvanIconButton( - gestureSize: 32, - onPressed: _showMoreOptions, - icon: DidvanIcons.menu_regular, - ), + DidvanIconButton( + gestureSize: 32, + onPressed: + widget.isRadar ? _showRadarMoreOptions : _showNewsMoreOptions, + icon: DidvanIcons.menu_regular, + ), ], ), ), @@ -192,7 +174,7 @@ class _FloatingNavigationBarState extends State { }); } - void _showMoreOptions() { + void _showRadarMoreOptions() { final categories = widget.item.categories!; ActionSheetUtils.showBottomSheet( data: ActionSheetData( @@ -293,4 +275,38 @@ class _FloatingNavigationBarState extends State { ), ); } + + void _showNewsMoreOptions() { + ActionSheetUtils.showBottomSheet( + data: ActionSheetData( + content: Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + MenuOption( + title: 'گزارش اشکال', + onTap: () { + Navigator.of(context).pop(); + Navigator.of(context).pushNamed( + Routes.direct, + arguments: { + 'newsAttachment': NewsAttachment( + id: widget.item.id, + title: widget.item.title, + description: widget.item.contents.first.text, + image: widget.item.image, + createdAt: widget.item.createdAt, + ), + 'type': 'پشتیبانی' + }, + ); + }, + icon: DidvanIcons.description_regular, + ), + ], + ), + title: 'موارد بیشتر', + withoutButtonMode: true, + ), + ); + } }