mirror of
				https://gitlab.com/famedly/fluffychat.git
				synced 2025-11-04 14:27:23 +01:00 
			
		
		
		
	Merge branch 'main' of gitlab.com:famedly/fluffychat
This commit is contained in:
		
						commit
						311a7b63dc
					
				@ -8,6 +8,8 @@
 | 
			
		||||
	</array>
 | 
			
		||||
	<key>CFBundleDevelopmentRegion</key>
 | 
			
		||||
	<string>$(DEVELOPMENT_LANGUAGE)</string>
 | 
			
		||||
	<key>CFBundleDisplayName</key>
 | 
			
		||||
	<string>FluffyChat</string>
 | 
			
		||||
	<key>CFBundleExecutable</key>
 | 
			
		||||
	<string>$(EXECUTABLE_NAME)</string>
 | 
			
		||||
	<key>CFBundleIdentifier</key>
 | 
			
		||||
@ -19,7 +21,7 @@
 | 
			
		||||
	<key>CFBundlePackageType</key>
 | 
			
		||||
	<string>APPL</string>
 | 
			
		||||
	<key>CFBundleShortVersionString</key>
 | 
			
		||||
	<string>$(MARKETING_VERSION)</string>
 | 
			
		||||
	<string>$(FLUTTER_BUILD_NAME)</string>
 | 
			
		||||
	<key>CFBundleSignature</key>
 | 
			
		||||
	<string>????</string>
 | 
			
		||||
	<key>CFBundleURLTypes</key>
 | 
			
		||||
@ -38,8 +40,6 @@
 | 
			
		||||
	</array>
 | 
			
		||||
	<key>CFBundleVersion</key>
 | 
			
		||||
	<string>$(FLUTTER_BUILD_NUMBER)</string>
 | 
			
		||||
	<key>CFBundleShortVersionString</key>
 | 
			
		||||
	<string>$(FLUTTER_BUILD_NAME)</string>
 | 
			
		||||
	<key>LSRequiresIPhoneOS</key>
 | 
			
		||||
	<true/>
 | 
			
		||||
	<key>NSAppleMusicUsageDescription</key>
 | 
			
		||||
 | 
			
		||||
@ -9,6 +9,7 @@ import 'package:flutter/material.dart';
 | 
			
		||||
import 'package:vrouter/vrouter.dart';
 | 
			
		||||
import '../../widgets/matrix.dart';
 | 
			
		||||
import 'package:flutter_gen/gen_l10n/l10n.dart';
 | 
			
		||||
import '../../utils/stream_extension.dart';
 | 
			
		||||
 | 
			
		||||
class ChatListView extends StatelessWidget {
 | 
			
		||||
  final ChatListController controller;
 | 
			
