From 6316dda9391b195c4aa8b62ca2824470c6402751 Mon Sep 17 00:00:00 2001 From: OfficialDakari Date: Tue, 17 Jun 2025 15:10:15 +0500 Subject: [PATCH] boiler plate for polls feat: replying with stickers --- lib/pages/chat/chat_emoji_picker.dart | 6 +++ lib/pages/chat/events/message.dart | 5 ++- lib/pages/chat/events/message_content.dart | 5 +++ lib/pages/chat/events/poll_content.dart | 38 +++++++++++++++++ lib/utils/client_manager.dart | 14 ++++++- .../filtered_timeline_extension.dart | 3 +- lib/utils/poll_events.dart | 5 +++ snap/snapcraft.yaml | 42 ++----------------- 8 files changed, 77 insertions(+), 41 deletions(-) create mode 100644 lib/pages/chat/events/poll_content.dart create mode 100644 lib/utils/poll_events.dart diff --git a/lib/pages/chat/chat_emoji_picker.dart b/lib/pages/chat/chat_emoji_picker.dart index 7d21fab..986c1c7 100644 --- a/lib/pages/chat/chat_emoji_picker.dart +++ b/lib/pages/chat/chat_emoji_picker.dart @@ -75,9 +75,15 @@ class ChatEmojiPicker extends StatelessWidget { 'body': sticker.body, 'info': sticker.info ?? {}, 'url': sticker.url.toString(), + 'm.relates_to': controller.replyEvent != null ? { + 'm.in_reply_to': { + 'event_id': controller.replyEvent!.eventId + } + } : null }, type: EventTypes.Sticker, ); + controller.cancelReplyEventAction(); controller.hideEmojiPicker(); }, ), diff --git a/lib/pages/chat/events/message.dart b/lib/pages/chat/events/message.dart index ed3f6c3..a524871 100644 --- a/lib/pages/chat/events/message.dart +++ b/lib/pages/chat/events/message.dart @@ -1,5 +1,6 @@ import 'dart:ui' as ui; +import 'package:fluffychat/utils/poll_events.dart'; import 'package:flutter/material.dart'; import 'package:flutter/services.dart'; @@ -66,12 +67,12 @@ class Message extends StatelessWidget { @override Widget build(BuildContext context) { final theme = Theme.of(context); - if (!{ EventTypes.Message, EventTypes.Sticker, EventTypes.Encrypted, EventTypes.CallInvite, + PollEvents.PollStart, }.contains(event.type)) { if (event.type.startsWith('m.call.')) { return const SizedBox.shrink(); @@ -100,6 +101,7 @@ class Message extends StatelessWidget { EventTypes.Message, EventTypes.Sticker, EventTypes.Encrypted, + PollEvents.PollStart, }.contains(nextEvent!.type) && nextEvent!.senderId == event.senderId && !displayTime; @@ -109,6 +111,7 @@ class Message extends StatelessWidget { EventTypes.Message, EventTypes.Sticker, EventTypes.Encrypted, + PollEvents.PollStart, }.contains(previousEvent!.type) && previousEvent!.senderId == event.senderId && previousEvent!.originServerTs.sameEnvironment(event.originServerTs); diff --git a/lib/pages/chat/events/message_content.dart b/lib/pages/chat/events/message_content.dart index 7ec7bac..020e854 100644 --- a/lib/pages/chat/events/message_content.dart +++ b/lib/pages/chat/events/message_content.dart @@ -1,5 +1,7 @@ import 'dart:math'; +import 'package:fluffychat/pages/chat/events/poll_content.dart'; +import 'package:fluffychat/utils/poll_events.dart'; import 'package:flutter/material.dart'; import 'package:fluffychat/generated/l10n/l10n.dart'; @@ -106,6 +108,9 @@ class MessageContent extends StatelessWidget { final fontSize = AppConfig.messageFontSize * AppConfig.fontSizeFactor; final buttonTextColor = textColor; switch (event.type) { + case PollEvents.PollStart: + Logs().v("Got poll event ${event.type}"); + return PollWidget(event, color: textColor, linkColor: linkColor, fontSize: fontSize); case EventTypes.Message: case EventTypes.Encrypted: case EventTypes.Sticker: diff --git a/lib/pages/chat/events/poll_content.dart b/lib/pages/chat/events/poll_content.dart new file mode 100644 index 0000000..ccbc216 --- /dev/null +++ b/lib/pages/chat/events/poll_content.dart @@ -0,0 +1,38 @@ +import 'package:fluffychat/utils/poll_events.dart'; +import 'package:flutter/material.dart'; +import 'package:flutter/widgets.dart'; +import 'package:matrix/matrix.dart'; + +class PollWidget extends StatefulWidget { + final Color color; + final Color linkColor; + final double fontSize; + final Event event; + + const PollWidget( + this.event, { + required this.color, + required this.linkColor, + required this.fontSize, + super.key, + }); + + @override + State createState() => PollWidgetState(); +} + +class PollWidgetState extends State { + @override + Widget build(BuildContext context) { + final event = widget.event; + final content = event.content[PollEvents.PollStart] as Map; + return Padding( + padding: EdgeInsetsGeometry.all(16), + child: Column( + children: [ + Text(content?['question']['m.text'] as String, style: TextStyle(fontWeight: FontWeight.bold)) + ], + ), + ); + } +} \ No newline at end of file diff --git a/lib/utils/client_manager.dart b/lib/utils/client_manager.dart index 1c1af43..51e37f8 100644 --- a/lib/utils/client_manager.dart +++ b/lib/utils/client_manager.dart @@ -1,6 +1,7 @@ import 'dart:io'; import 'package:fluffychat/generated/l10n/l10n.dart'; +import 'package:fluffychat/utils/poll_events.dart'; import 'package:flutter/foundation.dart'; import 'package:collection/collection.dart'; @@ -124,6 +125,17 @@ abstract class ClientManager { // To make room emotes work 'im.ponies.room_emotes', }, + roomPreviewLastEvents: { + EventTypes.Message, + EventTypes.Encrypted, + EventTypes.Sticker, + EventTypes.CallInvite, + EventTypes.CallAnswer, + EventTypes.CallReject, + EventTypes.CallHangup, + EventTypes.GroupCallMember, + PollEvents.PollStart, + }, logLevel: kReleaseMode ? Level.warning : Level.verbose, database: await flutterMatrixSdkDatabaseBuilder(clientName), supportedLoginTypes: { @@ -187,4 +199,4 @@ abstract class ClientManager { ), ); } -} \ No newline at end of file +} diff --git a/lib/utils/matrix_sdk_extensions/filtered_timeline_extension.dart b/lib/utils/matrix_sdk_extensions/filtered_timeline_extension.dart index 76655a6..44b627f 100644 --- a/lib/utils/matrix_sdk_extensions/filtered_timeline_extension.dart +++ b/lib/utils/matrix_sdk_extensions/filtered_timeline_extension.dart @@ -1,3 +1,4 @@ +import 'package:fluffychat/utils/poll_events.dart'; import 'package:matrix/matrix.dart'; import '../../config/app_config.dart'; @@ -45,7 +46,7 @@ extension IsStateExtension on Event { // if we enabled to hide all redacted events, don't show those (!AppConfig.hideRedactedEvents || !redacted) && // if we enabled to hide all unknown events, don't show those - (!AppConfig.hideUnknownEvents || isEventTypeKnown) && + (!AppConfig.hideUnknownEvents || isEventTypeKnown || type == PollEvents.PollStart) && // remove state events that we don't want to render (isState || !AppConfig.hideAllStateEvents) && // hide simple join/leave member events in public rooms diff --git a/lib/utils/poll_events.dart b/lib/utils/poll_events.dart new file mode 100644 index 0000000..8a35664 --- /dev/null +++ b/lib/utils/poll_events.dart @@ -0,0 +1,5 @@ +class PollEvents { + static const String PollStart = 'org.matrix.msc3381.poll.start'; + static const String TypeDisclosed = 'org.matrix.msc3381.poll.disclosed'; + static const String TypeUndisclosed = 'org.matrix.msc3381.poll.undisclosed'; +} \ No newline at end of file diff --git a/snap/snapcraft.yaml b/snap/snapcraft.yaml index 0e5a32f..b5c1f8a 100644 --- a/snap/snapcraft.yaml +++ b/snap/snapcraft.yaml @@ -1,45 +1,11 @@ -name: fluffychat -title: FluffyChat +name: extera-next +title: Extera Next base: core24 version: git license: AGPL-3.0 -summary: The cutest messenger in the Matrix network +summary: A fork of cutest messenger in the Matrix network description: | - FluffyChat is an open source, nonprofit and cute matrix messenger app. The app is easy to use but secure and decentralized. - - - ## Features - - - Send all kinds of messages, images and files - - Voice messages - - Location sharing - - Push notifications - - Unlimited private and public group chats - - Public channels with thousands of participants - - Feature rich group moderation including all matrix features - - Discover and join public groups - - Dark mode - - Hides complexity of Matrix IDs behind simple QR codes - - Custom emotes and stickers - - Video calls via sharing links to Jitsi - - Spaces - - Compatible with Element, Nheko, NeoChat and all other Matrix apps - - End to end encryption - - Emoji verification & cross signing - - And much more... - - - ## FluffyChat comes with a dream - - Imagine a world where everyone can choose the messenger they like and is still able to chat with all of their friends. - - A world where there are no companies spying on you when you send selfies to friends and lovers. - - And a world where apps are made for fluffyness and not for profit. ♥ - - Join the community: https://matrix.to/#/#fluffychat:matrix.org - Website: http://fluffychat.im - Microblog: https://mastodon.art/@krille + Extera Next is fork of FluffyChat with some additions grade: stable confinement: strict