From 7dfd3b1d87d7b0af8e9781bb6d4c4e2e28b4a79c Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Fri, 26 Sep 2025 01:30:15 +0400 Subject: [PATCH] Various improvements --- .../Sources/PresentationCallManager.swift | 3 + .../Sources/ChatListContainerItemNode.swift | 2 +- submodules/TelegramApi/Sources/Api0.swift | 4 +- submodules/TelegramApi/Sources/Api27.swift | 22 +++-- submodules/TelegramApi/Sources/Api39.swift | 14 +-- submodules/TelegramApi/Sources/Api7.swift | 54 ++++++----- .../Sources/AccountGroupCallContextImpl.swift | 1 + .../Components/MessageItemComponent.swift | 2 +- .../Sources/PresentationGroupCall.swift | 7 +- .../Sources/VideoChatScreen.swift | 1 + .../Account/AccountIntermediateState.swift | 6 +- .../TelegramCore/Sources/ForumChannels.swift | 5 +- .../State/AccountStateManagementUtils.swift | 17 ++-- .../TelegramEngine/Calls/GroupCalls.swift | 90 ++++++++++++++----- .../Peers/ChannelAdminEventLogs.swift | 12 +-- .../EdgeEffect/Sources/EdgeEffect.swift | 13 ++- .../Sources/UserApperanceScreen.swift | 2 +- 17 files changed, 167 insertions(+), 88 deletions(-) diff --git a/submodules/AccountContext/Sources/PresentationCallManager.swift b/submodules/AccountContext/Sources/PresentationCallManager.swift index 6ca0cb1725..45c8775d18 100644 --- a/submodules/AccountContext/Sources/PresentationCallManager.swift +++ b/submodules/AccountContext/Sources/PresentationCallManager.swift @@ -222,6 +222,7 @@ public struct PresentationGroupCallState: Equatable { public var adminIds: Set public var muteState: GroupCallParticipantsContext.Participant.MuteState? public var defaultParticipantMuteState: DefaultParticipantMuteState? + public var messagesAreEnabled: Bool public var recordingStartTimestamp: Int32? public var title: String? public var raisedHand: Bool @@ -238,6 +239,7 @@ public struct PresentationGroupCallState: Equatable { adminIds: Set, muteState: GroupCallParticipantsContext.Participant.MuteState?, defaultParticipantMuteState: DefaultParticipantMuteState?, + messagesAreEnabled: Bool, recordingStartTimestamp: Int32?, title: String?, raisedHand: Bool, @@ -253,6 +255,7 @@ public struct PresentationGroupCallState: Equatable { self.adminIds = adminIds self.muteState = muteState self.defaultParticipantMuteState = defaultParticipantMuteState + self.messagesAreEnabled = messagesAreEnabled self.recordingStartTimestamp = recordingStartTimestamp self.title = title self.raisedHand = raisedHand diff --git a/submodules/ChatListUI/Sources/ChatListContainerItemNode.swift b/submodules/ChatListUI/Sources/ChatListContainerItemNode.swift index 360c326f12..68fdcfd80e 100644 --- a/submodules/ChatListUI/Sources/ChatListContainerItemNode.swift +++ b/submodules/ChatListUI/Sources/ChatListContainerItemNode.swift @@ -453,7 +453,7 @@ final class ChatListContainerItemNode: ASDisplayNode { let edgeEffectHeight: CGFloat = insets.bottom let edgeEffectFrame = CGRect(origin: CGPoint(x: 0.0, y: size.height - edgeEffectHeight), size: CGSize(width: size.width, height: edgeEffectHeight)) transition.updateFrame(view: self.edgeEffectView, frame: edgeEffectFrame) - self.edgeEffectView.update(content: self.presentationData.theme.list.plainBackgroundColor, isInverted: false, rect: edgeEffectFrame, edge: .bottom, edgeSize: edgeEffectFrame.height, containerSize: size, transition: ComponentTransition(transition)) + self.edgeEffectView.update(content: self.presentationData.theme.list.plainBackgroundColor, rect: edgeEffectFrame, edge: .bottom, edgeSize: edgeEffectFrame.height, transition: ComponentTransition(transition)) } func updateScrollingOffset(navigationHeight: CGFloat, offset: CGFloat, transition: ContainedViewLayoutTransition) { diff --git a/submodules/TelegramApi/Sources/Api0.swift b/submodules/TelegramApi/Sources/Api0.swift index d6844b53ad..f646f57908 100644 --- a/submodules/TelegramApi/Sources/Api0.swift +++ b/submodules/TelegramApi/Sources/Api0.swift @@ -293,7 +293,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = { dict[-207944868] = { return Api.FileHash.parse_fileHash($0) } dict[-11252123] = { return Api.Folder.parse_folder($0) } dict[-373643672] = { return Api.FolderPeer.parse_folderPeer($0) } - dict[1903173033] = { return Api.ForumTopic.parse_forumTopic($0) } + dict[-838922550] = { return Api.ForumTopic.parse_forumTopic($0) } dict[37687451] = { return Api.ForumTopic.parse_forumTopicDeleted($0) } dict[-394605632] = { return Api.FoundStory.parse_foundStory($0) } dict[-1107729093] = { return Api.Game.parse_game($0) } @@ -1111,7 +1111,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = { dict[-1535694705] = { return Api.Update.parse_updateGroupCallChainBlocks($0) } dict[192428418] = { return Api.Update.parse_updateGroupCallConnection($0) } dict[-917002394] = { return Api.Update.parse_updateGroupCallEncryptedMessage($0) } - dict[-1761933248] = { return Api.Update.parse_updateGroupCallMessage($0) } + dict[2026050784] = { return Api.Update.parse_updateGroupCallMessage($0) } dict[-219423922] = { return Api.Update.parse_updateGroupCallParticipants($0) } dict[1763610706] = { return Api.Update.parse_updateInlineBotCallbackQuery($0) } dict[1442983757] = { return Api.Update.parse_updateLangPack($0) } diff --git a/submodules/TelegramApi/Sources/Api27.swift b/submodules/TelegramApi/Sources/Api27.swift index d0d6ab7e37..5052ea908c 100644 --- a/submodules/TelegramApi/Sources/Api27.swift +++ b/submodules/TelegramApi/Sources/Api27.swift @@ -608,7 +608,7 @@ public extension Api { case updateGroupCallChainBlocks(call: Api.InputGroupCall, subChainId: Int32, blocks: [Buffer], nextOffset: Int32) case updateGroupCallConnection(flags: Int32, params: Api.DataJSON) case updateGroupCallEncryptedMessage(call: Api.InputGroupCall, fromId: Api.Peer, encryptedMessage: Buffer) - case updateGroupCallMessage(call: Api.InputGroupCall, fromId: Api.Peer, message: Api.TextWithEntities) + case updateGroupCallMessage(call: Api.InputGroupCall, fromId: Api.Peer, randomId: Int64, message: Api.TextWithEntities) case updateGroupCallParticipants(call: Api.InputGroupCall, participants: [Api.GroupCallParticipant], version: Int32) case updateInlineBotCallbackQuery(flags: Int32, queryId: Int64, userId: Int64, msgId: Api.InputBotInlineMessageID, chatInstance: Int64, data: Buffer?, gameShortName: String?) case updateLangPack(difference: Api.LangPackDifference) @@ -1307,12 +1307,13 @@ public extension Api { fromId.serialize(buffer, true) serializeBytes(encryptedMessage, buffer: buffer, boxed: false) break - case .updateGroupCallMessage(let call, let fromId, let message): + case .updateGroupCallMessage(let call, let fromId, let randomId, let message): if boxed { - buffer.appendInt32(-1761933248) + buffer.appendInt32(2026050784) } call.serialize(buffer, true) fromId.serialize(buffer, true) + serializeInt64(randomId, buffer: buffer, boxed: false) message.serialize(buffer, true) break case .updateGroupCallParticipants(let call, let participants, let version): @@ -2117,8 +2118,8 @@ public extension Api { return ("updateGroupCallConnection", [("flags", flags as Any), ("params", params as Any)]) case .updateGroupCallEncryptedMessage(let call, let fromId, let encryptedMessage): return ("updateGroupCallEncryptedMessage", [("call", call as Any), ("fromId", fromId as Any), ("encryptedMessage", encryptedMessage as Any)]) - case .updateGroupCallMessage(let call, let fromId, let message): - return ("updateGroupCallMessage", [("call", call as Any), ("fromId", fromId as Any), ("message", message as Any)]) + case .updateGroupCallMessage(let call, let fromId, let randomId, let message): + return ("updateGroupCallMessage", [("call", call as Any), ("fromId", fromId as Any), ("randomId", randomId as Any), ("message", message as Any)]) case .updateGroupCallParticipants(let call, let participants, let version): return ("updateGroupCallParticipants", [("call", call as Any), ("participants", participants as Any), ("version", version as Any)]) case .updateInlineBotCallbackQuery(let flags, let queryId, let userId, let msgId, let chatInstance, let data, let gameShortName): @@ -3598,15 +3599,18 @@ public extension Api { if let signature = reader.readInt32() { _2 = Api.parse(reader, signature: signature) as? Api.Peer } - var _3: Api.TextWithEntities? + var _3: Int64? + _3 = reader.readInt64() + var _4: Api.TextWithEntities? if let signature = reader.readInt32() { - _3 = Api.parse(reader, signature: signature) as? Api.TextWithEntities + _4 = Api.parse(reader, signature: signature) as? Api.TextWithEntities } let _c1 = _1 != nil let _c2 = _2 != nil let _c3 = _3 != nil - if _c1 && _c2 && _c3 { - return Api.Update.updateGroupCallMessage(call: _1!, fromId: _2!, message: _3!) + let _c4 = _4 != nil + if _c1 && _c2 && _c3 && _c4 { + return Api.Update.updateGroupCallMessage(call: _1!, fromId: _2!, randomId: _3!, message: _4!) } else { return nil diff --git a/submodules/TelegramApi/Sources/Api39.swift b/submodules/TelegramApi/Sources/Api39.swift index f11e53fd5d..7fd583eee2 100644 --- a/submodules/TelegramApi/Sources/Api39.swift +++ b/submodules/TelegramApi/Sources/Api39.swift @@ -10829,12 +10829,13 @@ public extension Api.functions.phone { } } public extension Api.functions.phone { - static func sendGroupCallMessage(call: Api.InputGroupCall, message: Api.TextWithEntities) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) { + static func sendGroupCallMessage(call: Api.InputGroupCall, randomId: Int64, message: Api.TextWithEntities) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) { let buffer = Buffer() - buffer.appendInt32(-614432696) + buffer.appendInt32(-2021052396) call.serialize(buffer, true) + serializeInt64(randomId, buffer: buffer, boxed: false) message.serialize(buffer, true) - return (FunctionDescription(name: "phone.sendGroupCallMessage", parameters: [("call", String(describing: call)), ("message", String(describing: message))]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Bool? in + return (FunctionDescription(name: "phone.sendGroupCallMessage", parameters: [("call", String(describing: call)), ("randomId", String(describing: randomId)), ("message", String(describing: message))]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Bool? in let reader = BufferReader(buffer) var result: Api.Bool? if let signature = reader.readInt32() { @@ -10912,13 +10913,14 @@ public extension Api.functions.phone { } } public extension Api.functions.phone { - static func toggleGroupCallSettings(flags: Int32, call: Api.InputGroupCall, joinMuted: Api.Bool?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) { + static func toggleGroupCallSettings(flags: Int32, call: Api.InputGroupCall, joinMuted: Api.Bool?, messagesEnabled: Api.Bool?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) { let buffer = Buffer() - buffer.appendInt32(1958458429) + buffer.appendInt32(-378390524) serializeInt32(flags, buffer: buffer, boxed: false) call.serialize(buffer, true) if Int(flags) & Int(1 << 0) != 0 {joinMuted!.serialize(buffer, true)} - return (FunctionDescription(name: "phone.toggleGroupCallSettings", parameters: [("flags", String(describing: flags)), ("call", String(describing: call)), ("joinMuted", String(describing: joinMuted))]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Updates? in + if Int(flags) & Int(1 << 2) != 0 {messagesEnabled!.serialize(buffer, true)} + return (FunctionDescription(name: "phone.toggleGroupCallSettings", parameters: [("flags", String(describing: flags)), ("call", String(describing: call)), ("joinMuted", String(describing: joinMuted)), ("messagesEnabled", String(describing: messagesEnabled))]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Updates? in let reader = BufferReader(buffer) var result: Api.Updates? if let signature = reader.readInt32() { diff --git a/submodules/TelegramApi/Sources/Api7.swift b/submodules/TelegramApi/Sources/Api7.swift index 97dd79ac02..4b7df359d9 100644 --- a/submodules/TelegramApi/Sources/Api7.swift +++ b/submodules/TelegramApi/Sources/Api7.swift @@ -824,18 +824,19 @@ public extension Api { } public extension Api { indirect enum ForumTopic: TypeConstructorDescription { - case forumTopic(flags: Int32, id: Int32, date: Int32, title: String, iconColor: Int32, iconEmojiId: Int64?, topMessage: Int32, readInboxMaxId: Int32, readOutboxMaxId: Int32, unreadCount: Int32, unreadMentionsCount: Int32, unreadReactionsCount: Int32, fromId: Api.Peer, notifySettings: Api.PeerNotifySettings, draft: Api.DraftMessage?) + case forumTopic(flags: Int32, id: Int32, date: Int32, peer: Api.Peer, title: String, iconColor: Int32, iconEmojiId: Int64?, topMessage: Int32, readInboxMaxId: Int32, readOutboxMaxId: Int32, unreadCount: Int32, unreadMentionsCount: Int32, unreadReactionsCount: Int32, fromId: Api.Peer, notifySettings: Api.PeerNotifySettings, draft: Api.DraftMessage?) case forumTopicDeleted(id: Int32) public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { switch self { - case .forumTopic(let flags, let id, let date, let title, let iconColor, let iconEmojiId, let topMessage, let readInboxMaxId, let readOutboxMaxId, let unreadCount, let unreadMentionsCount, let unreadReactionsCount, let fromId, let notifySettings, let draft): + case .forumTopic(let flags, let id, let date, let peer, let title, let iconColor, let iconEmojiId, let topMessage, let readInboxMaxId, let readOutboxMaxId, let unreadCount, let unreadMentionsCount, let unreadReactionsCount, let fromId, let notifySettings, let draft): if boxed { - buffer.appendInt32(1903173033) + buffer.appendInt32(-838922550) } serializeInt32(flags, buffer: buffer, boxed: false) serializeInt32(id, buffer: buffer, boxed: false) serializeInt32(date, buffer: buffer, boxed: false) + peer.serialize(buffer, true) serializeString(title, buffer: buffer, boxed: false) serializeInt32(iconColor, buffer: buffer, boxed: false) if Int(flags) & Int(1 << 0) != 0 {serializeInt64(iconEmojiId!, buffer: buffer, boxed: false)} @@ -860,8 +861,8 @@ public extension Api { public func descriptionFields() -> (String, [(String, Any)]) { switch self { - case .forumTopic(let flags, let id, let date, let title, let iconColor, let iconEmojiId, let topMessage, let readInboxMaxId, let readOutboxMaxId, let unreadCount, let unreadMentionsCount, let unreadReactionsCount, let fromId, let notifySettings, let draft): - return ("forumTopic", [("flags", flags as Any), ("id", id as Any), ("date", date as Any), ("title", title as Any), ("iconColor", iconColor as Any), ("iconEmojiId", iconEmojiId as Any), ("topMessage", topMessage as Any), ("readInboxMaxId", readInboxMaxId as Any), ("readOutboxMaxId", readOutboxMaxId as Any), ("unreadCount", unreadCount as Any), ("unreadMentionsCount", unreadMentionsCount as Any), ("unreadReactionsCount", unreadReactionsCount as Any), ("fromId", fromId as Any), ("notifySettings", notifySettings as Any), ("draft", draft as Any)]) + case .forumTopic(let flags, let id, let date, let peer, let title, let iconColor, let iconEmojiId, let topMessage, let readInboxMaxId, let readOutboxMaxId, let unreadCount, let unreadMentionsCount, let unreadReactionsCount, let fromId, let notifySettings, let draft): + return ("forumTopic", [("flags", flags as Any), ("id", id as Any), ("date", date as Any), ("peer", peer as Any), ("title", title as Any), ("iconColor", iconColor as Any), ("iconEmojiId", iconEmojiId as Any), ("topMessage", topMessage as Any), ("readInboxMaxId", readInboxMaxId as Any), ("readOutboxMaxId", readOutboxMaxId as Any), ("unreadCount", unreadCount as Any), ("unreadMentionsCount", unreadMentionsCount as Any), ("unreadReactionsCount", unreadReactionsCount as Any), ("fromId", fromId as Any), ("notifySettings", notifySettings as Any), ("draft", draft as Any)]) case .forumTopicDeleted(let id): return ("forumTopicDeleted", [("id", id as Any)]) } @@ -874,14 +875,16 @@ public extension Api { _2 = reader.readInt32() var _3: Int32? _3 = reader.readInt32() - var _4: String? - _4 = parseString(reader) - var _5: Int32? - _5 = reader.readInt32() - var _6: Int64? - if Int(_1!) & Int(1 << 0) != 0 {_6 = reader.readInt64() } - var _7: Int32? - _7 = reader.readInt32() + var _4: Api.Peer? + if let signature = reader.readInt32() { + _4 = Api.parse(reader, signature: signature) as? Api.Peer + } + var _5: String? + _5 = parseString(reader) + var _6: Int32? + _6 = reader.readInt32() + var _7: Int64? + if Int(_1!) & Int(1 << 0) != 0 {_7 = reader.readInt64() } var _8: Int32? _8 = reader.readInt32() var _9: Int32? @@ -892,25 +895,27 @@ public extension Api { _11 = reader.readInt32() var _12: Int32? _12 = reader.readInt32() - var _13: Api.Peer? + var _13: Int32? + _13 = reader.readInt32() + var _14: Api.Peer? if let signature = reader.readInt32() { - _13 = Api.parse(reader, signature: signature) as? Api.Peer + _14 = Api.parse(reader, signature: signature) as? Api.Peer } - var _14: Api.PeerNotifySettings? + var _15: Api.PeerNotifySettings? if let signature = reader.readInt32() { - _14 = Api.parse(reader, signature: signature) as? Api.PeerNotifySettings + _15 = Api.parse(reader, signature: signature) as? Api.PeerNotifySettings } - var _15: Api.DraftMessage? + var _16: Api.DraftMessage? if Int(_1!) & Int(1 << 4) != 0 {if let signature = reader.readInt32() { - _15 = Api.parse(reader, signature: signature) as? Api.DraftMessage + _16 = Api.parse(reader, signature: signature) as? Api.DraftMessage } } let _c1 = _1 != nil let _c2 = _2 != nil let _c3 = _3 != nil let _c4 = _4 != nil let _c5 = _5 != nil - let _c6 = (Int(_1!) & Int(1 << 0) == 0) || _6 != nil - let _c7 = _7 != nil + let _c6 = _6 != nil + let _c7 = (Int(_1!) & Int(1 << 0) == 0) || _7 != nil let _c8 = _8 != nil let _c9 = _9 != nil let _c10 = _10 != nil @@ -918,9 +923,10 @@ public extension Api { let _c12 = _12 != nil let _c13 = _13 != nil let _c14 = _14 != nil - let _c15 = (Int(_1!) & Int(1 << 4) == 0) || _15 != nil - if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 && _c8 && _c9 && _c10 && _c11 && _c12 && _c13 && _c14 && _c15 { - return Api.ForumTopic.forumTopic(flags: _1!, id: _2!, date: _3!, title: _4!, iconColor: _5!, iconEmojiId: _6, topMessage: _7!, readInboxMaxId: _8!, readOutboxMaxId: _9!, unreadCount: _10!, unreadMentionsCount: _11!, unreadReactionsCount: _12!, fromId: _13!, notifySettings: _14!, draft: _15) + let _c15 = _15 != nil + let _c16 = (Int(_1!) & Int(1 << 4) == 0) || _16 != nil + if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 && _c8 && _c9 && _c10 && _c11 && _c12 && _c13 && _c14 && _c15 && _c16 { + return Api.ForumTopic.forumTopic(flags: _1!, id: _2!, date: _3!, peer: _4!, title: _5!, iconColor: _6!, iconEmojiId: _7, topMessage: _8!, readInboxMaxId: _9!, readOutboxMaxId: _10!, unreadCount: _11!, unreadMentionsCount: _12!, unreadReactionsCount: _13!, fromId: _14!, notifySettings: _15!, draft: _16) } else { return nil diff --git a/submodules/TelegramCallsUI/Sources/AccountGroupCallContextImpl.swift b/submodules/TelegramCallsUI/Sources/AccountGroupCallContextImpl.swift index e8187e7734..bbf2e28b75 100644 --- a/submodules/TelegramCallsUI/Sources/AccountGroupCallContextImpl.swift +++ b/submodules/TelegramCallsUI/Sources/AccountGroupCallContextImpl.swift @@ -96,6 +96,7 @@ public final class AccountGroupCallContextImpl: AccountGroupCallContext { recordingStartTimestamp: nil, sortAscending: state.sortAscending, defaultParticipantsAreMuted: state.defaultParticipantsAreMuted, + messagesAreEnabled: state.messagesAreEnabled, isVideoEnabled: state.isVideoEnabled, unmutedVideoLimit: state.unmutedVideoLimit, isStream: state.isStream, diff --git a/submodules/TelegramCallsUI/Sources/Components/MessageItemComponent.swift b/submodules/TelegramCallsUI/Sources/Components/MessageItemComponent.swift index e10ce0ab56..b2a54f4493 100644 --- a/submodules/TelegramCallsUI/Sources/Components/MessageItemComponent.swift +++ b/submodules/TelegramCallsUI/Sources/Components/MessageItemComponent.swift @@ -72,7 +72,7 @@ final class MessageItemComponent: Component { self.background = GlassBackgroundView() - self.avatarNode = AvatarNode(font: avatarPlaceholderFont(size: 10.0)) + self.avatarNode = AvatarNode(font: avatarPlaceholderFont(size: 12.0)) self.text = ComponentView() diff --git a/submodules/TelegramCallsUI/Sources/PresentationGroupCall.swift b/submodules/TelegramCallsUI/Sources/PresentationGroupCall.swift index 2abe1cf67d..9f0a665baf 100644 --- a/submodules/TelegramCallsUI/Sources/PresentationGroupCall.swift +++ b/submodules/TelegramCallsUI/Sources/PresentationGroupCall.swift @@ -28,6 +28,7 @@ private extension PresentationGroupCallState { adminIds: Set(), muteState: GroupCallParticipantsContext.Participant.MuteState(canUnmute: true, mutedByYou: false), defaultParticipantMuteState: nil, + messagesAreEnabled: true, recordingStartTimestamp: nil, title: title, raisedHand: false, @@ -1537,6 +1538,7 @@ public final class PresentationGroupCallImpl: PresentationGroupCall { adminIds: Set(), isCreator: false, defaultParticipantsAreMuted: callInfo.defaultParticipantsAreMuted ?? GroupCallParticipantsContext.State.DefaultParticipantsAreMuted(isMuted: self.stateValue.defaultParticipantMuteState == .muted, canChange: true), + messagesAreEnabled: callInfo.messagesAreEnabled ?? GroupCallParticipantsContext.State.MessagesAreEnabled(isEnabled: self.stateValue.messagesAreEnabled, canChange: true), sortAscending: true, recordingStartTimestamp: nil, title: self.stateValue.title, @@ -1657,6 +1659,7 @@ public final class PresentationGroupCallImpl: PresentationGroupCall { recordingStartTimestamp: nil, sortAscending: true, defaultParticipantsAreMuted: callInfo.defaultParticipantsAreMuted ?? state.defaultParticipantsAreMuted, + messagesAreEnabled: callInfo.messagesAreEnabled ?? state.messagesAreEnabled, isVideoEnabled: callInfo.isVideoEnabled, unmutedVideoLimit: callInfo.unmutedVideoLimit, isStream: callInfo.isStream, @@ -1674,6 +1677,7 @@ public final class PresentationGroupCallImpl: PresentationGroupCall { recordingStartTimestamp: state.recordingStartTimestamp, sortAscending: state.sortAscending, defaultParticipantsAreMuted: state.defaultParticipantsAreMuted, + messagesAreEnabled: state.messagesAreEnabled, isVideoEnabled: state.isVideoEnabled, unmutedVideoLimit: state.unmutedVideoLimit, isStream: callInfo.isStream, @@ -2628,6 +2632,7 @@ public final class PresentationGroupCallImpl: PresentationGroupCall { recordingStartTimestamp: state.recordingStartTimestamp, sortAscending: state.sortAscending, defaultParticipantsAreMuted: state.defaultParticipantsAreMuted, + messagesAreEnabled: state.messagesAreEnabled, isVideoEnabled: state.isVideoEnabled, unmutedVideoLimit: state.unmutedVideoLimit, isStream: callInfo.isStream, @@ -3994,7 +3999,7 @@ public final class PresentationGroupCallImpl: PresentationGroupCall { public func sendMessage(text: String, entities: [MessageTextEntity]) { if let messagesContext = self.messagesContext { - messagesContext.send(text: text, entities: entities) + messagesContext.send(fromId: self.joinAsPeerId, text: text, entities: entities) } } } diff --git a/submodules/TelegramCallsUI/Sources/VideoChatScreen.swift b/submodules/TelegramCallsUI/Sources/VideoChatScreen.swift index 84012935bb..81a53afd43 100644 --- a/submodules/TelegramCallsUI/Sources/VideoChatScreen.swift +++ b/submodules/TelegramCallsUI/Sources/VideoChatScreen.swift @@ -1181,6 +1181,7 @@ final class VideoChatScreenComponent: Component { adminIds: Set([accountPeerId, conferenceSourcePeerId]), muteState: isMuted ? GroupCallParticipantsContext.Participant.MuteState(canUnmute: true, mutedByYou: true) : nil, defaultParticipantMuteState: nil, + messagesAreEnabled: true, recordingStartTimestamp: nil, title: nil, raisedHand: false, diff --git a/submodules/TelegramCore/Sources/Account/AccountIntermediateState.swift b/submodules/TelegramCore/Sources/Account/AccountIntermediateState.swift index df16ffedc2..ed3543dc7c 100644 --- a/submodules/TelegramCore/Sources/Account/AccountIntermediateState.swift +++ b/submodules/TelegramCore/Sources/Account/AccountIntermediateState.swift @@ -118,7 +118,7 @@ enum AccountStateMutationOperation { case UpdateGroupCallParticipants(id: Int64, accessHash: Int64, participants: [Api.GroupCallParticipant], version: Int32) case UpdateGroupCall(peerId: PeerId?, call: Api.GroupCall) case UpdateGroupCallChainBlocks(id: Int64, accessHash: Int64, subChainId: Int32, blocks: [Data], nextOffset: Int32) - case UpdateGroupCallMessage(id: Int64, authorId: PeerId, text: Api.TextWithEntities) + case UpdateGroupCallMessage(id: Int64, authorId: PeerId, randomId: Int64, text: Api.TextWithEntities) case UpdateGroupCallOpaqueMessage(id: Int64, authorId: PeerId, data: Data) case UpdateAutoremoveTimeout(peer: Api.Peer, value: CachedPeerAutoremoveTimeout.Value?) case UpdateAttachMenuBots @@ -411,8 +411,8 @@ struct AccountMutableState { self.addOperation(.UpdateGroupCallChainBlocks(id: id, accessHash: accessHash, subChainId: subChainId, blocks: blocks, nextOffset: nextOffset)) } - mutating func updateGroupCallMessage(id: Int64, authorId: PeerId, text: Api.TextWithEntities) { - self.addOperation(.UpdateGroupCallMessage(id: id, authorId: authorId, text: text)) + mutating func updateGroupCallMessage(id: Int64, authorId: PeerId, randomId: Int64, text: Api.TextWithEntities) { + self.addOperation(.UpdateGroupCallMessage(id: id, authorId: authorId, randomId: randomId, text: text)) } mutating func updateGroupCallOpaqueMessage(id: Int64, authorId: PeerId, data: Data) { diff --git a/submodules/TelegramCore/Sources/ForumChannels.swift b/submodules/TelegramCore/Sources/ForumChannels.swift index 7fc609da77..48e43b8d48 100644 --- a/submodules/TelegramCore/Sources/ForumChannels.swift +++ b/submodules/TelegramCore/Sources/ForumChannels.swift @@ -991,8 +991,9 @@ func _internal_requestMessageHistoryThreads(accountPeerId: PeerId, postbox: Post for topic in topics { switch topic { - case let .forumTopic(flags, id, date, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): + case let .forumTopic(flags, id, date, peer, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): let _ = draft + let _ = peer if (flags & (1 << 3)) != 0 { pinnedIds.append(Int64(id)) @@ -1198,7 +1199,7 @@ func _internal_forumChannelTopicNotificationExceptions(account: Account, id: Eng case let .forumTopics(_, _, topics, _, _, _, _): for topic in topics { switch topic { - case let .forumTopic(_, id, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): + case let .forumTopic(_, id, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): infoMapping[Int64(id)] = EngineMessageHistoryThread.Info(title: title, icon: iconEmojiId, iconColor: iconColor) case .forumTopicDeleted: break diff --git a/submodules/TelegramCore/Sources/State/AccountStateManagementUtils.swift b/submodules/TelegramCore/Sources/State/AccountStateManagementUtils.swift index 4bd29bab42..8183995e6d 100644 --- a/submodules/TelegramCore/Sources/State/AccountStateManagementUtils.swift +++ b/submodules/TelegramCore/Sources/State/AccountStateManagementUtils.swift @@ -1684,9 +1684,9 @@ private func finalStateWithUpdatesAndServerTime(accountPeerId: PeerId, postbox: if case let .inputGroupCall(id, accessHash) = call { updatedState.updateGroupCallChainBlocks(id: id, accessHash: accessHash, subChainId: subChainId, blocks: blocks.map { $0.makeData() }, nextOffset: nextOffset) } - case let .updateGroupCallMessage(call, fromId, message): + case let .updateGroupCallMessage(call, fromId, randomId, message): if case let .inputGroupCall(id, _) = call { - updatedState.updateGroupCallMessage(id: id, authorId: fromId.peerId, text: message) + updatedState.updateGroupCallMessage(id: id, authorId: fromId.peerId, randomId: randomId, text: message) } case let .updateGroupCallEncryptedMessage(call, fromId, encryptedMessage): if case let .inputGroupCall(id, _) = call { @@ -2122,7 +2122,8 @@ func resolveForumThreads(accountPeerId: PeerId, postbox: Postbox, source: FetchM switch topic { case let .forum(topic): switch topic { - case let .forumTopic(flags, id, date, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): + case let .forumTopic(flags, id, date, peer, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): + let _ = peer let _ = draft state.operations.append(.ResetForumTopic( @@ -2286,7 +2287,8 @@ func resolveForumThreads(accountPeerId: PeerId, postbox: Postbox, source: FetchM switch item { case let .forum(topic): switch topic { - case let .forumTopic(flags, id, date, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): + case let .forumTopic(flags, id, date, peer, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): + let _ = peer let _ = draft let data = MessageHistoryThreadData( @@ -2452,7 +2454,8 @@ func resolveForumThreads(accountPeerId: PeerId, postbox: Postbox, source: FetchM switch item { case let .forum(topic): switch topic { - case let .forumTopic(flags, id, date, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): + case let .forumTopic(flags, id, date, peer, title, iconColor, iconEmojiId, topMessage, readInboxMaxId, readOutboxMaxId, unreadCount, unreadMentionsCount, unreadReactionsCount, fromId, notifySettings, draft): + let _ = peer let _ = draft fetchedChatList.threadInfos[PeerAndBoundThreadId(peerId: peerId, threadId: Int64(id))] = StoreMessageHistoryThreadData( @@ -4877,10 +4880,10 @@ func replayFinalState( callId, .state(update: GroupCallParticipantsContext.Update.StateUpdate(participants: participants, version: version)) )) - case let .UpdateGroupCallMessage(callId, authorId, text): + case let .UpdateGroupCallMessage(callId, authorId, randomId, text): switch text { case let .textWithEntities(text, entities): - groupCallMessageUpdates.append(GroupCallMessageUpdate(callId: callId, update: .newPlaintextMessage(authorId: authorId, text: text, entities: messageTextEntitiesFromApiEntities(entities)))) + groupCallMessageUpdates.append(GroupCallMessageUpdate(callId: callId, update: .newPlaintextMessage(authorId: authorId, randomId: randomId, text: text, entities: messageTextEntitiesFromApiEntities(entities)))) } case let .UpdateGroupCallOpaqueMessage(callId, authorId, data): groupCallMessageUpdates.append(GroupCallMessageUpdate(callId: callId, update: .newOpaqueMessage(authorId: authorId, data: data))) diff --git a/submodules/TelegramCore/Sources/TelegramEngine/Calls/GroupCalls.swift b/submodules/TelegramCore/Sources/TelegramEngine/Calls/GroupCalls.swift index 1f2a90d176..9fd25dd6c2 100644 --- a/submodules/TelegramCore/Sources/TelegramEngine/Calls/GroupCalls.swift +++ b/submodules/TelegramCore/Sources/TelegramEngine/Calls/GroupCalls.swift @@ -94,6 +94,7 @@ public struct GroupCallInfo: Equatable { public var recordingStartTimestamp: Int32? public var sortAscending: Bool public var defaultParticipantsAreMuted: GroupCallParticipantsContext.State.DefaultParticipantsAreMuted? + public var messagesAreEnabled: GroupCallParticipantsContext.State.MessagesAreEnabled? public var isVideoEnabled: Bool public var unmutedVideoLimit: Int public var isStream: Bool @@ -110,6 +111,7 @@ public struct GroupCallInfo: Equatable { recordingStartTimestamp: Int32?, sortAscending: Bool, defaultParticipantsAreMuted: GroupCallParticipantsContext.State.DefaultParticipantsAreMuted?, + messagesAreEnabled: GroupCallParticipantsContext.State.MessagesAreEnabled?, isVideoEnabled: Bool, unmutedVideoLimit: Int, isStream: Bool, @@ -125,6 +127,7 @@ public struct GroupCallInfo: Equatable { self.recordingStartTimestamp = recordingStartTimestamp self.sortAscending = sortAscending self.defaultParticipantsAreMuted = defaultParticipantsAreMuted + self.messagesAreEnabled = messagesAreEnabled self.isVideoEnabled = isVideoEnabled self.unmutedVideoLimit = unmutedVideoLimit self.isStream = isStream @@ -152,6 +155,7 @@ extension GroupCallInfo { recordingStartTimestamp: recordStartDate, sortAscending: (flags & (1 << 6)) != 0, defaultParticipantsAreMuted: GroupCallParticipantsContext.State.DefaultParticipantsAreMuted(isMuted: (flags & (1 << 1)) != 0, canChange: (flags & (1 << 2)) != 0), + messagesAreEnabled: GroupCallParticipantsContext.State.MessagesAreEnabled(isEnabled: (flags & (1 << 17)) != 0, canChange: (flags & (1 << 18)) != 0), isVideoEnabled: (flags & (1 << 9)) != 0, unmutedVideoLimit: Int(unmutedVideoLimit), isStream: (flags & (1 << 12)) != 0, @@ -506,17 +510,17 @@ public enum GetGroupCallParticipantsError { func _internal_getGroupCallParticipants(account: Account, reference: InternalGroupCallReference, offset: String, ssrcs: [UInt32], limit: Int32, sortAscending: Bool?) -> Signal { let accountPeerId = account.peerId - let sortAscendingValue: Signal<(Bool, Int32?, Bool, GroupCallParticipantsContext.State.DefaultParticipantsAreMuted?, Bool, Int, Bool, Bool), GetGroupCallParticipantsError> + let sortAscendingValue: Signal<(Bool, Int32?, Bool, GroupCallParticipantsContext.State.DefaultParticipantsAreMuted?, GroupCallParticipantsContext.State.MessagesAreEnabled?, Bool, Int, Bool, Bool), GetGroupCallParticipantsError> sortAscendingValue = _internal_getCurrentGroupCall(account: account, reference: reference) |> mapError { _ -> GetGroupCallParticipantsError in return .generic } - |> mapToSignal { result -> Signal<(Bool, Int32?, Bool, GroupCallParticipantsContext.State.DefaultParticipantsAreMuted?, Bool, Int, Bool, Bool), GetGroupCallParticipantsError> in + |> mapToSignal { result -> Signal<(Bool, Int32?, Bool, GroupCallParticipantsContext.State.DefaultParticipantsAreMuted?, GroupCallParticipantsContext.State.MessagesAreEnabled?, Bool, Int, Bool, Bool), GetGroupCallParticipantsError> in guard let result = result else { return .fail(.generic) } - return .single((sortAscending ?? result.info.sortAscending, result.info.scheduleTimestamp, result.info.subscribedToScheduled, result.info.defaultParticipantsAreMuted, result.info.isVideoEnabled, result.info.unmutedVideoLimit, result.info.isStream, result.info.isCreator)) + return .single((sortAscending ?? result.info.sortAscending, result.info.scheduleTimestamp, result.info.subscribedToScheduled, result.info.defaultParticipantsAreMuted, result.info.messagesAreEnabled, result.info.isVideoEnabled, result.info.unmutedVideoLimit, result.info.isStream, result.info.isCreator)) } return combineLatest( @@ -533,7 +537,7 @@ func _internal_getGroupCallParticipants(account: Account, reference: InternalGro let version: Int32 let nextParticipantsFetchOffset: String? - let (sortAscendingValue, scheduleTimestamp, subscribedToScheduled, defaultParticipantsAreMuted, isVideoEnabled, unmutedVideoLimit, isStream, isCreator) = sortAscendingAndScheduleTimestamp + let (sortAscendingValue, scheduleTimestamp, subscribedToScheduled, defaultParticipantsAreMuted, messagesAreEnabled, isVideoEnabled, unmutedVideoLimit, isStream, isCreator) = sortAscendingAndScheduleTimestamp switch result { case let .groupParticipants(count, participants, nextOffset, chats, users, apiVersion): @@ -560,6 +564,7 @@ func _internal_getGroupCallParticipants(account: Account, reference: InternalGro adminIds: Set(), isCreator: isCreator, defaultParticipantsAreMuted: defaultParticipantsAreMuted ?? GroupCallParticipantsContext.State.DefaultParticipantsAreMuted(isMuted: false, canChange: false), + messagesAreEnabled: messagesAreEnabled ?? GroupCallParticipantsContext.State.MessagesAreEnabled(isEnabled: true, canChange: false), sortAscending: sortAscendingValue, recordingStartTimestamp: nil, title: nil, @@ -1374,11 +1379,22 @@ public final class GroupCallParticipantsContext { } } + public struct MessagesAreEnabled: Equatable { + public var isEnabled: Bool + public var canChange: Bool + + public init(isEnabled: Bool, canChange: Bool) { + self.isEnabled = isEnabled + self.canChange = canChange + } + } + public var participants: [Participant] public var nextParticipantsFetchOffset: String? public var adminIds: Set public var isCreator: Bool public var defaultParticipantsAreMuted: DefaultParticipantsAreMuted + public var messagesAreEnabled: MessagesAreEnabled public var sortAscending: Bool public var recordingStartTimestamp: Int32? public var title: String? @@ -1416,6 +1432,7 @@ public final class GroupCallParticipantsContext { adminIds: Set, isCreator: Bool, defaultParticipantsAreMuted: DefaultParticipantsAreMuted, + messagesAreEnabled: MessagesAreEnabled, sortAscending: Bool, recordingStartTimestamp: Int32?, title: String?, @@ -1432,6 +1449,7 @@ public final class GroupCallParticipantsContext { self.adminIds = adminIds self.isCreator = isCreator self.defaultParticipantsAreMuted = defaultParticipantsAreMuted + self.messagesAreEnabled = messagesAreEnabled self.sortAscending = sortAscending self.recordingStartTimestamp = recordingStartTimestamp self.title = title @@ -1708,6 +1726,7 @@ public final class GroupCallParticipantsContext { private let updateDefaultMuteDisposable = MetaDisposable() private let resetInviteLinksDisposable = MetaDisposable() private let updateShouldBeRecordingDisposable = MetaDisposable() + private let updateMessagesEnabledDisposable = MetaDisposable() private let subscribeDisposable = MetaDisposable() private var localVideoIsMuted: Bool? = nil @@ -1801,6 +1820,7 @@ public final class GroupCallParticipantsContext { adminIds: strongSelf.stateValue.state.adminIds, isCreator: strongSelf.stateValue.state.isCreator, defaultParticipantsAreMuted: strongSelf.stateValue.state.defaultParticipantsAreMuted, + messagesAreEnabled: strongSelf.stateValue.state.messagesAreEnabled, sortAscending: strongSelf.stateValue.state.sortAscending, recordingStartTimestamp: strongSelf.stateValue.state.recordingStartTimestamp, title: strongSelf.stateValue.state.title, @@ -1916,6 +1936,7 @@ public final class GroupCallParticipantsContext { self.activitiesDisposable?.dispose() self.updateDefaultMuteDisposable.dispose() self.updateShouldBeRecordingDisposable.dispose() + self.updateMessagesEnabledDisposable.dispose() self.activityRankResetTimer?.invalidate() self.resetInviteLinksDisposable.dispose() self.subscribeDisposable.dispose() @@ -2029,6 +2050,7 @@ public final class GroupCallParticipantsContext { adminIds: strongSelf.stateValue.state.adminIds, isCreator: strongSelf.stateValue.state.isCreator, defaultParticipantsAreMuted: strongSelf.stateValue.state.defaultParticipantsAreMuted, + messagesAreEnabled: strongSelf.stateValue.state.messagesAreEnabled, sortAscending: strongSelf.stateValue.state.sortAscending, recordingStartTimestamp: strongSelf.stateValue.state.recordingStartTimestamp, title: strongSelf.stateValue.state.title, @@ -2273,6 +2295,7 @@ public final class GroupCallParticipantsContext { adminIds: adminIds, isCreator: isCreator, defaultParticipantsAreMuted: defaultParticipantsAreMuted, + messagesAreEnabled: strongSelf.stateValue.state.messagesAreEnabled, sortAscending: strongSelf.stateValue.state.sortAscending, recordingStartTimestamp: recordingStartTimestamp, title: title, @@ -2550,7 +2573,22 @@ public final class GroupCallParticipantsContext { } self.stateValue.state.defaultParticipantsAreMuted.isMuted = isMuted - self.updateDefaultMuteDisposable.set((self.account.network.request(Api.functions.phone.toggleGroupCallSettings(flags: 1 << 0, call: self.reference.apiInputGroupCall, joinMuted: isMuted ? .boolTrue : .boolFalse)) + self.updateDefaultMuteDisposable.set((self.account.network.request(Api.functions.phone.toggleGroupCallSettings(flags: 1 << 0, call: self.reference.apiInputGroupCall, joinMuted: isMuted ? .boolTrue : .boolFalse, messagesEnabled: nil)) + |> deliverOnMainQueue).start(next: { [weak self] updates in + guard let strongSelf = self else { + return + } + strongSelf.account.stateManager.addUpdates(updates) + })) + } + + public func updateMessagesEnabled(isEnabled: Bool) { + if isEnabled == self.stateValue.state.messagesAreEnabled.isEnabled { + return + } + self.stateValue.state.messagesAreEnabled.isEnabled = isEnabled + + self.updateDefaultMuteDisposable.set((self.account.network.request(Api.functions.phone.toggleGroupCallSettings(flags: 1 << 2, call: self.reference.apiInputGroupCall, joinMuted: nil, messagesEnabled: isEnabled ? .boolTrue : .boolFalse)) |> deliverOnMainQueue).start(next: { [weak self] updates in guard let strongSelf = self else { return @@ -2560,7 +2598,7 @@ public final class GroupCallParticipantsContext { } public func resetInviteLinks() { - self.resetInviteLinksDisposable.set((self.account.network.request(Api.functions.phone.toggleGroupCallSettings(flags: 1 << 1, call: self.reference.apiInputGroupCall, joinMuted: nil)) + self.resetInviteLinksDisposable.set((self.account.network.request(Api.functions.phone.toggleGroupCallSettings(flags: 1 << 1, call: self.reference.apiInputGroupCall, joinMuted: nil, messagesEnabled: nil)) |> deliverOnMainQueue).start(next: { [weak self] updates in guard let strongSelf = self else { return @@ -3251,7 +3289,7 @@ public enum RevokeConferenceInviteLinkError { } func _internal_revokeConferenceInviteLink(account: Account, reference: InternalGroupCallReference, link: String) -> Signal { - return account.network.request(Api.functions.phone.toggleGroupCallSettings(flags: 1 << 1, call: reference.apiInputGroupCall, joinMuted: .boolFalse)) + return account.network.request(Api.functions.phone.toggleGroupCallSettings(flags: 1 << 1, call: reference.apiInputGroupCall, joinMuted: .boolFalse, messagesEnabled: nil)) |> mapError { _ -> RevokeConferenceInviteLinkError in return .generic } @@ -3376,7 +3414,7 @@ func _internal_refreshInlineGroupCall(account: Account, messageId: MessageId) -> struct GroupCallMessageUpdate { enum Update { - case newPlaintextMessage(authorId: PeerId, text: String, entities: [MessageTextEntity]) + case newPlaintextMessage(authorId: PeerId, randomId: Int64, text: String, entities: [MessageTextEntity]) case newOpaqueMessage(authorId: PeerId, data: Data) } @@ -3462,6 +3500,8 @@ public final class GroupCallMessagesContext { var updatesDisposable: Disposable? let sendMessageDisposables = DisposableSet() + var processedIds = Set() + private var messageLifeTimer: SwiftSignalKit.Timer? init(queue: Queue, account: Account, callId: Int64, reference: InternalGroupCallReference, e2eContext: ConferenceCallE2EContext?, messageLifetime: Int32) { @@ -3481,16 +3521,16 @@ public final class GroupCallMessagesContext { return } let currentTime = Int32(CFAbsoluteTimeGetCurrent()) - var addedMessages: [(authorId: PeerId, text: String, entities: [MessageTextEntity])] = [] + var addedMessages: [(authorId: PeerId, randomId: Int64, text: String, entities: [MessageTextEntity])] = [] var addedOpaqueMessages: [(authorId: PeerId, data: Data)] = [] for update in updates { if update.callId != self.callId { continue } switch update.update { - case let .newPlaintextMessage(authorId, text, entities): + case let .newPlaintextMessage(authorId, randomId, text, entities): if authorId != self.account.peerId { - addedMessages.append((authorId, text, entities)) + addedMessages.append((authorId, randomId, text, entities)) } case let .newOpaqueMessage(authorId, data): if authorId != self.account.peerId { @@ -3544,13 +3584,11 @@ public final class GroupCallMessagesContext { } } else { for addedMessage in addedMessages { - if addedMessage.authorId == account.peerId { + if self.processedIds.contains(addedMessage.randomId) { continue } - let messageId = self.nextId - self.nextId += 1 messages.append(Message( - id: messageId, + id: addedMessage.randomId, author: transaction.getPeer(addedMessage.authorId).flatMap(EnginePeer.init), text: addedMessage.text, entities: addedMessage.entities, @@ -3565,6 +3603,9 @@ public final class GroupCallMessagesContext { guard let self else { return } + for message in messages { + self.processedIds.insert(message.id) + } var state = self.state state.messages.append(contentsOf: messages) self.state = state @@ -3595,15 +3636,15 @@ public final class GroupCallMessagesContext { } } - func send(text: String, entities: [MessageTextEntity]) { - let accountPeerId = self.account.peerId + func send(fromId: EnginePeer.Id, text: String, entities: [MessageTextEntity]) { let _ = (self.account.postbox.transaction { transaction -> Peer? in - return transaction.getPeer(accountPeerId) + return transaction.getPeer(fromId) } - |> deliverOn(self.queue)).startStandalone(next: { [weak self] accountPeer in + |> deliverOn(self.queue)).startStandalone(next: { [weak self] fromPeer in guard let self else { return } + let currentTime = Int32(CFAbsoluteTimeGetCurrent()) let messageId = self.nextId @@ -3612,7 +3653,7 @@ public final class GroupCallMessagesContext { var state = self.state state.messages.append(Message( id: messageId, - author: accountPeer.flatMap(EnginePeer.init), + author: fromPeer.flatMap(EnginePeer.init), text: text, entities: entities, date: currentTime, @@ -3620,6 +3661,8 @@ public final class GroupCallMessagesContext { )) self.state = state + self.processedIds.insert(messageId) + if let e2eContext = self.e2eContext { let buffer = Buffer() Api.TextWithEntities.textWithEntities(text: text, entities: apiEntitiesFromMessageTextEntities(entities, associatedPeers: SimpleDictionary())).serialize(buffer, true) @@ -3637,8 +3680,11 @@ public final class GroupCallMessagesContext { )).startStrict()) } } else { + var randomId: Int64 = 0 + arc4random_buf(&randomId, 8) self.sendMessageDisposables.add(self.account.network.request(Api.functions.phone.sendGroupCallMessage( call: self.reference.apiInputGroupCall, + randomId: randomId, message: .textWithEntities( text: text, entities: apiEntitiesFromMessageTextEntities(entities, associatedPeers: SimpleDictionary()) @@ -3666,9 +3712,9 @@ public final class GroupCallMessagesContext { }) } - public func send(text: String, entities: [MessageTextEntity]) { + public func send(fromId: EnginePeer.Id, text: String, entities: [MessageTextEntity]) { self.impl.with { impl in - impl.send(text: text, entities: entities) + impl.send(fromId: fromId, text: text, entities: entities) } } } diff --git a/submodules/TelegramCore/Sources/TelegramEngine/Peers/ChannelAdminEventLogs.swift b/submodules/TelegramCore/Sources/TelegramEngine/Peers/ChannelAdminEventLogs.swift index 3f2d19367b..2fd1488d76 100644 --- a/submodules/TelegramCore/Sources/TelegramEngine/Peers/ChannelAdminEventLogs.swift +++ b/submodules/TelegramCore/Sources/TelegramEngine/Peers/ChannelAdminEventLogs.swift @@ -328,14 +328,14 @@ func channelAdminLogEvents(accountPeerId: PeerId, postbox: Postbox, network: Net action = .changeUsernames(prev: prevValue, new: newValue) case let .channelAdminLogEventActionCreateTopic(topic): switch topic { - case let .forumTopic(_, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): + case let .forumTopic(_, _, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): action = .createTopic(info: EngineMessageHistoryThread.Info(title: title, icon: iconEmojiId, iconColor: iconColor)) case .forumTopicDeleted: action = .createTopic(info: EngineMessageHistoryThread.Info(title: "", icon: nil, iconColor: 0)) } case let .channelAdminLogEventActionDeleteTopic(topic): switch topic { - case let .forumTopic(_, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): + case let .forumTopic(_, _, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): action = .deleteTopic(info: EngineMessageHistoryThread.Info(title: title, icon: iconEmojiId, iconColor: iconColor)) case .forumTopicDeleted: action = .deleteTopic(info: EngineMessageHistoryThread.Info(title: "", icon: nil, iconColor: 0)) @@ -343,7 +343,7 @@ func channelAdminLogEvents(accountPeerId: PeerId, postbox: Postbox, network: Net case let .channelAdminLogEventActionEditTopic(prevTopic, newTopic): let prevInfo: AdminLogEventAction.ForumTopicInfo switch prevTopic { - case let .forumTopic(flags, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): + case let .forumTopic(flags, _, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): prevInfo = AdminLogEventAction.ForumTopicInfo(info: EngineMessageHistoryThread.Info(title: title, icon: iconEmojiId, iconColor: iconColor), isClosed: (flags & (1 << 2)) != 0, isHidden: (flags & (1 << 6)) != 0) case .forumTopicDeleted: prevInfo = AdminLogEventAction.ForumTopicInfo(info: EngineMessageHistoryThread.Info(title: "", icon: nil, iconColor: 0), isClosed: false, isHidden: false) @@ -351,7 +351,7 @@ func channelAdminLogEvents(accountPeerId: PeerId, postbox: Postbox, network: Net let newInfo: AdminLogEventAction.ForumTopicInfo switch newTopic { - case let .forumTopic(flags, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): + case let .forumTopic(flags, _, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): newInfo = AdminLogEventAction.ForumTopicInfo(info: EngineMessageHistoryThread.Info(title: title, icon: iconEmojiId, iconColor: iconColor), isClosed: (flags & (1 << 2)) != 0, isHidden: (flags & (1 << 6)) != 0) case .forumTopicDeleted: newInfo = AdminLogEventAction.ForumTopicInfo(info: EngineMessageHistoryThread.Info(title: "", icon: nil, iconColor: 0), isClosed: false, isHidden: false) @@ -361,7 +361,7 @@ func channelAdminLogEvents(accountPeerId: PeerId, postbox: Postbox, network: Net case let .channelAdminLogEventActionPinTopic(_, prevTopic, newTopic): let prevInfo: EngineMessageHistoryThread.Info? switch prevTopic { - case let .forumTopic(_, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): + case let .forumTopic(_, _, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): prevInfo = EngineMessageHistoryThread.Info(title: title, icon: iconEmojiId, iconColor: iconColor) case .forumTopicDeleted: prevInfo = EngineMessageHistoryThread.Info(title: "", icon: nil, iconColor: 0) @@ -371,7 +371,7 @@ func channelAdminLogEvents(accountPeerId: PeerId, postbox: Postbox, network: Net let newInfo: EngineMessageHistoryThread.Info? switch newTopic { - case let .forumTopic(_, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): + case let .forumTopic(_, _, _, _, title, iconColor, iconEmojiId, _, _, _, _, _, _, _, _, _): newInfo = EngineMessageHistoryThread.Info(title: title, icon: iconEmojiId, iconColor: iconColor) case .forumTopicDeleted: newInfo = EngineMessageHistoryThread.Info(title: "", icon: nil, iconColor: 0) diff --git a/submodules/TelegramUI/Components/EdgeEffect/Sources/EdgeEffect.swift b/submodules/TelegramUI/Components/EdgeEffect/Sources/EdgeEffect.swift index 5b05658797..d2e812a783 100644 --- a/submodules/TelegramUI/Components/EdgeEffect/Sources/EdgeEffect.swift +++ b/submodules/TelegramUI/Components/EdgeEffect/Sources/EdgeEffect.swift @@ -26,14 +26,21 @@ public final class EdgeEffectView: UIView { fatalError("init(coder:) has not been implemented") } - public func update(content: UIColor, isInverted: Bool, rect: CGRect, edge: Edge, edgeSize: CGFloat, containerSize: CGSize, transition: ComponentTransition) { + public func update(content: UIColor, alpha: CGFloat = 0.65, rect: CGRect, edge: Edge, edgeSize: CGFloat, transition: ComponentTransition) { self.contentView.backgroundColor = content + switch edge { + case .top: + self.contentMaskView.transform = CGAffineTransformMakeScale(1.0, -1.0) + case .bottom: + self.contentMaskView.transform = .identity + } + transition.setFrame(view: self.contentView, frame: CGRect(origin: CGPoint(), size: rect.size)) transition.setFrame(view: self.contentMaskView, frame: CGRect(origin: CGPoint(), size: rect.size)) if self.contentMaskView.image?.size.height != edgeSize { - let baseGradientAlpha: CGFloat = 0.65 + let baseGradientAlpha: CGFloat = alpha let numSteps = 8 let firstStep = 1 let firstLocation = 0.0 @@ -54,7 +61,7 @@ public final class EdgeEffectView: UIView { return (firstLocation + (1.0 - firstLocation) * step) } } - + if edgeSize > 0.0 { self.contentMaskView.image = generateGradientImage( size: CGSize(width: 8.0, height: edgeSize), diff --git a/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/UserApperanceScreen.swift b/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/UserApperanceScreen.swift index c93b7d1f04..9fb46e7c2b 100644 --- a/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/UserApperanceScreen.swift +++ b/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/UserApperanceScreen.swift @@ -1808,7 +1808,7 @@ final class UserAppearanceScreenComponent: Component { let edgeEffectHeight: CGFloat = availableSize.height - buttonY + 24.0 let edgeEffectFrame = CGRect(origin: CGPoint(x: 0.0, y: availableSize.height - edgeEffectHeight), size: CGSize(width: availableSize.width, height: edgeEffectHeight)) transition.setFrame(view: self.edgeEffectView, frame: edgeEffectFrame) - self.edgeEffectView.update(content: environment.theme.list.blocksBackgroundColor, isInverted: false, rect: edgeEffectFrame, edge: .bottom, edgeSize: edgeEffectFrame.height, containerSize: availableSize, transition: transition) + self.edgeEffectView.update(content: environment.theme.list.blocksBackgroundColor, rect: edgeEffectFrame, edge: .bottom, edgeSize: edgeEffectFrame.height, transition: transition) let previousBounds = self.scrollView.bounds let contentSize = CGSize(width: availableSize.width, height: contentHeight)