		||||
@ -161,7 +162,8 @@ class ChatListView extends StatelessWidget {
 | 
			
		||||
                            .client
 | 
			
		||||
                            .onSync
 | 
			
		||||
                            .stream
 | 
			
		||||
                            .where((s) => s.hasRoomUpdate),
 | 
			
		||||
                            .where((s) => s.hasRoomUpdate)
 | 
			
		||||
                            .rateLimit(Duration(seconds: 1)),
 | 
			
		||||
                        builder: (context, snapshot) {
 | 
			
		||||
                          return FutureBuilder<void>(
 | 
			
		||||
                            future: controller.waitForFirstSync(),
 | 
			
		||||
 | 
			
		||||
@ -27,6 +27,8 @@ import 'package:scroll_to_index/scroll_to_index.dart';
 | 
			
		||||
import 'package:swipe_to_action/swipe_to_action.dart';
 | 
			
		||||
import 'package:vrouter/vrouter.dart';
 | 
			
		||||
 | 
			
		||||
import '../../utils/stream_extension.dart';
 | 
			
		||||
 | 
			
		||||
class ChatView extends StatelessWidget {
 | 
			
		||||
  final ChatController controller;
 | 
			
		||||
 | 
			
		||||
@ -72,7 +74,8 @@ class ChatView extends StatelessWidget {
 | 
			
		||||
            titleSpacing: 0,
 | 
			
		||||
            title: controller.selectedEvents.isEmpty
 | 
			
		||||
                ? StreamBuilder(
 | 
			
		||||
                    stream: controller.room.onUpdate.stream,
 | 
			
		||||
                    stream: controller.room.onUpdate.stream
 | 
			
		||||
                        .rateLimit(Duration(milliseconds: 250)),
 | 
			
		||||
                    builder: (context, snapshot) => ListTile(
 | 
			
		||||
                          leading: Avatar(controller.room.avatar,
 | 
			
		||||
                              controller.room.displayname),
 | 
			
		||||
@ -105,7 +108,8 @@ class ChatView extends StatelessWidget {
 | 
			
		||||
                                      .stream
 | 
			
		||||
                                      .where((p) =>
 | 
			
		||||
                                          p.senderId ==
 | 
			
		||||
                                          controller.room.directChatMatrixID),
 | 
			
		||||
                                          controller.room.directChatMatrixID)
 | 
			
		||||
                                      .rateLimit(Duration(seconds: 1)),
 | 
			
		||||
                                  builder: (context, snapshot) => Text(
 | 
			
		||||
                                        controller.room
 | 
			
		||||
                                            .getLocalizedStatus(context),
 | 
			
		||||
@ -283,8 +287,10 @@ class ChatView extends StatelessWidget {
 | 
			
		||||
                                            : Container()
 | 
			
		||||
                                    : i == 0
 | 
			
		||||
                                        ? StreamBuilder(
 | 
			
		||||
                                            stream:
 | 
			
		||||
                                                controller.room.onUpdate.stream,
 | 
			
		||||
                                            stream: controller
 | 
			
		||||
                                                .room.onUpdate.stream
 | 
			
		||||
                                                .rateLimit(Duration(
 | 
			
		||||
                                                    milliseconds: 250)),
 | 
			
		||||
                                            builder: (_, __) {
 | 
			
		||||
                                              final seenByText = controller.room
 | 
			
		||||
                                                  .getLocalizedSeenByText(
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										46
									
								
								lib/utils/stream_extension.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										46
									
								
								lib/utils/stream_extension.dart
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,46 @@
 | 
			
		||||
import 'dart:async';
 | 
			
		||||
 | 
			
		||||
extension StreamExtension on Stream {
 | 
			
		||||
  /// Returns a new Stream which outputs only `true` for every update of the original
 | 
			
		||||
  /// stream, ratelimited by the Duration t
 | 
			
		||||
  Stream<bool> rateLimit(Duration t) {
 | 
			
		||||
    final controller = StreamController<bool>();
 | 
			
		||||
    Timer timer;
 | 
			
		||||
    var gotMessage = false;
 | 
			
		||||
    // as we call our inline-defined function recursively we need to make sure that the
 | 
			
		||||
    // variable exists prior of creating the function. Silly dart.
 | 
			
		||||
    Function _onMessage;
 | 
			
		||||
    // callback to determine if we should send out an update
 | 
			
		||||
    _onMessage = () {
 | 
			
		||||
      // do nothing if it is already closed
 | 
			
		||||
      if (controller.isClosed) {
 | 
			
		||||
        return;
 | 
			
		||||
      }
 | 
			
		||||
      if (timer == null) {
 | 
			
		||||
        // if we don't have a timer yet, send out the update and start a timer
 | 
			
		||||
        gotMessage = false;
 | 
			
		||||
        controller.add(true);
 | 
			
		||||
        timer = Timer(t, () {
 | 
			
		||||
          // the timer has ended...delete it and, if we got a message, re-run the
 | 
			
		||||
          // method to send out an update!
 | 
			
		||||
          timer = null;
 | 
			
		||||
          if (gotMessage) {
 | 
			
		||||
            _onMessage();
 | 
			
		||||
          }
 | 
			
		||||
        });
 | 
			
		||||
      } else {
 | 
			
		||||
        // set that we got a message
 | 
			
		||||
        gotMessage = true;
 | 
			
		||||
      }
 | 
			
		||||
    };
 | 
			
		||||
    final subscription = listen((_) => _onMessage(),
 | 
			
		||||
        onDone: () => controller.close(),
 | 
			
		||||
        onError: (e, s) => controller.addError(e, s));
 | 
			
		||||
    // add proper cleanup to the subscription and the controller, to not memory leak
 | 
			
		||||
    controller.onCancel = () {
 | 
			
		||||
      subscription.cancel();
 | 
			
		||||
      controller.close();
 | 
			
		||||
    };
 | 
			
		||||
    return controller.stream;
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
@ -289,7 +289,9 @@ class ChatListItem extends StatelessWidget {
 | 
			
		||||
                curve: Curves.bounceInOut,
 | 
			
		||||
                padding: EdgeInsets.symmetric(horizontal: 7),
 | 
			
		||||
                height: unreadBubbleSize,
 | 
			
		||||
                width: room.notificationCount == 0 && !room.isUnread ? 0 : null,
 | 
			
		||||
                width: room.notificationCount == 0 && !room.isUnread
 | 
			
		||||
                    ? 0
 | 
			
		||||
                    : unreadBubbleSize,
 | 
			
		||||
                decoration: BoxDecoration(
 | 
			
		||||
                  color: room.highlightCount > 0
 | 
			
		||||
                      ? Colors.red
 | 
			
		||||
 | 
			
		||||
@ -56,7 +56,7 @@
 | 
			
		||||
		2D20EFA3D49BBBDA1F07645D /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = "<group>"; };
 | 
			
		||||
		333000ED22D3DE5D00554162 /* Warnings.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = Warnings.xcconfig; sourceTree = "<group>"; };
 | 
			
		||||
		335BBD1A22A9A15E00E9071D /* GeneratedPluginRegistrant.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = GeneratedPluginRegistrant.swift; sourceTree = "<group>"; };
 | 
			
		||||
		33CC10ED2044A3C60003C045 /* fluffychat.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = fluffychat.app; sourceTree = BUILT_PRODUCTS_DIR; };
 | 
			
		||||
		33CC10ED2044A3C60003C045 /* FluffyChat.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = FluffyChat.app; sourceTree = BUILT_PRODUCTS_DIR; };
 | 
			
		||||
		33CC10F02044A3C60003C045 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
 | 
			
		||||
		33CC10F22044A3C60003C045 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; name = Assets.xcassets; path = Runner/Assets.xcassets; sourceTree = "<group>"; };
 | 
			
		||||
		33CC10F52044A3C60003C045 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/MainMenu.xib; sourceTree = "<group>"; };
 | 
			
		||||
@ -112,7 +112,7 @@
 | 
			
		||||
		33CC10EE2044A3C60003C045 /* Products */ = {
 | 
			
		||||
			isa = PBXGroup;
 | 
			
		||||
			children = (
 | 
			
		||||
				33CC10ED2044A3C60003C045 /* fluffychat.app */,
 | 
			
		||||
				33CC10ED2044A3C60003C045 /* FluffyChat.app */,
 | 
			
		||||
			);
 | 
			
		||||
			name = Products;
 | 
			
		||||
			sourceTree = "<group>";
 | 
			
		||||
@ -192,7 +192,7 @@
 | 
			
		||||
			);
 | 
			
		||||
			name = Runner;
 | 
			
		||||
			productName = Runner;
 | 
			
		||||
			productReference = 33CC10ED2044A3C60003C045 /* fluffychat.app */;
 | 
			
		||||
			productReference = 33CC10ED2044A3C60003C045 /* FluffyChat.app */;
 | 
			
		||||
			productType = "com.apple.product-type.application";
 | 
			
		||||
		};
 | 
			
		||||
/* End PBXNativeTarget section */
 | 
			
		||||
@ -461,6 +461,7 @@
 | 
			
		||||
					"$(inherited)",
 | 
			
		||||
					"@executable_path/../Frameworks",
 | 
			
		||||
				);
 | 
			
		||||
				PRODUCT_NAME = FluffyChat;
 | 
			
		||||
				PROVISIONING_PROFILE_SPECIFIER = "";
 | 
			
		||||
				SWIFT_VERSION = 5.0;
 | 
			
		||||
			};
 | 
			
		||||
@ -592,6 +593,7 @@
 | 
			
		||||
					"$(inherited)",
 | 
			
		||||
					"@executable_path/../Frameworks",
 | 
			
		||||
				);
 | 
			
		||||
				PRODUCT_NAME = FluffyChat;
 | 
			
		||||
				PROVISIONING_PROFILE_SPECIFIER = "";
 | 
			
		||||
				SWIFT_OPTIMIZATION_LEVEL = "-Onone";
 | 
			
		||||
				SWIFT_VERSION = 5.0;
 | 
			
		||||
@ -617,6 +619,7 @@
 | 
			
		||||
					"$(inherited)",
 | 
			
		||||
					"@executable_path/../Frameworks",
 | 
			
		||||
				);
 | 
			
		||||
				PRODUCT_NAME = FluffyChat;
 | 
			
		||||
				PROVISIONING_PROFILE_SPECIFIER = "";
 | 
			
		||||
				SWIFT_VERSION = 5.0;
 | 
			
		||||
			};
 | 
			
		||||
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user