Skip to content

Commit

Permalink
TW-245: add own PillBuilder for HtmlMessage
Browse files Browse the repository at this point in the history
  • Loading branch information
sherlockvn authored and hoangdat committed Jul 7, 2023
1 parent 651955f commit ece5261
Show file tree
Hide file tree
Showing 8 changed files with 124 additions and 12 deletions.
18 changes: 17 additions & 1 deletion lib/pages/chat/events/html_message.dart
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
import 'package:fluffychat/config/app_config.dart';
import 'package:fluffychat/config/setting_keys.dart';
import 'package:fluffychat/pages/chat/chat.dart';
import 'package:fluffychat/pages/image_viewer/image_viewer.dart';
import 'package:fluffychat/utils/matrix_sdk_extensions/matrix_locals.dart';
import 'package:fluffychat/utils/url_launcher.dart';
import 'package:fluffychat/widgets/pill.dart';
import 'package:flutter/material.dart';

import 'package:flutter_gen/gen_l10n/l10n.dart';
Expand All @@ -15,14 +17,18 @@ class HtmlMessage extends StatelessWidget {
final String html;
final int? maxLines;
final Room room;
final Event event;
final TextStyle? defaultTextStyle;
final TextStyle? linkStyle;
final double? emoteSize;
final Widget? bottomWidgetSpan;
final ChatController? chatController;

const HtmlMessage({
Key? key,
required this.html,
this.chatController,
required this.event,
this.maxLines,
required this.room,
this.defaultTextStyle,
Expand Down Expand Up @@ -163,6 +169,16 @@ class HtmlMessage extends StatelessWidget {
}
return {};
},
);
pillBuilder: (identifier, url, onTap, getMxcUrl) {
if (chatController == null) {
return null;
}
return Pill(
identifier: identifier,
chatController: chatController!,
url: url,
onTap: onTap,
);
});
}
}
1 change: 1 addition & 0 deletions lib/pages/chat/events/message.dart
Original file line number Diff line number Diff line change
Expand Up @@ -250,6 +250,7 @@ class Message extends StatelessWidget {
replyEvent,
ownMessage: ownMessage,
timeline: timeline,
chatController: controller,
),
),
),
Expand Down
6 changes: 4 additions & 2 deletions lib/pages/chat/events/message_content.dart
Original file line number Diff line number Diff line change
Expand Up @@ -202,6 +202,7 @@ class MessageContent extends StatelessWidget {
return Padding(
padding: const EdgeInsets.only(left: 8.0, right: 8.0),
child: HtmlMessage(
event: event,
html: html,
defaultTextStyle: Theme.of(context).textTheme.bodyLarge?.copyWith(
color: textColor,
Expand All @@ -210,6 +211,7 @@ class MessageContent extends StatelessWidget {
linkStyle: TextStyle(
color: Theme.of(context).colorScheme.secondary,
fontSize: bigEmotes ? fontSize * 3 : fontSize,
decoration: TextDecoration.underline,
decorationColor: textColor.withAlpha(150),
),
room: event.room,
Expand All @@ -219,8 +221,8 @@ class MessageContent extends StatelessWidget {
maintainSize: true,
maintainAnimation: true,
maintainState: true,
child: endOfBubbleWidget,
),
child: endOfBubbleWidget),
chatController: controller,
),
);
}
Expand Down
39 changes: 30 additions & 9 deletions lib/pages/chat/events/reply_content.dart
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import 'package:fluffychat/pages/chat/chat.dart';
import 'package:fluffychat/utils/matrix_sdk_extensions/event_extension.dart';
import 'package:flutter/material.dart';

import 'package:flutter_gen/gen_l10n/l10n.dart';
Expand All @@ -11,10 +13,12 @@ class ReplyContent extends StatelessWidget {
final Event replyEvent;
final bool ownMessage;
final Timeline? timeline;
final ChatController chatController;

const ReplyContent(
this.replyEvent, {
this.ownMessage = false,
required this.chatController,
Key? key,
this.timeline,
}) : super(key: key);
Expand Down Expand Up @@ -49,6 +53,8 @@ class ReplyContent extends StatelessWidget {
maxLines: 1,
room: displayEvent.room,
emoteSize: fontSizeDisplayContent * 1.5,
event: timeline!.events.first,
chatController: chatController,
);
} else {
replyBody = Text(
Expand All @@ -65,6 +71,7 @@ class ReplyContent extends StatelessWidget {
),
);
}
final user = displayEvent.getUser();
return Row(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Expand All @@ -81,12 +88,10 @@ class ReplyContent extends StatelessWidget {
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
FutureBuilder<User?>(
future: displayEvent.fetchSenderUser(),
builder: (context, snapshot) {
return Text(
'${snapshot.data?.calcDisplayname() ?? displayEvent.senderFromMemoryOrFallback.calcDisplayname()}:',
maxLines: 1,
if (user != null)
Text(
'${user.calcDisplayname()}:',
maxLines: 1,
overflow: TextOverflow.ellipsis,
style: TextStyle(
fontWeight: FontWeight.bold,
Expand All @@ -95,9 +100,25 @@ class ReplyContent extends StatelessWidget {
: Theme.of(context).colorScheme.primary,
fontSize: fontSizeDisplayName,
),
);
},
),
),
if (displayEvent.getUser() == null)
FutureBuilder<User?>(
future: displayEvent.fetchSenderUser(),
builder: (context, snapshot) {
return Text(
'${snapshot.data?.calcDisplayname() ?? displayEvent.senderFromMemoryOrFallback.calcDisplayname()}:',
maxLines: 1,
overflow: TextOverflow.ellipsis,
style: TextStyle(
fontWeight: FontWeight.bold,
color: ownMessage
? Theme.of(context).colorScheme.onPrimaryContainer
: Theme.of(context).colorScheme.primary,
fontSize: fontSizeDisplayName,
),
);
},
),
replyBody,
],
),
Expand Down
1 change: 1 addition & 0 deletions lib/pages/chat/reply_display.dart
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ class ReplyDisplay extends StatelessWidget {
? ReplyContent(
controller.replyEvent!,
timeline: controller.timeline!,
chatController: controller,
)
: _EditContent(
controller.editEvent?.getDisplayEvent(controller.timeline!),
Expand Down
5 changes: 5 additions & 0 deletions lib/presentation/extensions/room_extension.dart
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import 'dart:collection';

import 'package:collection/collection.dart';
import 'package:dartz/dartz.dart' hide id;
import 'package:fluffychat/di/global/get_it_initializer.dart';
import 'package:fluffychat/presentation/extensions/asset_entity_extension.dart';
Expand Down Expand Up @@ -270,4 +271,8 @@ extension SendImage on Room {
}
return txIdMapToImageFile;
}

User? getUser(mxId) {
return getParticipants().firstWhereOrNull((user) => user.id == mxId);
}
}
5 changes: 5 additions & 0 deletions lib/utils/matrix_sdk_extensions/event_extension.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import 'package:fluffychat/domain/model/extensions/string_extension.dart';
import 'package:collection/collection.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';

Expand Down Expand Up @@ -87,4 +88,8 @@ extension LocalizedBody on Event {
}
return null;
}

User? getUser() {
return room.getParticipants().firstWhereOrNull((user) => user.id == senderId);
}
}
61 changes: 61 additions & 0 deletions lib/widgets/pill.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
import 'package:fluffychat/pages/chat/chat.dart';
import 'package:fluffychat/presentation/extensions/room_extension.dart';
import 'package:fluffychat/widgets/matrix.dart';
import 'package:flutter/material.dart';
import 'package:cached_network_image/cached_network_image.dart';
import 'package:flutter_matrix_html/text_parser.dart';
import 'package:matrix/matrix.dart';

class Pill extends StatelessWidget {
final String identifier;
final String url;
final OnPillTap? onTap;
final ChatController chatController;

const Pill({
Key? key,
required this.identifier,
required this.chatController,
required this.url,
this.onTap,
}) : super(key: key);

@override
build(BuildContext context) {
final user = chatController.room?.getUser(identifier);
final displayname = user?.displayName ?? identifier;
final avatarUrl = user?.avatarUrl?.getDownloadLink(Matrix.of(context).client);
final avatarSize = DefaultTextStyle.of(context).style.fontSize ?? 14.0;
final padding = avatarSize / 20;
return InkWell(
child: Container(
padding: EdgeInsets.only(
top: padding,
bottom: padding,
left: avatarUrl != null ? padding * 3 : avatarSize / 2,
right: avatarSize / 2,
),
decoration: BoxDecoration(
color: Colors.grey[800],
borderRadius:
BorderRadius.all(Radius.circular(avatarSize + padding)),
),
child: Row(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisSize: MainAxisSize.min,
children: <Widget>[
if (avatarUrl?.toString().isNotEmpty == true)
CircleAvatar(
radius: avatarSize / 2,
backgroundImage: CachedNetworkImageProvider(avatarUrl!.toString()),
),
Text(displayname, style: TextStyle(color: Colors.white)),
],
),
),
onTap: () {
onTap?.call(url);
},
);
}
}

0 comments on commit ece5261

Please sign in to comment.