From 40d40dd8e76576d801b8f1da23c1d7c18b75f043 Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Fri, 26 Jul 2024 20:59:48 +0200 Subject: [PATCH 1/8] Various improvements --- .../Telegram-iOS/en.lproj/Localizable.strings | 12 +- .../Sources/BrowserAddressBarComponent.swift | 3 +- .../Sources/BrowserAddressListComponent.swift | 2 +- .../BrowserUI/Sources/BrowserScreen.swift | 47 +- .../BrowserUI/Sources/BrowserWebContent.swift | 7 +- .../WebBrowserSettingsController.swift | 73 ++- submodules/TelegramApi/Sources/Api0.swift | 3 +- submodules/TelegramApi/Sources/Api10.swift | 280 ++++------ submodules/TelegramApi/Sources/Api11.swift | 486 ++++++----------- submodules/TelegramApi/Sources/Api12.swift | 492 +++++++++++------- submodules/TelegramApi/Sources/Api13.swift | 310 ++++++----- submodules/TelegramApi/Sources/Api14.swift | 136 +++++ submodules/TelegramApi/Sources/Api9.swift | 134 +---- .../Sources/State/ApplyUpdateMessage.swift | 14 +- .../TelegramEngine/Messages/Stories.swift | 6 +- .../Components/Chat/ChatEmptyNode/BUILD | 1 + .../ChatEmptyNode/Sources/ChatEmptyNode.swift | 32 +- .../ChatMessageWebpageBubbleContentNode.swift | 6 +- .../Sources/EditStories.swift | 13 +- .../Sources/MediaEditorScreen.swift | 8 +- .../Resources/Animations/PremiumRequired.tgs | Bin 0 -> 1676 bytes .../Chat/ChatControllerOpenWebApp.swift | 10 +- .../Sources/TelegramRootController.swift | 4 +- .../WebUI/Sources/WebAppController.swift | 8 + 24 files changed, 1117 insertions(+), 970 deletions(-) create mode 100644 submodules/TelegramUI/Resources/Animations/PremiumRequired.tgs diff --git a/Telegram/Telegram-iOS/en.lproj/Localizable.strings b/Telegram/Telegram-iOS/en.lproj/Localizable.strings index da0a67d6af..a5f2b09caa 100644 --- a/Telegram/Telegram-iOS/en.lproj/Localizable.strings +++ b/Telegram/Telegram-iOS/en.lproj/Localizable.strings @@ -12571,7 +12571,7 @@ Sorry for the inconvenience."; "WebBrowser.AutoLogin.Info" = "Use your Telegram account to automatically log in to websites opened in the in-app browser."; "WebBrowser.ClearCookies" = "Clear Cookies"; -"WebBrowser.ClearCookies.Info" = "Delete all cookies in the Telegram in-app browser. This action will sign you out of most websites."; +"WebBrowser.ClearCookies.Info" = "Delete all cookies and cache in the Telegram in-app browser. This action will sign you out of most websites."; "WebBrowser.ClearCookies.Succeed" = "Cookies cleared."; "WebBrowser.Exceptions.Title" = "NEVER OPEN IN THE IN-APP BROWSER"; @@ -12589,6 +12589,12 @@ Sorry for the inconvenience."; "WebBrowser.ClearCookies.ClearConfirmation.Text" = "Are you sure you want to clear cookies?"; "WebBrowser.ClearCookies.ClearConfirmation.Clear" = "Clear"; +"WebBrowser.ClearCache" = "Clear Cache"; +"WebBrowser.ClearCache.ClearConfirmation.Text" = "Are you sure you want to clear cookies?"; +"WebBrowser.ClearCache.ClearConfirmation.Clear" = "Clear"; +"WebBrowser.ClearCache.Succeed" = "Cookies cleared."; + + "WebBrowser.Done" = "Done"; "AccessDenied.LocationWeather" = "Telegram needs access to your location so that you can add the weather widget to your stories.\n\nPlease go to Settings > Privacy > Location Services and set Telegram to ON."; @@ -12658,3 +12664,7 @@ Sorry for the inconvenience."; "Stars.Intro.Transaction.Gift.Title" = "Received Gift"; "Stars.Intro.Transaction.Gift.UnknownUser" = "Unknown User"; + +"WebApp.PrivacyPolicy" = "Privacy Policy"; + +"Conversation.OpenProfile" = "OPEN PROFILE"; diff --git a/submodules/BrowserUI/Sources/BrowserAddressBarComponent.swift b/submodules/BrowserUI/Sources/BrowserAddressBarComponent.swift index cb5f0d373c..dcb1cd88c8 100644 --- a/submodules/BrowserUI/Sources/BrowserAddressBarComponent.swift +++ b/submodules/BrowserUI/Sources/BrowserAddressBarComponent.swift @@ -249,8 +249,7 @@ final class AddressBarContentComponent: Component { public func textFieldShouldReturn(_ textField: UITextField) -> Bool { if let component = self.component { let finalUrl = explicitUrl(textField.text ?? "") -// finalUrl = finalUrl.addingPercentEncoding(withAllowedCharacters: .urlFragmentAllowed) ?? finalUrl - component.performAction.invoke(.navigateTo(finalUrl)) + component.performAction.invoke(.navigateTo(finalUrl, true)) } textField.endEditing(true) return false diff --git a/submodules/BrowserUI/Sources/BrowserAddressListComponent.swift b/submodules/BrowserUI/Sources/BrowserAddressListComponent.swift index b07f068e49..5675dd5a46 100644 --- a/submodules/BrowserUI/Sources/BrowserAddressListComponent.swift +++ b/submodules/BrowserUI/Sources/BrowserAddressListComponent.swift @@ -390,7 +390,7 @@ final class BrowserAddressListComponent: Component { insets: component.insets, action: { if let url = webPage?.content.url { - performAction.invoke(.navigateTo(url)) + performAction.invoke(.navigateTo(url, false)) } }, contextAction: { [weak self] webPage, message, sourceView, gesture in diff --git a/submodules/BrowserUI/Sources/BrowserScreen.swift b/submodules/BrowserUI/Sources/BrowserScreen.swift index 2b0df2a489..c9ce6c8ed8 100644 --- a/submodules/BrowserUI/Sources/BrowserScreen.swift +++ b/submodules/BrowserUI/Sources/BrowserScreen.swift @@ -153,24 +153,26 @@ private final class BrowserScreenComponent: CombinedComponent { ] if isTablet { -// navigationLeftItems.append( -// AnyComponentWithIdentity( -// id: "minimize", -// component: AnyComponent( -// Button( -// content: AnyComponent( -// BundleIconComponent( -// name: "Media Gallery/PictureInPictureButton", -// tintColor: environment.theme.rootController.navigationBar.accentTextColor -// ) -// ), -// action: { -// performAction.invoke(.close) -// } -// ) -// ) -// ) -// ) + #if DEBUG + navigationLeftItems.append( + AnyComponentWithIdentity( + id: "minimize", + component: AnyComponent( + Button( + content: AnyComponent( + BundleIconComponent( + name: "Media Gallery/PictureInPictureButton", + tintColor: environment.theme.rootController.navigationBar.accentTextColor + ) + ), + action: { + performAction.invoke(.close) + } + ) + ) + ) + ) + #endif let canGoBack = context.component.contentState?.canGoBack ?? false let canGoForward = context.component.contentState?.canGoForward ?? false @@ -483,7 +485,7 @@ public class BrowserScreen: ViewController, MinimizableController { case openBookmarks case openAddressBar case closeAddressBar - case navigateTo(String) + case navigateTo(String, Bool) case expand } @@ -730,9 +732,12 @@ public class BrowserScreen: ViewController, MinimizableController { updatedState.addressFocused = false return updatedState }) - case let .navigateTo(address): + case let .navigateTo(address, addToRecent): if let content = self.content.last as? BrowserWebContent { content.navigateTo(address: address) + if addToRecent { + content.addToRecentlyVisited() + } } self.updatePresentationState(transition: .spring(duration: 0.4), { state in var updatedState = state @@ -988,7 +993,7 @@ public class BrowserScreen: ViewController, MinimizableController { } let controller = BrowserBookmarksScreen(context: self.context, url: url, openUrl: { [weak self] url in if let self { - self.performAction.invoke(.navigateTo(url)) + self.performAction.invoke(.navigateTo(url, true)) } }, addBookmark: { [weak self] in self?.addBookmark(url, showArrow: false) diff --git a/submodules/BrowserUI/Sources/BrowserWebContent.swift b/submodules/BrowserUI/Sources/BrowserWebContent.swift index 438236dd96..7efff4450f 100644 --- a/submodules/BrowserUI/Sources/BrowserWebContent.swift +++ b/submodules/BrowserUI/Sources/BrowserWebContent.swift @@ -752,7 +752,12 @@ final class BrowserWebContent: UIView, BrowserContent, WKNavigationDelegate, WKU func webView(_ webView: WKWebView, createWebViewWith configuration: WKWebViewConfiguration, for navigationAction: WKNavigationAction, windowFeatures: WKWindowFeatures) -> WKWebView? { if navigationAction.targetFrame == nil { if let url = navigationAction.request.url?.absoluteString { - self.open(url: url, new: true) + if isTelegramMeLink(url) || isTelegraPhLink(url) { + self.minimize() + self.openAppUrl(url) + } else { + self.open(url: url, new: true) + } } } return nil diff --git a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift index 8a303cdf76..455b8d430a 100644 --- a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift +++ b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift @@ -21,6 +21,7 @@ private final class WebBrowserSettingsControllerArguments { let context: AccountContext let updateDefaultBrowser: (String?) -> Void let clearCookies: () -> Void + let clearCache: () -> Void let addException: () -> Void let removeException: (String) -> Void let clearExceptions: () -> Void @@ -29,6 +30,7 @@ private final class WebBrowserSettingsControllerArguments { context: AccountContext, updateDefaultBrowser: @escaping (String?) -> Void, clearCookies: @escaping () -> Void, + clearCache: @escaping () -> Void, addException: @escaping () -> Void, removeException: @escaping (String) -> Void, clearExceptions: @escaping () -> Void @@ -36,6 +38,7 @@ private final class WebBrowserSettingsControllerArguments { self.context = context self.updateDefaultBrowser = updateDefaultBrowser self.clearCookies = clearCookies + self.clearCache = clearCache self.addException = addException self.removeException = removeException self.clearExceptions = clearExceptions @@ -53,6 +56,7 @@ private enum WebBrowserSettingsControllerEntry: ItemListNodeEntry { case browser(PresentationTheme, String, OpenInApplication?, String?, Bool, Int32) case clearCookies(PresentationTheme, String) + case clearCache(PresentationTheme, String) case clearCookiesInfo(PresentationTheme, String) case exceptionsHeader(PresentationTheme, String) @@ -65,7 +69,7 @@ private enum WebBrowserSettingsControllerEntry: ItemListNodeEntry { switch self { case .browserHeader, .browser: return WebBrowserSettingsSection.browsers.rawValue - case .clearCookies, .clearCookiesInfo: + case .clearCookies, .clearCache, .clearCookiesInfo: return WebBrowserSettingsSection.clearCookies.rawValue case .exceptionsHeader, .exceptionsAdd, .exception, .exceptionsClear, .exceptionsInfo: return WebBrowserSettingsSection.exceptions.rawValue @@ -80,12 +84,14 @@ private enum WebBrowserSettingsControllerEntry: ItemListNodeEntry { return UInt64(1 + index) case .clearCookies: return 102 - case .clearCookiesInfo: + case .clearCache: return 103 - case .exceptionsHeader: + case .clearCookiesInfo: return 104 - case .exceptionsAdd: + case .exceptionsHeader: return 105 + case .exceptionsAdd: + return 106 case let .exception(_, _, exception): return 2000 + exception.domain.persistentHashValue case .exceptionsClear: @@ -103,14 +109,16 @@ private enum WebBrowserSettingsControllerEntry: ItemListNodeEntry { return 1 + index case .clearCookies: return 102 - case .clearCookiesInfo: + case .clearCache: return 103 - case .exceptionsHeader: + case .clearCookiesInfo: return 104 - case .exceptionsAdd: + case .exceptionsHeader: return 105 + case .exceptionsAdd: + return 106 case let .exception(index, _, _): - return 106 + index + return 107 + index case .exceptionsClear: return 1000 case .exceptionsInfo: @@ -138,6 +146,12 @@ private enum WebBrowserSettingsControllerEntry: ItemListNodeEntry { } else { return false } + case let .clearCache(lhsTheme, lhsText): + if case let .clearCache(rhsTheme, rhsText) = rhs, lhsTheme === rhsTheme, lhsText == rhsText { + return true + } else { + return false + } case let .clearCookiesInfo(lhsTheme, lhsText): if case let .clearCookiesInfo(rhsTheme, rhsText) = rhs, lhsTheme === rhsTheme, lhsText == rhsText { return true @@ -194,6 +208,10 @@ private enum WebBrowserSettingsControllerEntry: ItemListNodeEntry { return ItemListPeerActionItem(presentationData: presentationData, icon: PresentationResourcesItemList.accentDeleteIconImage(presentationData.theme), title: text, sectionId: self.section, height: .generic, color: .accent, editing: false, action: { arguments.clearCookies() }) + case let .clearCache(_, text): + return ItemListPeerActionItem(presentationData: presentationData, icon: PresentationResourcesItemList.accentDeleteIconImage(presentationData.theme), title: text, sectionId: self.section, height: .generic, color: .accent, editing: false, action: { + arguments.clearCache() + }) case let .clearCookiesInfo(_, text): return ItemListTextItem(presentationData: presentationData, text: .plain(text), sectionId: self.section) case let .exceptionsHeader(_, text): @@ -232,6 +250,7 @@ private func webBrowserSettingsControllerEntries(context: AccountContext, presen if settings.defaultWebBrowser == nil { entries.append(.clearCookies(presentationData.theme, presentationData.strings.WebBrowser_ClearCookies)) + entries.append(.clearCache(presentationData.theme, presentationData.strings.WebBrowser_ClearCache)) entries.append(.clearCookiesInfo(presentationData.theme, presentationData.strings.WebBrowser_ClearCookies_Info)) entries.append(.exceptionsHeader(presentationData.theme, presentationData.strings.WebBrowser_Exceptions_Title)) @@ -255,6 +274,7 @@ private func webBrowserSettingsControllerEntries(context: AccountContext, presen public func webBrowserSettingsController(context: AccountContext) -> ViewController { var clearCookiesImpl: (() -> Void)? + var clearCacheImpl: (() -> Void)? var addExceptionImpl: (() -> Void)? var removeExceptionImpl: ((String) -> Void)? var clearExceptionsImpl: (() -> Void)? @@ -269,6 +289,9 @@ public func webBrowserSettingsController(context: AccountContext) -> ViewControl clearCookies: { clearCookiesImpl?() }, + clearCache: { + clearCacheImpl?() + }, addException: { addExceptionImpl?() }, @@ -320,7 +343,7 @@ public func webBrowserSettingsController(context: AccountContext) -> ViewControl actions: [ TextAlertAction(type: .genericAction, title: presentationData.strings.Common_Cancel, action: {}), TextAlertAction(type: .defaultAction, title: presentationData.strings.WebBrowser_ClearCookies_ClearConfirmation_Clear, action: { - WKWebsiteDataStore.default().removeData(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes(), modifiedSince: Date(timeIntervalSince1970: 0), completionHandler:{}) + WKWebsiteDataStore.default().removeData(ofTypes: [WKWebsiteDataTypeCookies, WKWebsiteDataTypeLocalStorage, WKWebsiteDataTypeSessionStorage], modifiedSince: Date(timeIntervalSince1970: 0), completionHandler:{}) let presentationData = context.sharedContext.currentPresentationData.with { $0 } controller?.present(UndoOverlayController( @@ -341,6 +364,38 @@ public func webBrowserSettingsController(context: AccountContext) -> ViewControl controller?.present(alertController, in: .window(.root)) } + clearCacheImpl = { [weak controller] in + let presentationData = context.sharedContext.currentPresentationData.with { $0 } + + let alertController = textAlertController( + context: context, + updatedPresentationData: nil, + title: nil, + text: presentationData.strings.WebBrowser_ClearCache_ClearConfirmation_Text, + actions: [ + TextAlertAction(type: .genericAction, title: presentationData.strings.Common_Cancel, action: {}), + TextAlertAction(type: .defaultAction, title: presentationData.strings.WebBrowser_ClearCache_ClearConfirmation_Clear, action: { + WKWebsiteDataStore.default().removeData(ofTypes: [WKWebsiteDataTypeDiskCache, WKWebsiteDataTypeMemoryCache], modifiedSince: Date(timeIntervalSince1970: 0), completionHandler:{}) + + let presentationData = context.sharedContext.currentPresentationData.with { $0 } + controller?.present(UndoOverlayController( + presentationData: presentationData, + content: .info( + title: nil, + text: presentationData.strings.WebBrowser_ClearCache_Succeed, + timeout: nil, + customUndoText: nil + ), + elevatedLayout: false, + position: .bottom, + action: { _ in return false }), in: .current + ) + }) + ] + ) + controller?.present(alertController, in: .window(.root)) + } + addExceptionImpl = { [weak controller] in var dismissImpl: (() -> Void)? let linkController = webBrowserDomainController(context: context, apply: { url in diff --git a/submodules/TelegramApi/Sources/Api0.swift b/submodules/TelegramApi/Sources/Api0.swift index ff4d7a0245..11b0f8515c 100644 --- a/submodules/TelegramApi/Sources/Api0.swift +++ b/submodules/TelegramApi/Sources/Api0.swift @@ -355,6 +355,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = { dict[1690108678] = { return Api.InputEncryptedFile.parse_inputEncryptedFileUploaded($0) } dict[-181407105] = { return Api.InputFile.parse_inputFile($0) } dict[-95482955] = { return Api.InputFile.parse_inputFileBig($0) } + dict[1658620744] = { return Api.InputFile.parse_inputFileStoryDocument($0) } dict[-1160743548] = { return Api.InputFileLocation.parse_inputDocumentFileLocation($0) } dict[-182231723] = { return Api.InputFileLocation.parse_inputEncryptedFileLocation($0) } dict[-539317279] = { return Api.InputFileLocation.parse_inputFileLocation($0) } @@ -1401,7 +1402,7 @@ public extension Api { return parser(reader) } else { - telegramApiLog("Type constructor \(String(UInt32(bitPattern: signature), radix: 16, uppercase: false)) not found") + telegramApiLog("Type constructor \(String(signature, radix: 16, uppercase: false)) not found") return nil } } diff --git a/submodules/TelegramApi/Sources/Api10.swift b/submodules/TelegramApi/Sources/Api10.swift index eefc46b743..79acdb0d0a 100644 --- a/submodules/TelegramApi/Sources/Api10.swift +++ b/submodules/TelegramApi/Sources/Api10.swift @@ -1,3 +1,115 @@ +public extension Api { + indirect enum InputInvoice: TypeConstructorDescription { + case inputInvoiceMessage(peer: Api.InputPeer, msgId: Int32) + case inputInvoicePremiumGiftCode(purpose: Api.InputStorePaymentPurpose, option: Api.PremiumGiftCodeOption) + case inputInvoiceSlug(slug: String) + case inputInvoiceStars(purpose: Api.InputStorePaymentPurpose) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputInvoiceMessage(let peer, let msgId): + if boxed { + buffer.appendInt32(-977967015) + } + peer.serialize(buffer, true) + serializeInt32(msgId, buffer: buffer, boxed: false) + break + case .inputInvoicePremiumGiftCode(let purpose, let option): + if boxed { + buffer.appendInt32(-1734841331) + } + purpose.serialize(buffer, true) + option.serialize(buffer, true) + break + case .inputInvoiceSlug(let slug): + if boxed { + buffer.appendInt32(-1020867857) + } + serializeString(slug, buffer: buffer, boxed: false) + break + case .inputInvoiceStars(let purpose): + if boxed { + buffer.appendInt32(1710230755) + } + purpose.serialize(buffer, true) + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputInvoiceMessage(let peer, let msgId): + return ("inputInvoiceMessage", [("peer", peer as Any), ("msgId", msgId as Any)]) + case .inputInvoicePremiumGiftCode(let purpose, let option): + return ("inputInvoicePremiumGiftCode", [("purpose", purpose as Any), ("option", option as Any)]) + case .inputInvoiceSlug(let slug): + return ("inputInvoiceSlug", [("slug", slug as Any)]) + case .inputInvoiceStars(let purpose): + return ("inputInvoiceStars", [("purpose", purpose as Any)]) + } + } + + public static func parse_inputInvoiceMessage(_ reader: BufferReader) -> InputInvoice? { + var _1: Api.InputPeer? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputPeer + } + var _2: Int32? + _2 = reader.readInt32() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputInvoice.inputInvoiceMessage(peer: _1!, msgId: _2!) + } + else { + return nil + } + } + public static func parse_inputInvoicePremiumGiftCode(_ reader: BufferReader) -> InputInvoice? { + var _1: Api.InputStorePaymentPurpose? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputStorePaymentPurpose + } + var _2: Api.PremiumGiftCodeOption? + if let signature = reader.readInt32() { + _2 = Api.parse(reader, signature: signature) as? Api.PremiumGiftCodeOption + } + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputInvoice.inputInvoicePremiumGiftCode(purpose: _1!, option: _2!) + } + else { + return nil + } + } + public static func parse_inputInvoiceSlug(_ reader: BufferReader) -> InputInvoice? { + var _1: String? + _1 = parseString(reader) + let _c1 = _1 != nil + if _c1 { + return Api.InputInvoice.inputInvoiceSlug(slug: _1!) + } + else { + return nil + } + } + public static func parse_inputInvoiceStars(_ reader: BufferReader) -> InputInvoice? { + var _1: Api.InputStorePaymentPurpose? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputStorePaymentPurpose + } + let _c1 = _1 != nil + if _c1 { + return Api.InputInvoice.inputInvoiceStars(purpose: _1!) + } + else { + return nil + } + } + + } +} public extension Api { indirect enum InputMedia: TypeConstructorDescription { case inputMediaContact(phoneNumber: String, firstName: String, lastName: String, vcard: String) @@ -918,171 +1030,3 @@ public extension Api { } } -public extension Api { - indirect enum InputPeer: TypeConstructorDescription { - case inputPeerChannel(channelId: Int64, accessHash: Int64) - case inputPeerChannelFromMessage(peer: Api.InputPeer, msgId: Int32, channelId: Int64) - case inputPeerChat(chatId: Int64) - case inputPeerEmpty - case inputPeerSelf - case inputPeerUser(userId: Int64, accessHash: Int64) - case inputPeerUserFromMessage(peer: Api.InputPeer, msgId: Int32, userId: Int64) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputPeerChannel(let channelId, let accessHash): - if boxed { - buffer.appendInt32(666680316) - } - serializeInt64(channelId, buffer: buffer, boxed: false) - serializeInt64(accessHash, buffer: buffer, boxed: false) - break - case .inputPeerChannelFromMessage(let peer, let msgId, let channelId): - if boxed { - buffer.appendInt32(-1121318848) - } - peer.serialize(buffer, true) - serializeInt32(msgId, buffer: buffer, boxed: false) - serializeInt64(channelId, buffer: buffer, boxed: false) - break - case .inputPeerChat(let chatId): - if boxed { - buffer.appendInt32(900291769) - } - serializeInt64(chatId, buffer: buffer, boxed: false) - break - case .inputPeerEmpty: - if boxed { - buffer.appendInt32(2134579434) - } - - break - case .inputPeerSelf: - if boxed { - buffer.appendInt32(2107670217) - } - - break - case .inputPeerUser(let userId, let accessHash): - if boxed { - buffer.appendInt32(-571955892) - } - serializeInt64(userId, buffer: buffer, boxed: false) - serializeInt64(accessHash, buffer: buffer, boxed: false) - break - case .inputPeerUserFromMessage(let peer, let msgId, let userId): - if boxed { - buffer.appendInt32(-1468331492) - } - peer.serialize(buffer, true) - serializeInt32(msgId, buffer: buffer, boxed: false) - serializeInt64(userId, buffer: buffer, boxed: false) - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputPeerChannel(let channelId, let accessHash): - return ("inputPeerChannel", [("channelId", channelId as Any), ("accessHash", accessHash as Any)]) - case .inputPeerChannelFromMessage(let peer, let msgId, let channelId): - return ("inputPeerChannelFromMessage", [("peer", peer as Any), ("msgId", msgId as Any), ("channelId", channelId as Any)]) - case .inputPeerChat(let chatId): - return ("inputPeerChat", [("chatId", chatId as Any)]) - case .inputPeerEmpty: - return ("inputPeerEmpty", []) - case .inputPeerSelf: - return ("inputPeerSelf", []) - case .inputPeerUser(let userId, let accessHash): - return ("inputPeerUser", [("userId", userId as Any), ("accessHash", accessHash as Any)]) - case .inputPeerUserFromMessage(let peer, let msgId, let userId): - return ("inputPeerUserFromMessage", [("peer", peer as Any), ("msgId", msgId as Any), ("userId", userId as Any)]) - } - } - - public static func parse_inputPeerChannel(_ reader: BufferReader) -> InputPeer? { - var _1: Int64? - _1 = reader.readInt64() - var _2: Int64? - _2 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputPeer.inputPeerChannel(channelId: _1!, accessHash: _2!) - } - else { - return nil - } - } - public static func parse_inputPeerChannelFromMessage(_ reader: BufferReader) -> InputPeer? { - var _1: Api.InputPeer? - if let signature = reader.readInt32() { - _1 = Api.parse(reader, signature: signature) as? Api.InputPeer - } - var _2: Int32? - _2 = reader.readInt32() - var _3: Int64? - _3 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - let _c3 = _3 != nil - if _c1 && _c2 && _c3 { - return Api.InputPeer.inputPeerChannelFromMessage(peer: _1!, msgId: _2!, channelId: _3!) - } - else { - return nil - } - } - public static func parse_inputPeerChat(_ reader: BufferReader) -> InputPeer? { - var _1: Int64? - _1 = reader.readInt64() - let _c1 = _1 != nil - if _c1 { - return Api.InputPeer.inputPeerChat(chatId: _1!) - } - else { - return nil - } - } - public static func parse_inputPeerEmpty(_ reader: BufferReader) -> InputPeer? { - return Api.InputPeer.inputPeerEmpty - } - public static func parse_inputPeerSelf(_ reader: BufferReader) -> InputPeer? { - return Api.InputPeer.inputPeerSelf - } - public static func parse_inputPeerUser(_ reader: BufferReader) -> InputPeer? { - var _1: Int64? - _1 = reader.readInt64() - var _2: Int64? - _2 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputPeer.inputPeerUser(userId: _1!, accessHash: _2!) - } - else { - return nil - } - } - public static func parse_inputPeerUserFromMessage(_ reader: BufferReader) -> InputPeer? { - var _1: Api.InputPeer? - if let signature = reader.readInt32() { - _1 = Api.parse(reader, signature: signature) as? Api.InputPeer - } - var _2: Int32? - _2 = reader.readInt32() - var _3: Int64? - _3 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - let _c3 = _3 != nil - if _c1 && _c2 && _c3 { - return Api.InputPeer.inputPeerUserFromMessage(peer: _1!, msgId: _2!, userId: _3!) - } - else { - return nil - } - } - - } -} diff --git a/submodules/TelegramApi/Sources/Api11.swift b/submodules/TelegramApi/Sources/Api11.swift index 8a502fcddf..8845ce3ec6 100644 --- a/submodules/TelegramApi/Sources/Api11.swift +++ b/submodules/TelegramApi/Sources/Api11.swift @@ -1,3 +1,171 @@ +public extension Api { + indirect enum InputPeer: TypeConstructorDescription { + case inputPeerChannel(channelId: Int64, accessHash: Int64) + case inputPeerChannelFromMessage(peer: Api.InputPeer, msgId: Int32, channelId: Int64) + case inputPeerChat(chatId: Int64) + case inputPeerEmpty + case inputPeerSelf + case inputPeerUser(userId: Int64, accessHash: Int64) + case inputPeerUserFromMessage(peer: Api.InputPeer, msgId: Int32, userId: Int64) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputPeerChannel(let channelId, let accessHash): + if boxed { + buffer.appendInt32(666680316) + } + serializeInt64(channelId, buffer: buffer, boxed: false) + serializeInt64(accessHash, buffer: buffer, boxed: false) + break + case .inputPeerChannelFromMessage(let peer, let msgId, let channelId): + if boxed { + buffer.appendInt32(-1121318848) + } + peer.serialize(buffer, true) + serializeInt32(msgId, buffer: buffer, boxed: false) + serializeInt64(channelId, buffer: buffer, boxed: false) + break + case .inputPeerChat(let chatId): + if boxed { + buffer.appendInt32(900291769) + } + serializeInt64(chatId, buffer: buffer, boxed: false) + break + case .inputPeerEmpty: + if boxed { + buffer.appendInt32(2134579434) + } + + break + case .inputPeerSelf: + if boxed { + buffer.appendInt32(2107670217) + } + + break + case .inputPeerUser(let userId, let accessHash): + if boxed { + buffer.appendInt32(-571955892) + } + serializeInt64(userId, buffer: buffer, boxed: false) + serializeInt64(accessHash, buffer: buffer, boxed: false) + break + case .inputPeerUserFromMessage(let peer, let msgId, let userId): + if boxed { + buffer.appendInt32(-1468331492) + } + peer.serialize(buffer, true) + serializeInt32(msgId, buffer: buffer, boxed: false) + serializeInt64(userId, buffer: buffer, boxed: false) + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputPeerChannel(let channelId, let accessHash): + return ("inputPeerChannel", [("channelId", channelId as Any), ("accessHash", accessHash as Any)]) + case .inputPeerChannelFromMessage(let peer, let msgId, let channelId): + return ("inputPeerChannelFromMessage", [("peer", peer as Any), ("msgId", msgId as Any), ("channelId", channelId as Any)]) + case .inputPeerChat(let chatId): + return ("inputPeerChat", [("chatId", chatId as Any)]) + case .inputPeerEmpty: + return ("inputPeerEmpty", []) + case .inputPeerSelf: + return ("inputPeerSelf", []) + case .inputPeerUser(let userId, let accessHash): + return ("inputPeerUser", [("userId", userId as Any), ("accessHash", accessHash as Any)]) + case .inputPeerUserFromMessage(let peer, let msgId, let userId): + return ("inputPeerUserFromMessage", [("peer", peer as Any), ("msgId", msgId as Any), ("userId", userId as Any)]) + } + } + + public static func parse_inputPeerChannel(_ reader: BufferReader) -> InputPeer? { + var _1: Int64? + _1 = reader.readInt64() + var _2: Int64? + _2 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputPeer.inputPeerChannel(channelId: _1!, accessHash: _2!) + } + else { + return nil + } + } + public static func parse_inputPeerChannelFromMessage(_ reader: BufferReader) -> InputPeer? { + var _1: Api.InputPeer? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputPeer + } + var _2: Int32? + _2 = reader.readInt32() + var _3: Int64? + _3 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + let _c3 = _3 != nil + if _c1 && _c2 && _c3 { + return Api.InputPeer.inputPeerChannelFromMessage(peer: _1!, msgId: _2!, channelId: _3!) + } + else { + return nil + } + } + public static func parse_inputPeerChat(_ reader: BufferReader) -> InputPeer? { + var _1: Int64? + _1 = reader.readInt64() + let _c1 = _1 != nil + if _c1 { + return Api.InputPeer.inputPeerChat(chatId: _1!) + } + else { + return nil + } + } + public static func parse_inputPeerEmpty(_ reader: BufferReader) -> InputPeer? { + return Api.InputPeer.inputPeerEmpty + } + public static func parse_inputPeerSelf(_ reader: BufferReader) -> InputPeer? { + return Api.InputPeer.inputPeerSelf + } + public static func parse_inputPeerUser(_ reader: BufferReader) -> InputPeer? { + var _1: Int64? + _1 = reader.readInt64() + var _2: Int64? + _2 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputPeer.inputPeerUser(userId: _1!, accessHash: _2!) + } + else { + return nil + } + } + public static func parse_inputPeerUserFromMessage(_ reader: BufferReader) -> InputPeer? { + var _1: Api.InputPeer? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputPeer + } + var _2: Int32? + _2 = reader.readInt32() + var _3: Int64? + _3 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + let _c3 = _3 != nil + if _c1 && _c2 && _c3 { + return Api.InputPeer.inputPeerUserFromMessage(peer: _1!, msgId: _2!, userId: _3!) + } + else { + return nil + } + } + + } +} public extension Api { enum InputPeerNotifySettings: TypeConstructorDescription { case inputPeerNotifySettings(flags: Int32, showPreviews: Api.Bool?, silent: Api.Bool?, muteUntil: Int32?, sound: Api.NotificationSound?, storiesMuted: Api.Bool?, storiesHideSender: Api.Bool?, storiesSound: Api.NotificationSound?) @@ -510,321 +678,3 @@ public extension Api { } } -public extension Api { - enum InputQuickReplyShortcut: TypeConstructorDescription { - case inputQuickReplyShortcut(shortcut: String) - case inputQuickReplyShortcutId(shortcutId: Int32) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputQuickReplyShortcut(let shortcut): - if boxed { - buffer.appendInt32(609840449) - } - serializeString(shortcut, buffer: buffer, boxed: false) - break - case .inputQuickReplyShortcutId(let shortcutId): - if boxed { - buffer.appendInt32(18418929) - } - serializeInt32(shortcutId, buffer: buffer, boxed: false) - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputQuickReplyShortcut(let shortcut): - return ("inputQuickReplyShortcut", [("shortcut", shortcut as Any)]) - case .inputQuickReplyShortcutId(let shortcutId): - return ("inputQuickReplyShortcutId", [("shortcutId", shortcutId as Any)]) - } - } - - public static func parse_inputQuickReplyShortcut(_ reader: BufferReader) -> InputQuickReplyShortcut? { - var _1: String? - _1 = parseString(reader) - let _c1 = _1 != nil - if _c1 { - return Api.InputQuickReplyShortcut.inputQuickReplyShortcut(shortcut: _1!) - } - else { - return nil - } - } - public static func parse_inputQuickReplyShortcutId(_ reader: BufferReader) -> InputQuickReplyShortcut? { - var _1: Int32? - _1 = reader.readInt32() - let _c1 = _1 != nil - if _c1 { - return Api.InputQuickReplyShortcut.inputQuickReplyShortcutId(shortcutId: _1!) - } - else { - return nil - } - } - - } -} -public extension Api { - indirect enum InputReplyTo: TypeConstructorDescription { - case inputReplyToMessage(flags: Int32, replyToMsgId: Int32, topMsgId: Int32?, replyToPeerId: Api.InputPeer?, quoteText: String?, quoteEntities: [Api.MessageEntity]?, quoteOffset: Int32?) - case inputReplyToStory(peer: Api.InputPeer, storyId: Int32) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputReplyToMessage(let flags, let replyToMsgId, let topMsgId, let replyToPeerId, let quoteText, let quoteEntities, let quoteOffset): - if boxed { - buffer.appendInt32(583071445) - } - serializeInt32(flags, buffer: buffer, boxed: false) - serializeInt32(replyToMsgId, buffer: buffer, boxed: false) - if Int(flags) & Int(1 << 0) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)} - if Int(flags) & Int(1 << 1) != 0 {replyToPeerId!.serialize(buffer, true)} - if Int(flags) & Int(1 << 2) != 0 {serializeString(quoteText!, buffer: buffer, boxed: false)} - if Int(flags) & Int(1 << 3) != 0 {buffer.appendInt32(481674261) - buffer.appendInt32(Int32(quoteEntities!.count)) - for item in quoteEntities! { - item.serialize(buffer, true) - }} - if Int(flags) & Int(1 << 4) != 0 {serializeInt32(quoteOffset!, buffer: buffer, boxed: false)} - break - case .inputReplyToStory(let peer, let storyId): - if boxed { - buffer.appendInt32(1484862010) - } - peer.serialize(buffer, true) - serializeInt32(storyId, buffer: buffer, boxed: false) - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputReplyToMessage(let flags, let replyToMsgId, let topMsgId, let replyToPeerId, let quoteText, let quoteEntities, let quoteOffset): - return ("inputReplyToMessage", [("flags", flags as Any), ("replyToMsgId", replyToMsgId as Any), ("topMsgId", topMsgId as Any), ("replyToPeerId", replyToPeerId as Any), ("quoteText", quoteText as Any), ("quoteEntities", quoteEntities as Any), ("quoteOffset", quoteOffset as Any)]) - case .inputReplyToStory(let peer, let storyId): - return ("inputReplyToStory", [("peer", peer as Any), ("storyId", storyId as Any)]) - } - } - - public static func parse_inputReplyToMessage(_ reader: BufferReader) -> InputReplyTo? { - var _1: Int32? - _1 = reader.readInt32() - var _2: Int32? - _2 = reader.readInt32() - var _3: Int32? - if Int(_1!) & Int(1 << 0) != 0 {_3 = reader.readInt32() } - var _4: Api.InputPeer? - if Int(_1!) & Int(1 << 1) != 0 {if let signature = reader.readInt32() { - _4 = Api.parse(reader, signature: signature) as? Api.InputPeer - } } - var _5: String? - if Int(_1!) & Int(1 << 2) != 0 {_5 = parseString(reader) } - var _6: [Api.MessageEntity]? - if Int(_1!) & Int(1 << 3) != 0 {if let _ = reader.readInt32() { - _6 = Api.parseVector(reader, elementSignature: 0, elementType: Api.MessageEntity.self) - } } - var _7: Int32? - if Int(_1!) & Int(1 << 4) != 0 {_7 = reader.readInt32() } - let _c1 = _1 != nil - let _c2 = _2 != nil - let _c3 = (Int(_1!) & Int(1 << 0) == 0) || _3 != nil - let _c4 = (Int(_1!) & Int(1 << 1) == 0) || _4 != nil - let _c5 = (Int(_1!) & Int(1 << 2) == 0) || _5 != nil - let _c6 = (Int(_1!) & Int(1 << 3) == 0) || _6 != nil - let _c7 = (Int(_1!) & Int(1 << 4) == 0) || _7 != nil - if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 { - return Api.InputReplyTo.inputReplyToMessage(flags: _1!, replyToMsgId: _2!, topMsgId: _3, replyToPeerId: _4, quoteText: _5, quoteEntities: _6, quoteOffset: _7) - } - else { - return nil - } - } - public static func parse_inputReplyToStory(_ reader: BufferReader) -> InputReplyTo? { - var _1: Api.InputPeer? - if let signature = reader.readInt32() { - _1 = Api.parse(reader, signature: signature) as? Api.InputPeer - } - var _2: Int32? - _2 = reader.readInt32() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputReplyTo.inputReplyToStory(peer: _1!, storyId: _2!) - } - else { - return nil - } - } - - } -} -public extension Api { - enum InputSecureFile: TypeConstructorDescription { - case inputSecureFile(id: Int64, accessHash: Int64) - case inputSecureFileUploaded(id: Int64, parts: Int32, md5Checksum: String, fileHash: Buffer, secret: Buffer) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputSecureFile(let id, let accessHash): - if boxed { - buffer.appendInt32(1399317950) - } - serializeInt64(id, buffer: buffer, boxed: false) - serializeInt64(accessHash, buffer: buffer, boxed: false) - break - case .inputSecureFileUploaded(let id, let parts, let md5Checksum, let fileHash, let secret): - if boxed { - buffer.appendInt32(859091184) - } - serializeInt64(id, buffer: buffer, boxed: false) - serializeInt32(parts, buffer: buffer, boxed: false) - serializeString(md5Checksum, buffer: buffer, boxed: false) - serializeBytes(fileHash, buffer: buffer, boxed: false) - serializeBytes(secret, buffer: buffer, boxed: false) - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputSecureFile(let id, let accessHash): - return ("inputSecureFile", [("id", id as Any), ("accessHash", accessHash as Any)]) - case .inputSecureFileUploaded(let id, let parts, let md5Checksum, let fileHash, let secret): - return ("inputSecureFileUploaded", [("id", id as Any), ("parts", parts as Any), ("md5Checksum", md5Checksum as Any), ("fileHash", fileHash as Any), ("secret", secret as Any)]) - } - } - - public static func parse_inputSecureFile(_ reader: BufferReader) -> InputSecureFile? { - var _1: Int64? - _1 = reader.readInt64() - var _2: Int64? - _2 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputSecureFile.inputSecureFile(id: _1!, accessHash: _2!) - } - else { - return nil - } - } - public static func parse_inputSecureFileUploaded(_ reader: BufferReader) -> InputSecureFile? { - var _1: Int64? - _1 = reader.readInt64() - var _2: Int32? - _2 = reader.readInt32() - var _3: String? - _3 = parseString(reader) - var _4: Buffer? - _4 = parseBytes(reader) - var _5: Buffer? - _5 = parseBytes(reader) - let _c1 = _1 != nil - let _c2 = _2 != nil - let _c3 = _3 != nil - let _c4 = _4 != nil - let _c5 = _5 != nil - if _c1 && _c2 && _c3 && _c4 && _c5 { - return Api.InputSecureFile.inputSecureFileUploaded(id: _1!, parts: _2!, md5Checksum: _3!, fileHash: _4!, secret: _5!) - } - else { - return nil - } - } - - } -} -public extension Api { - enum InputSecureValue: TypeConstructorDescription { - case inputSecureValue(flags: Int32, type: Api.SecureValueType, data: Api.SecureData?, frontSide: Api.InputSecureFile?, reverseSide: Api.InputSecureFile?, selfie: Api.InputSecureFile?, translation: [Api.InputSecureFile]?, files: [Api.InputSecureFile]?, plainData: Api.SecurePlainData?) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputSecureValue(let flags, let type, let data, let frontSide, let reverseSide, let selfie, let translation, let files, let plainData): - if boxed { - buffer.appendInt32(-618540889) - } - serializeInt32(flags, buffer: buffer, boxed: false) - type.serialize(buffer, true) - if Int(flags) & Int(1 << 0) != 0 {data!.serialize(buffer, true)} - if Int(flags) & Int(1 << 1) != 0 {frontSide!.serialize(buffer, true)} - if Int(flags) & Int(1 << 2) != 0 {reverseSide!.serialize(buffer, true)} - if Int(flags) & Int(1 << 3) != 0 {selfie!.serialize(buffer, true)} - if Int(flags) & Int(1 << 6) != 0 {buffer.appendInt32(481674261) - buffer.appendInt32(Int32(translation!.count)) - for item in translation! { - item.serialize(buffer, true) - }} - if Int(flags) & Int(1 << 4) != 0 {buffer.appendInt32(481674261) - buffer.appendInt32(Int32(files!.count)) - for item in files! { - item.serialize(buffer, true) - }} - if Int(flags) & Int(1 << 5) != 0 {plainData!.serialize(buffer, true)} - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputSecureValue(let flags, let type, let data, let frontSide, let reverseSide, let selfie, let translation, let files, let plainData): - return ("inputSecureValue", [("flags", flags as Any), ("type", type as Any), ("data", data as Any), ("frontSide", frontSide as Any), ("reverseSide", reverseSide as Any), ("selfie", selfie as Any), ("translation", translation as Any), ("files", files as Any), ("plainData", plainData as Any)]) - } - } - - public static func parse_inputSecureValue(_ reader: BufferReader) -> InputSecureValue? { - var _1: Int32? - _1 = reader.readInt32() - var _2: Api.SecureValueType? - if let signature = reader.readInt32() { - _2 = Api.parse(reader, signature: signature) as? Api.SecureValueType - } - var _3: Api.SecureData? - if Int(_1!) & Int(1 << 0) != 0 {if let signature = reader.readInt32() { - _3 = Api.parse(reader, signature: signature) as? Api.SecureData - } } - var _4: Api.InputSecureFile? - if Int(_1!) & Int(1 << 1) != 0 {if let signature = reader.readInt32() { - _4 = Api.parse(reader, signature: signature) as? Api.InputSecureFile - } } - var _5: Api.InputSecureFile? - if Int(_1!) & Int(1 << 2) != 0 {if let signature = reader.readInt32() { - _5 = Api.parse(reader, signature: signature) as? Api.InputSecureFile - } } - var _6: Api.InputSecureFile? - if Int(_1!) & Int(1 << 3) != 0 {if let signature = reader.readInt32() { - _6 = Api.parse(reader, signature: signature) as? Api.InputSecureFile - } } - var _7: [Api.InputSecureFile]? - if Int(_1!) & Int(1 << 6) != 0 {if let _ = reader.readInt32() { - _7 = Api.parseVector(reader, elementSignature: 0, elementType: Api.InputSecureFile.self) - } } - var _8: [Api.InputSecureFile]? - if Int(_1!) & Int(1 << 4) != 0 {if let _ = reader.readInt32() { - _8 = Api.parseVector(reader, elementSignature: 0, elementType: Api.InputSecureFile.self) - } } - var _9: Api.SecurePlainData? - if Int(_1!) & Int(1 << 5) != 0 {if let signature = reader.readInt32() { - _9 = Api.parse(reader, signature: signature) as? Api.SecurePlainData - } } - let _c1 = _1 != nil - let _c2 = _2 != nil - let _c3 = (Int(_1!) & Int(1 << 0) == 0) || _3 != nil - let _c4 = (Int(_1!) & Int(1 << 1) == 0) || _4 != nil - let _c5 = (Int(_1!) & Int(1 << 2) == 0) || _5 != nil - let _c6 = (Int(_1!) & Int(1 << 3) == 0) || _6 != nil - let _c7 = (Int(_1!) & Int(1 << 6) == 0) || _7 != nil - let _c8 = (Int(_1!) & Int(1 << 4) == 0) || _8 != nil - let _c9 = (Int(_1!) & Int(1 << 5) == 0) || _9 != nil - if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 && _c8 && _c9 { - return Api.InputSecureValue.inputSecureValue(flags: _1!, type: _2!, data: _3, frontSide: _4, reverseSide: _5, selfie: _6, translation: _7, files: _8, plainData: _9) - } - else { - return nil - } - } - - } -} diff --git a/submodules/TelegramApi/Sources/Api12.swift b/submodules/TelegramApi/Sources/Api12.swift index 91a4fdefa6..ac16a87240 100644 --- a/submodules/TelegramApi/Sources/Api12.swift +++ b/submodules/TelegramApi/Sources/Api12.swift @@ -1,3 +1,321 @@ +public extension Api { + enum InputQuickReplyShortcut: TypeConstructorDescription { + case inputQuickReplyShortcut(shortcut: String) + case inputQuickReplyShortcutId(shortcutId: Int32) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputQuickReplyShortcut(let shortcut): + if boxed { + buffer.appendInt32(609840449) + } + serializeString(shortcut, buffer: buffer, boxed: false) + break + case .inputQuickReplyShortcutId(let shortcutId): + if boxed { + buffer.appendInt32(18418929) + } + serializeInt32(shortcutId, buffer: buffer, boxed: false) + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputQuickReplyShortcut(let shortcut): + return ("inputQuickReplyShortcut", [("shortcut", shortcut as Any)]) + case .inputQuickReplyShortcutId(let shortcutId): + return ("inputQuickReplyShortcutId", [("shortcutId", shortcutId as Any)]) + } + } + + public static func parse_inputQuickReplyShortcut(_ reader: BufferReader) -> InputQuickReplyShortcut? { + var _1: String? + _1 = parseString(reader) + let _c1 = _1 != nil + if _c1 { + return Api.InputQuickReplyShortcut.inputQuickReplyShortcut(shortcut: _1!) + } + else { + return nil + } + } + public static func parse_inputQuickReplyShortcutId(_ reader: BufferReader) -> InputQuickReplyShortcut? { + var _1: Int32? + _1 = reader.readInt32() + let _c1 = _1 != nil + if _c1 { + return Api.InputQuickReplyShortcut.inputQuickReplyShortcutId(shortcutId: _1!) + } + else { + return nil + } + } + + } +} +public extension Api { + indirect enum InputReplyTo: TypeConstructorDescription { + case inputReplyToMessage(flags: Int32, replyToMsgId: Int32, topMsgId: Int32?, replyToPeerId: Api.InputPeer?, quoteText: String?, quoteEntities: [Api.MessageEntity]?, quoteOffset: Int32?) + case inputReplyToStory(peer: Api.InputPeer, storyId: Int32) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputReplyToMessage(let flags, let replyToMsgId, let topMsgId, let replyToPeerId, let quoteText, let quoteEntities, let quoteOffset): + if boxed { + buffer.appendInt32(583071445) + } + serializeInt32(flags, buffer: buffer, boxed: false) + serializeInt32(replyToMsgId, buffer: buffer, boxed: false) + if Int(flags) & Int(1 << 0) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)} + if Int(flags) & Int(1 << 1) != 0 {replyToPeerId!.serialize(buffer, true)} + if Int(flags) & Int(1 << 2) != 0 {serializeString(quoteText!, buffer: buffer, boxed: false)} + if Int(flags) & Int(1 << 3) != 0 {buffer.appendInt32(481674261) + buffer.appendInt32(Int32(quoteEntities!.count)) + for item in quoteEntities! { + item.serialize(buffer, true) + }} + if Int(flags) & Int(1 << 4) != 0 {serializeInt32(quoteOffset!, buffer: buffer, boxed: false)} + break + case .inputReplyToStory(let peer, let storyId): + if boxed { + buffer.appendInt32(1484862010) + } + peer.serialize(buffer, true) + serializeInt32(storyId, buffer: buffer, boxed: false) + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputReplyToMessage(let flags, let replyToMsgId, let topMsgId, let replyToPeerId, let quoteText, let quoteEntities, let quoteOffset): + return ("inputReplyToMessage", [("flags", flags as Any), ("replyToMsgId", replyToMsgId as Any), ("topMsgId", topMsgId as Any), ("replyToPeerId", replyToPeerId as Any), ("quoteText", quoteText as Any), ("quoteEntities", quoteEntities as Any), ("quoteOffset", quoteOffset as Any)]) + case .inputReplyToStory(let peer, let storyId): + return ("inputReplyToStory", [("peer", peer as Any), ("storyId", storyId as Any)]) + } + } + + public static func parse_inputReplyToMessage(_ reader: BufferReader) -> InputReplyTo? { + var _1: Int32? + _1 = reader.readInt32() + var _2: Int32? + _2 = reader.readInt32() + var _3: Int32? + if Int(_1!) & Int(1 << 0) != 0 {_3 = reader.readInt32() } + var _4: Api.InputPeer? + if Int(_1!) & Int(1 << 1) != 0 {if let signature = reader.readInt32() { + _4 = Api.parse(reader, signature: signature) as? Api.InputPeer + } } + var _5: String? + if Int(_1!) & Int(1 << 2) != 0 {_5 = parseString(reader) } + var _6: [Api.MessageEntity]? + if Int(_1!) & Int(1 << 3) != 0 {if let _ = reader.readInt32() { + _6 = Api.parseVector(reader, elementSignature: 0, elementType: Api.MessageEntity.self) + } } + var _7: Int32? + if Int(_1!) & Int(1 << 4) != 0 {_7 = reader.readInt32() } + let _c1 = _1 != nil + let _c2 = _2 != nil + let _c3 = (Int(_1!) & Int(1 << 0) == 0) || _3 != nil + let _c4 = (Int(_1!) & Int(1 << 1) == 0) || _4 != nil + let _c5 = (Int(_1!) & Int(1 << 2) == 0) || _5 != nil + let _c6 = (Int(_1!) & Int(1 << 3) == 0) || _6 != nil + let _c7 = (Int(_1!) & Int(1 << 4) == 0) || _7 != nil + if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 { + return Api.InputReplyTo.inputReplyToMessage(flags: _1!, replyToMsgId: _2!, topMsgId: _3, replyToPeerId: _4, quoteText: _5, quoteEntities: _6, quoteOffset: _7) + } + else { + return nil + } + } + public static func parse_inputReplyToStory(_ reader: BufferReader) -> InputReplyTo? { + var _1: Api.InputPeer? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputPeer + } + var _2: Int32? + _2 = reader.readInt32() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputReplyTo.inputReplyToStory(peer: _1!, storyId: _2!) + } + else { + return nil + } + } + + } +} +public extension Api { + enum InputSecureFile: TypeConstructorDescription { + case inputSecureFile(id: Int64, accessHash: Int64) + case inputSecureFileUploaded(id: Int64, parts: Int32, md5Checksum: String, fileHash: Buffer, secret: Buffer) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputSecureFile(let id, let accessHash): + if boxed { + buffer.appendInt32(1399317950) + } + serializeInt64(id, buffer: buffer, boxed: false) + serializeInt64(accessHash, buffer: buffer, boxed: false) + break + case .inputSecureFileUploaded(let id, let parts, let md5Checksum, let fileHash, let secret): + if boxed { + buffer.appendInt32(859091184) + } + serializeInt64(id, buffer: buffer, boxed: false) + serializeInt32(parts, buffer: buffer, boxed: false) + serializeString(md5Checksum, buffer: buffer, boxed: false) + serializeBytes(fileHash, buffer: buffer, boxed: false) + serializeBytes(secret, buffer: buffer, boxed: false) + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputSecureFile(let id, let accessHash): + return ("inputSecureFile", [("id", id as Any), ("accessHash", accessHash as Any)]) + case .inputSecureFileUploaded(let id, let parts, let md5Checksum, let fileHash, let secret): + return ("inputSecureFileUploaded", [("id", id as Any), ("parts", parts as Any), ("md5Checksum", md5Checksum as Any), ("fileHash", fileHash as Any), ("secret", secret as Any)]) + } + } + + public static func parse_inputSecureFile(_ reader: BufferReader) -> InputSecureFile? { + var _1: Int64? + _1 = reader.readInt64() + var _2: Int64? + _2 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputSecureFile.inputSecureFile(id: _1!, accessHash: _2!) + } + else { + return nil + } + } + public static func parse_inputSecureFileUploaded(_ reader: BufferReader) -> InputSecureFile? { + var _1: Int64? + _1 = reader.readInt64() + var _2: Int32? + _2 = reader.readInt32() + var _3: String? + _3 = parseString(reader) + var _4: Buffer? + _4 = parseBytes(reader) + var _5: Buffer? + _5 = parseBytes(reader) + let _c1 = _1 != nil + let _c2 = _2 != nil + let _c3 = _3 != nil + let _c4 = _4 != nil + let _c5 = _5 != nil + if _c1 && _c2 && _c3 && _c4 && _c5 { + return Api.InputSecureFile.inputSecureFileUploaded(id: _1!, parts: _2!, md5Checksum: _3!, fileHash: _4!, secret: _5!) + } + else { + return nil + } + } + + } +} +public extension Api { + enum InputSecureValue: TypeConstructorDescription { + case inputSecureValue(flags: Int32, type: Api.SecureValueType, data: Api.SecureData?, frontSide: Api.InputSecureFile?, reverseSide: Api.InputSecureFile?, selfie: Api.InputSecureFile?, translation: [Api.InputSecureFile]?, files: [Api.InputSecureFile]?, plainData: Api.SecurePlainData?) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputSecureValue(let flags, let type, let data, let frontSide, let reverseSide, let selfie, let translation, let files, let plainData): + if boxed { + buffer.appendInt32(-618540889) + } + serializeInt32(flags, buffer: buffer, boxed: false) + type.serialize(buffer, true) + if Int(flags) & Int(1 << 0) != 0 {data!.serialize(buffer, true)} + if Int(flags) & Int(1 << 1) != 0 {frontSide!.serialize(buffer, true)} + if Int(flags) & Int(1 << 2) != 0 {reverseSide!.serialize(buffer, true)} + if Int(flags) & Int(1 << 3) != 0 {selfie!.serialize(buffer, true)} + if Int(flags) & Int(1 << 6) != 0 {buffer.appendInt32(481674261) + buffer.appendInt32(Int32(translation!.count)) + for item in translation! { + item.serialize(buffer, true) + }} + if Int(flags) & Int(1 << 4) != 0 {buffer.appendInt32(481674261) + buffer.appendInt32(Int32(files!.count)) + for item in files! { + item.serialize(buffer, true) + }} + if Int(flags) & Int(1 << 5) != 0 {plainData!.serialize(buffer, true)} + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputSecureValue(let flags, let type, let data, let frontSide, let reverseSide, let selfie, let translation, let files, let plainData): + return ("inputSecureValue", [("flags", flags as Any), ("type", type as Any), ("data", data as Any), ("frontSide", frontSide as Any), ("reverseSide", reverseSide as Any), ("selfie", selfie as Any), ("translation", translation as Any), ("files", files as Any), ("plainData", plainData as Any)]) + } + } + + public static func parse_inputSecureValue(_ reader: BufferReader) -> InputSecureValue? { + var _1: Int32? + _1 = reader.readInt32() + var _2: Api.SecureValueType? + if let signature = reader.readInt32() { + _2 = Api.parse(reader, signature: signature) as? Api.SecureValueType + } + var _3: Api.SecureData? + if Int(_1!) & Int(1 << 0) != 0 {if let signature = reader.readInt32() { + _3 = Api.parse(reader, signature: signature) as? Api.SecureData + } } + var _4: Api.InputSecureFile? + if Int(_1!) & Int(1 << 1) != 0 {if let signature = reader.readInt32() { + _4 = Api.parse(reader, signature: signature) as? Api.InputSecureFile + } } + var _5: Api.InputSecureFile? + if Int(_1!) & Int(1 << 2) != 0 {if let signature = reader.readInt32() { + _5 = Api.parse(reader, signature: signature) as? Api.InputSecureFile + } } + var _6: Api.InputSecureFile? + if Int(_1!) & Int(1 << 3) != 0 {if let signature = reader.readInt32() { + _6 = Api.parse(reader, signature: signature) as? Api.InputSecureFile + } } + var _7: [Api.InputSecureFile]? + if Int(_1!) & Int(1 << 6) != 0 {if let _ = reader.readInt32() { + _7 = Api.parseVector(reader, elementSignature: 0, elementType: Api.InputSecureFile.self) + } } + var _8: [Api.InputSecureFile]? + if Int(_1!) & Int(1 << 4) != 0 {if let _ = reader.readInt32() { + _8 = Api.parseVector(reader, elementSignature: 0, elementType: Api.InputSecureFile.self) + } } + var _9: Api.SecurePlainData? + if Int(_1!) & Int(1 << 5) != 0 {if let signature = reader.readInt32() { + _9 = Api.parse(reader, signature: signature) as? Api.SecurePlainData + } } + let _c1 = _1 != nil + let _c2 = _2 != nil + let _c3 = (Int(_1!) & Int(1 << 0) == 0) || _3 != nil + let _c4 = (Int(_1!) & Int(1 << 1) == 0) || _4 != nil + let _c5 = (Int(_1!) & Int(1 << 2) == 0) || _5 != nil + let _c6 = (Int(_1!) & Int(1 << 3) == 0) || _6 != nil + let _c7 = (Int(_1!) & Int(1 << 6) == 0) || _7 != nil + let _c8 = (Int(_1!) & Int(1 << 4) == 0) || _8 != nil + let _c9 = (Int(_1!) & Int(1 << 5) == 0) || _9 != nil + if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 && _c8 && _c9 { + return Api.InputSecureValue.inputSecureValue(flags: _1!, type: _2!, data: _3, frontSide: _4, reverseSide: _5, selfie: _6, translation: _7, files: _8, plainData: _9) + } + else { + return nil + } + } + + } +} public extension Api { indirect enum InputSingleMedia: TypeConstructorDescription { case inputSingleMedia(flags: Int32, media: Api.InputMedia, randomId: Int64, message: String, entities: [Api.MessageEntity]?) @@ -760,177 +1078,3 @@ public extension Api { } } -public extension Api { - indirect enum InputUser: TypeConstructorDescription { - case inputUser(userId: Int64, accessHash: Int64) - case inputUserEmpty - case inputUserFromMessage(peer: Api.InputPeer, msgId: Int32, userId: Int64) - case inputUserSelf - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputUser(let userId, let accessHash): - if boxed { - buffer.appendInt32(-233744186) - } - serializeInt64(userId, buffer: buffer, boxed: false) - serializeInt64(accessHash, buffer: buffer, boxed: false) - break - case .inputUserEmpty: - if boxed { - buffer.appendInt32(-1182234929) - } - - break - case .inputUserFromMessage(let peer, let msgId, let userId): - if boxed { - buffer.appendInt32(497305826) - } - peer.serialize(buffer, true) - serializeInt32(msgId, buffer: buffer, boxed: false) - serializeInt64(userId, buffer: buffer, boxed: false) - break - case .inputUserSelf: - if boxed { - buffer.appendInt32(-138301121) - } - - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputUser(let userId, let accessHash): - return ("inputUser", [("userId", userId as Any), ("accessHash", accessHash as Any)]) - case .inputUserEmpty: - return ("inputUserEmpty", []) - case .inputUserFromMessage(let peer, let msgId, let userId): - return ("inputUserFromMessage", [("peer", peer as Any), ("msgId", msgId as Any), ("userId", userId as Any)]) - case .inputUserSelf: - return ("inputUserSelf", []) - } - } - - public static func parse_inputUser(_ reader: BufferReader) -> InputUser? { - var _1: Int64? - _1 = reader.readInt64() - var _2: Int64? - _2 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputUser.inputUser(userId: _1!, accessHash: _2!) - } - else { - return nil - } - } - public static func parse_inputUserEmpty(_ reader: BufferReader) -> InputUser? { - return Api.InputUser.inputUserEmpty - } - public static func parse_inputUserFromMessage(_ reader: BufferReader) -> InputUser? { - var _1: Api.InputPeer? - if let signature = reader.readInt32() { - _1 = Api.parse(reader, signature: signature) as? Api.InputPeer - } - var _2: Int32? - _2 = reader.readInt32() - var _3: Int64? - _3 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - let _c3 = _3 != nil - if _c1 && _c2 && _c3 { - return Api.InputUser.inputUserFromMessage(peer: _1!, msgId: _2!, userId: _3!) - } - else { - return nil - } - } - public static func parse_inputUserSelf(_ reader: BufferReader) -> InputUser? { - return Api.InputUser.inputUserSelf - } - - } -} -public extension Api { - enum InputWallPaper: TypeConstructorDescription { - case inputWallPaper(id: Int64, accessHash: Int64) - case inputWallPaperNoFile(id: Int64) - case inputWallPaperSlug(slug: String) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputWallPaper(let id, let accessHash): - if boxed { - buffer.appendInt32(-433014407) - } - serializeInt64(id, buffer: buffer, boxed: false) - serializeInt64(accessHash, buffer: buffer, boxed: false) - break - case .inputWallPaperNoFile(let id): - if boxed { - buffer.appendInt32(-1770371538) - } - serializeInt64(id, buffer: buffer, boxed: false) - break - case .inputWallPaperSlug(let slug): - if boxed { - buffer.appendInt32(1913199744) - } - serializeString(slug, buffer: buffer, boxed: false) - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputWallPaper(let id, let accessHash): - return ("inputWallPaper", [("id", id as Any), ("accessHash", accessHash as Any)]) - case .inputWallPaperNoFile(let id): - return ("inputWallPaperNoFile", [("id", id as Any)]) - case .inputWallPaperSlug(let slug): - return ("inputWallPaperSlug", [("slug", slug as Any)]) - } - } - - public static func parse_inputWallPaper(_ reader: BufferReader) -> InputWallPaper? { - var _1: Int64? - _1 = reader.readInt64() - var _2: Int64? - _2 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputWallPaper.inputWallPaper(id: _1!, accessHash: _2!) - } - else { - return nil - } - } - public static func parse_inputWallPaperNoFile(_ reader: BufferReader) -> InputWallPaper? { - var _1: Int64? - _1 = reader.readInt64() - let _c1 = _1 != nil - if _c1 { - return Api.InputWallPaper.inputWallPaperNoFile(id: _1!) - } - else { - return nil - } - } - public static func parse_inputWallPaperSlug(_ reader: BufferReader) -> InputWallPaper? { - var _1: String? - _1 = parseString(reader) - let _c1 = _1 != nil - if _c1 { - return Api.InputWallPaper.inputWallPaperSlug(slug: _1!) - } - else { - return nil - } - } - - } -} diff --git a/submodules/TelegramApi/Sources/Api13.swift b/submodules/TelegramApi/Sources/Api13.swift index 81b087af3a..c66b7ed17b 100644 --- a/submodules/TelegramApi/Sources/Api13.swift +++ b/submodules/TelegramApi/Sources/Api13.swift @@ -1,3 +1,177 @@ +public extension Api { + indirect enum InputUser: TypeConstructorDescription { + case inputUser(userId: Int64, accessHash: Int64) + case inputUserEmpty + case inputUserFromMessage(peer: Api.InputPeer, msgId: Int32, userId: Int64) + case inputUserSelf + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputUser(let userId, let accessHash): + if boxed { + buffer.appendInt32(-233744186) + } + serializeInt64(userId, buffer: buffer, boxed: false) + serializeInt64(accessHash, buffer: buffer, boxed: false) + break + case .inputUserEmpty: + if boxed { + buffer.appendInt32(-1182234929) + } + + break + case .inputUserFromMessage(let peer, let msgId, let userId): + if boxed { + buffer.appendInt32(497305826) + } + peer.serialize(buffer, true) + serializeInt32(msgId, buffer: buffer, boxed: false) + serializeInt64(userId, buffer: buffer, boxed: false) + break + case .inputUserSelf: + if boxed { + buffer.appendInt32(-138301121) + } + + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputUser(let userId, let accessHash): + return ("inputUser", [("userId", userId as Any), ("accessHash", accessHash as Any)]) + case .inputUserEmpty: + return ("inputUserEmpty", []) + case .inputUserFromMessage(let peer, let msgId, let userId): + return ("inputUserFromMessage", [("peer", peer as Any), ("msgId", msgId as Any), ("userId", userId as Any)]) + case .inputUserSelf: + return ("inputUserSelf", []) + } + } + + public static func parse_inputUser(_ reader: BufferReader) -> InputUser? { + var _1: Int64? + _1 = reader.readInt64() + var _2: Int64? + _2 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputUser.inputUser(userId: _1!, accessHash: _2!) + } + else { + return nil + } + } + public static func parse_inputUserEmpty(_ reader: BufferReader) -> InputUser? { + return Api.InputUser.inputUserEmpty + } + public static func parse_inputUserFromMessage(_ reader: BufferReader) -> InputUser? { + var _1: Api.InputPeer? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputPeer + } + var _2: Int32? + _2 = reader.readInt32() + var _3: Int64? + _3 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + let _c3 = _3 != nil + if _c1 && _c2 && _c3 { + return Api.InputUser.inputUserFromMessage(peer: _1!, msgId: _2!, userId: _3!) + } + else { + return nil + } + } + public static func parse_inputUserSelf(_ reader: BufferReader) -> InputUser? { + return Api.InputUser.inputUserSelf + } + + } +} +public extension Api { + enum InputWallPaper: TypeConstructorDescription { + case inputWallPaper(id: Int64, accessHash: Int64) + case inputWallPaperNoFile(id: Int64) + case inputWallPaperSlug(slug: String) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .inputWallPaper(let id, let accessHash): + if boxed { + buffer.appendInt32(-433014407) + } + serializeInt64(id, buffer: buffer, boxed: false) + serializeInt64(accessHash, buffer: buffer, boxed: false) + break + case .inputWallPaperNoFile(let id): + if boxed { + buffer.appendInt32(-1770371538) + } + serializeInt64(id, buffer: buffer, boxed: false) + break + case .inputWallPaperSlug(let slug): + if boxed { + buffer.appendInt32(1913199744) + } + serializeString(slug, buffer: buffer, boxed: false) + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .inputWallPaper(let id, let accessHash): + return ("inputWallPaper", [("id", id as Any), ("accessHash", accessHash as Any)]) + case .inputWallPaperNoFile(let id): + return ("inputWallPaperNoFile", [("id", id as Any)]) + case .inputWallPaperSlug(let slug): + return ("inputWallPaperSlug", [("slug", slug as Any)]) + } + } + + public static func parse_inputWallPaper(_ reader: BufferReader) -> InputWallPaper? { + var _1: Int64? + _1 = reader.readInt64() + var _2: Int64? + _2 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.InputWallPaper.inputWallPaper(id: _1!, accessHash: _2!) + } + else { + return nil + } + } + public static func parse_inputWallPaperNoFile(_ reader: BufferReader) -> InputWallPaper? { + var _1: Int64? + _1 = reader.readInt64() + let _c1 = _1 != nil + if _c1 { + return Api.InputWallPaper.inputWallPaperNoFile(id: _1!) + } + else { + return nil + } + } + public static func parse_inputWallPaperSlug(_ reader: BufferReader) -> InputWallPaper? { + var _1: String? + _1 = parseString(reader) + let _c1 = _1 != nil + if _c1 { + return Api.InputWallPaper.inputWallPaperSlug(slug: _1!) + } + else { + return nil + } + } + + } +} public extension Api { enum InputWebDocument: TypeConstructorDescription { case inputWebDocument(url: String, size: Int32, mimeType: String, attributes: [Api.DocumentAttribute]) @@ -900,139 +1074,3 @@ public extension Api { } } -public extension Api { - enum KeyboardButtonRow: TypeConstructorDescription { - case keyboardButtonRow(buttons: [Api.KeyboardButton]) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .keyboardButtonRow(let buttons): - if boxed { - buffer.appendInt32(2002815875) - } - buffer.appendInt32(481674261) - buffer.appendInt32(Int32(buttons.count)) - for item in buttons { - item.serialize(buffer, true) - } - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .keyboardButtonRow(let buttons): - return ("keyboardButtonRow", [("buttons", buttons as Any)]) - } - } - - public static func parse_keyboardButtonRow(_ reader: BufferReader) -> KeyboardButtonRow? { - var _1: [Api.KeyboardButton]? - if let _ = reader.readInt32() { - _1 = Api.parseVector(reader, elementSignature: 0, elementType: Api.KeyboardButton.self) - } - let _c1 = _1 != nil - if _c1 { - return Api.KeyboardButtonRow.keyboardButtonRow(buttons: _1!) - } - else { - return nil - } - } - - } -} -public extension Api { - enum LabeledPrice: TypeConstructorDescription { - case labeledPrice(label: String, amount: Int64) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .labeledPrice(let label, let amount): - if boxed { - buffer.appendInt32(-886477832) - } - serializeString(label, buffer: buffer, boxed: false) - serializeInt64(amount, buffer: buffer, boxed: false) - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .labeledPrice(let label, let amount): - return ("labeledPrice", [("label", label as Any), ("amount", amount as Any)]) - } - } - - public static func parse_labeledPrice(_ reader: BufferReader) -> LabeledPrice? { - var _1: String? - _1 = parseString(reader) - var _2: Int64? - _2 = reader.readInt64() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.LabeledPrice.labeledPrice(label: _1!, amount: _2!) - } - else { - return nil - } - } - - } -} -public extension Api { - enum LangPackDifference: TypeConstructorDescription { - case langPackDifference(langCode: String, fromVersion: Int32, version: Int32, strings: [Api.LangPackString]) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .langPackDifference(let langCode, let fromVersion, let version, let strings): - if boxed { - buffer.appendInt32(-209337866) - } - serializeString(langCode, buffer: buffer, boxed: false) - serializeInt32(fromVersion, buffer: buffer, boxed: false) - serializeInt32(version, buffer: buffer, boxed: false) - buffer.appendInt32(481674261) - buffer.appendInt32(Int32(strings.count)) - for item in strings { - item.serialize(buffer, true) - } - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .langPackDifference(let langCode, let fromVersion, let version, let strings): - return ("langPackDifference", [("langCode", langCode as Any), ("fromVersion", fromVersion as Any), ("version", version as Any), ("strings", strings as Any)]) - } - } - - public static func parse_langPackDifference(_ reader: BufferReader) -> LangPackDifference? { - var _1: String? - _1 = parseString(reader) - var _2: Int32? - _2 = reader.readInt32() - var _3: Int32? - _3 = reader.readInt32() - var _4: [Api.LangPackString]? - if let _ = reader.readInt32() { - _4 = Api.parseVector(reader, elementSignature: 0, elementType: Api.LangPackString.self) - } - let _c1 = _1 != nil - let _c2 = _2 != nil - let _c3 = _3 != nil - let _c4 = _4 != nil - if _c1 && _c2 && _c3 && _c4 { - return Api.LangPackDifference.langPackDifference(langCode: _1!, fromVersion: _2!, version: _3!, strings: _4!) - } - else { - return nil - } - } - - } -} diff --git a/submodules/TelegramApi/Sources/Api14.swift b/submodules/TelegramApi/Sources/Api14.swift index d7f64bdd25..6bdd0446fe 100644 --- a/submodules/TelegramApi/Sources/Api14.swift +++ b/submodules/TelegramApi/Sources/Api14.swift @@ -1,3 +1,139 @@ +public extension Api { + enum KeyboardButtonRow: TypeConstructorDescription { + case keyboardButtonRow(buttons: [Api.KeyboardButton]) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .keyboardButtonRow(let buttons): + if boxed { + buffer.appendInt32(2002815875) + } + buffer.appendInt32(481674261) + buffer.appendInt32(Int32(buttons.count)) + for item in buttons { + item.serialize(buffer, true) + } + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .keyboardButtonRow(let buttons): + return ("keyboardButtonRow", [("buttons", buttons as Any)]) + } + } + + public static func parse_keyboardButtonRow(_ reader: BufferReader) -> KeyboardButtonRow? { + var _1: [Api.KeyboardButton]? + if let _ = reader.readInt32() { + _1 = Api.parseVector(reader, elementSignature: 0, elementType: Api.KeyboardButton.self) + } + let _c1 = _1 != nil + if _c1 { + return Api.KeyboardButtonRow.keyboardButtonRow(buttons: _1!) + } + else { + return nil + } + } + + } +} +public extension Api { + enum LabeledPrice: TypeConstructorDescription { + case labeledPrice(label: String, amount: Int64) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .labeledPrice(let label, let amount): + if boxed { + buffer.appendInt32(-886477832) + } + serializeString(label, buffer: buffer, boxed: false) + serializeInt64(amount, buffer: buffer, boxed: false) + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .labeledPrice(let label, let amount): + return ("labeledPrice", [("label", label as Any), ("amount", amount as Any)]) + } + } + + public static func parse_labeledPrice(_ reader: BufferReader) -> LabeledPrice? { + var _1: String? + _1 = parseString(reader) + var _2: Int64? + _2 = reader.readInt64() + let _c1 = _1 != nil + let _c2 = _2 != nil + if _c1 && _c2 { + return Api.LabeledPrice.labeledPrice(label: _1!, amount: _2!) + } + else { + return nil + } + } + + } +} +public extension Api { + enum LangPackDifference: TypeConstructorDescription { + case langPackDifference(langCode: String, fromVersion: Int32, version: Int32, strings: [Api.LangPackString]) + + public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { + switch self { + case .langPackDifference(let langCode, let fromVersion, let version, let strings): + if boxed { + buffer.appendInt32(-209337866) + } + serializeString(langCode, buffer: buffer, boxed: false) + serializeInt32(fromVersion, buffer: buffer, boxed: false) + serializeInt32(version, buffer: buffer, boxed: false) + buffer.appendInt32(481674261) + buffer.appendInt32(Int32(strings.count)) + for item in strings { + item.serialize(buffer, true) + } + break + } + } + + public func descriptionFields() -> (String, [(String, Any)]) { + switch self { + case .langPackDifference(let langCode, let fromVersion, let version, let strings): + return ("langPackDifference", [("langCode", langCode as Any), ("fromVersion", fromVersion as Any), ("version", version as Any), ("strings", strings as Any)]) + } + } + + public static func parse_langPackDifference(_ reader: BufferReader) -> LangPackDifference? { + var _1: String? + _1 = parseString(reader) + var _2: Int32? + _2 = reader.readInt32() + var _3: Int32? + _3 = reader.readInt32() + var _4: [Api.LangPackString]? + if let _ = reader.readInt32() { + _4 = Api.parseVector(reader, elementSignature: 0, elementType: Api.LangPackString.self) + } + let _c1 = _1 != nil + let _c2 = _2 != nil + let _c3 = _3 != nil + let _c4 = _4 != nil + if _c1 && _c2 && _c3 && _c4 { + return Api.LangPackDifference.langPackDifference(langCode: _1!, fromVersion: _2!, version: _3!, strings: _4!) + } + else { + return nil + } + } + + } +} public extension Api { enum LangPackLanguage: TypeConstructorDescription { case langPackLanguage(flags: Int32, name: String, nativeName: String, langCode: String, baseLangCode: String?, pluralCode: String, stringsCount: Int32, translatedCount: Int32, translationsUrl: String) diff --git a/submodules/TelegramApi/Sources/Api9.swift b/submodules/TelegramApi/Sources/Api9.swift index 85225552db..4ef5bacfdd 100644 --- a/submodules/TelegramApi/Sources/Api9.swift +++ b/submodules/TelegramApi/Sources/Api9.swift @@ -412,6 +412,7 @@ public extension Api { enum InputFile: TypeConstructorDescription { case inputFile(id: Int64, parts: Int32, name: String, md5Checksum: String) case inputFileBig(id: Int64, parts: Int32, name: String) + case inputFileStoryDocument(id: Api.InputDocument) public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { switch self { @@ -432,6 +433,12 @@ public extension Api { serializeInt32(parts, buffer: buffer, boxed: false) serializeString(name, buffer: buffer, boxed: false) break + case .inputFileStoryDocument(let id): + if boxed { + buffer.appendInt32(1658620744) + } + id.serialize(buffer, true) + break } } @@ -441,6 +448,8 @@ public extension Api { return ("inputFile", [("id", id as Any), ("parts", parts as Any), ("name", name as Any), ("md5Checksum", md5Checksum as Any)]) case .inputFileBig(let id, let parts, let name): return ("inputFileBig", [("id", id as Any), ("parts", parts as Any), ("name", name as Any)]) + case .inputFileStoryDocument(let id): + return ("inputFileStoryDocument", [("id", id as Any)]) } } @@ -481,6 +490,19 @@ public extension Api { return nil } } + public static func parse_inputFileStoryDocument(_ reader: BufferReader) -> InputFile? { + var _1: Api.InputDocument? + if let signature = reader.readInt32() { + _1 = Api.parse(reader, signature: signature) as? Api.InputDocument + } + let _c1 = _1 != nil + if _c1 { + return Api.InputFile.inputFileStoryDocument(id: _1!) + } + else { + return nil + } + } } } @@ -1002,115 +1024,3 @@ public extension Api { } } -public extension Api { - indirect enum InputInvoice: TypeConstructorDescription { - case inputInvoiceMessage(peer: Api.InputPeer, msgId: Int32) - case inputInvoicePremiumGiftCode(purpose: Api.InputStorePaymentPurpose, option: Api.PremiumGiftCodeOption) - case inputInvoiceSlug(slug: String) - case inputInvoiceStars(purpose: Api.InputStorePaymentPurpose) - - public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) { - switch self { - case .inputInvoiceMessage(let peer, let msgId): - if boxed { - buffer.appendInt32(-977967015) - } - peer.serialize(buffer, true) - serializeInt32(msgId, buffer: buffer, boxed: false) - break - case .inputInvoicePremiumGiftCode(let purpose, let option): - if boxed { - buffer.appendInt32(-1734841331) - } - purpose.serialize(buffer, true) - option.serialize(buffer, true) - break - case .inputInvoiceSlug(let slug): - if boxed { - buffer.appendInt32(-1020867857) - } - serializeString(slug, buffer: buffer, boxed: false) - break - case .inputInvoiceStars(let purpose): - if boxed { - buffer.appendInt32(1710230755) - } - purpose.serialize(buffer, true) - break - } - } - - public func descriptionFields() -> (String, [(String, Any)]) { - switch self { - case .inputInvoiceMessage(let peer, let msgId): - return ("inputInvoiceMessage", [("peer", peer as Any), ("msgId", msgId as Any)]) - case .inputInvoicePremiumGiftCode(let purpose, let option): - return ("inputInvoicePremiumGiftCode", [("purpose", purpose as Any), ("option", option as Any)]) - case .inputInvoiceSlug(let slug): - return ("inputInvoiceSlug", [("slug", slug as Any)]) - case .inputInvoiceStars(let purpose): - return ("inputInvoiceStars", [("purpose", purpose as Any)]) - } - } - - public static func parse_inputInvoiceMessage(_ reader: BufferReader) -> InputInvoice? { - var _1: Api.InputPeer? - if let signature = reader.readInt32() { - _1 = Api.parse(reader, signature: signature) as? Api.InputPeer - } - var _2: Int32? - _2 = reader.readInt32() - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputInvoice.inputInvoiceMessage(peer: _1!, msgId: _2!) - } - else { - return nil - } - } - public static func parse_inputInvoicePremiumGiftCode(_ reader: BufferReader) -> InputInvoice? { - var _1: Api.InputStorePaymentPurpose? - if let signature = reader.readInt32() { - _1 = Api.parse(reader, signature: signature) as? Api.InputStorePaymentPurpose - } - var _2: Api.PremiumGiftCodeOption? - if let signature = reader.readInt32() { - _2 = Api.parse(reader, signature: signature) as? Api.PremiumGiftCodeOption - } - let _c1 = _1 != nil - let _c2 = _2 != nil - if _c1 && _c2 { - return Api.InputInvoice.inputInvoicePremiumGiftCode(purpose: _1!, option: _2!) - } - else { - return nil - } - } - public static func parse_inputInvoiceSlug(_ reader: BufferReader) -> InputInvoice? { - var _1: String? - _1 = parseString(reader) - let _c1 = _1 != nil - if _c1 { - return Api.InputInvoice.inputInvoiceSlug(slug: _1!) - } - else { - return nil - } - } - public static func parse_inputInvoiceStars(_ reader: BufferReader) -> InputInvoice? { - var _1: Api.InputStorePaymentPurpose? - if let signature = reader.readInt32() { - _1 = Api.parse(reader, signature: signature) as? Api.InputStorePaymentPurpose - } - let _c1 = _1 != nil - if _c1 { - return Api.InputInvoice.inputInvoiceStars(purpose: _1!) - } - else { - return nil - } - } - - } -} diff --git a/submodules/TelegramCore/Sources/State/ApplyUpdateMessage.swift b/submodules/TelegramCore/Sources/State/ApplyUpdateMessage.swift index edf64213f0..be44796999 100644 --- a/submodules/TelegramCore/Sources/State/ApplyUpdateMessage.swift +++ b/submodules/TelegramCore/Sources/State/ApplyUpdateMessage.swift @@ -14,7 +14,7 @@ private func copyOrMoveResourceData(from fromResource: MediaResource, to toResou } } -func applyMediaResourceChanges(from: Media, to: Media, postbox: Postbox, force: Bool) { +func applyMediaResourceChanges(from: Media, to: Media, postbox: Postbox, force: Bool, skipPreviews: Bool = false) { if let fromImage = from as? TelegramMediaImage, let toImage = to as? TelegramMediaImage { let fromSmallestRepresentation = smallestImageRepresentation(fromImage.representations) if let fromSmallestRepresentation = fromSmallestRepresentation, let toSmallestRepresentation = smallestImageRepresentation(toImage.representations) { @@ -32,11 +32,13 @@ func applyMediaResourceChanges(from: Media, to: Media, postbox: Postbox, force: } } } else if let fromFile = from as? TelegramMediaFile, let toFile = to as? TelegramMediaFile { - if let fromPreview = smallestImageRepresentation(fromFile.previewRepresentations), let toPreview = smallestImageRepresentation(toFile.previewRepresentations) { - copyOrMoveResourceData(from: fromPreview.resource, to: toPreview.resource, mediaBox: postbox.mediaBox) - } - if let fromVideoThumbnail = fromFile.videoThumbnails.first, let toVideoThumbnail = toFile.videoThumbnails.first, fromVideoThumbnail.resource.id != toVideoThumbnail.resource.id { - copyOrMoveResourceData(from: fromVideoThumbnail.resource, to: toVideoThumbnail.resource, mediaBox: postbox.mediaBox) + if !skipPreviews { + if let fromPreview = smallestImageRepresentation(fromFile.previewRepresentations), let toPreview = smallestImageRepresentation(toFile.previewRepresentations) { + copyOrMoveResourceData(from: fromPreview.resource, to: toPreview.resource, mediaBox: postbox.mediaBox) + } + if let fromVideoThumbnail = fromFile.videoThumbnails.first, let toVideoThumbnail = toFile.videoThumbnails.first, fromVideoThumbnail.resource.id != toVideoThumbnail.resource.id { + copyOrMoveResourceData(from: fromVideoThumbnail.resource, to: toVideoThumbnail.resource, mediaBox: postbox.mediaBox) + } } let videoFirstFrameFromPath = postbox.mediaBox.cachedRepresentationCompletePath(fromFile.resource.id, keepDuration: .general, representationId: "first-frame") let videoFirstFrameToPath = postbox.mediaBox.cachedRepresentationCompletePath(toFile.resource.id, keepDuration: .general, representationId: "first-frame") diff --git a/submodules/TelegramCore/Sources/TelegramEngine/Messages/Stories.swift b/submodules/TelegramCore/Sources/TelegramEngine/Messages/Stories.swift index 4c0b7329cb..0ff890c31b 100644 --- a/submodules/TelegramCore/Sources/TelegramEngine/Messages/Stories.swift +++ b/submodules/TelegramCore/Sources/TelegramEngine/Messages/Stories.swift @@ -1498,9 +1498,13 @@ func _internal_editStory(account: Account, peerId: PeerId, id: Int32, media: Eng return .single(.progress(progress.progress)) } + var updatingCoverTime = false let inputMedia: Api.InputMedia? if let result = result, case let .content(uploadedContent) = result, case let .media(media, _) = uploadedContent.content { inputMedia = media + } else if case let .existing(media) = media, let file = media as? TelegramMediaFile, let resource = file.resource as? CloudDocumentMediaResource { + inputMedia = .inputMediaUploadedDocument(flags: 0, file: .inputFileStoryDocument(id: .inputDocument(id: resource.fileId, accessHash: resource.accessHash, fileReference: Buffer(data: resource.fileReference))), thumb: nil, mimeType: file.mimeType, attributes: inputDocumentAttributesFromFileAttributes(file.attributes), stickers: nil, ttlSeconds: nil) + updatingCoverTime = true } else { inputMedia = nil } @@ -1566,7 +1570,7 @@ func _internal_editStory(account: Account, peerId: PeerId, id: Int32, media: Eng case let .storyItem(_, _, _, _, _, _, _, _, media, _, _, _, _): let (parsedMedia, _, _, _, _) = textMediaAndExpirationTimerFromApiMedia(media, account.peerId) if let parsedMedia = parsedMedia, let originalMedia = originalMedia { - applyMediaResourceChanges(from: originalMedia, to: parsedMedia, postbox: account.postbox, force: false) + applyMediaResourceChanges(from: originalMedia, to: parsedMedia, postbox: account.postbox, force: false, skipPreviews: updatingCoverTime) } default: break diff --git a/submodules/TelegramUI/Components/Chat/ChatEmptyNode/BUILD b/submodules/TelegramUI/Components/Chat/ChatEmptyNode/BUILD index 405bbcd734..b374c14152 100644 --- a/submodules/TelegramUI/Components/Chat/ChatEmptyNode/BUILD +++ b/submodules/TelegramUI/Components/Chat/ChatEmptyNode/BUILD @@ -31,6 +31,7 @@ swift_library( "//submodules/ReactionSelectionNode", "//submodules/TelegramUI/Components/Chat/ChatMediaInputStickerGridItem", "//submodules/PremiumUI", + "//submodules/TelegramUI/Components/LottieComponent", ], visibility = [ "//visibility:public", diff --git a/submodules/TelegramUI/Components/Chat/ChatEmptyNode/Sources/ChatEmptyNode.swift b/submodules/TelegramUI/Components/Chat/ChatEmptyNode/Sources/ChatEmptyNode.swift index d4388e4be2..7eccdcf765 100644 --- a/submodules/TelegramUI/Components/Chat/ChatEmptyNode/Sources/ChatEmptyNode.swift +++ b/submodules/TelegramUI/Components/Chat/ChatEmptyNode/Sources/ChatEmptyNode.swift @@ -22,6 +22,7 @@ import ReactionSelectionNode import ChatMediaInputStickerGridItem import UndoUI import PremiumUI +import LottieComponent private protocol ChatEmptyNodeContent { func updateLayout(interfaceState: ChatPresentationInterfaceState, subject: ChatEmptyNode.Subject, size: CGSize, transition: ContainedViewLayoutTransition) -> CGSize @@ -1203,7 +1204,7 @@ public final class ChatEmptyNodePremiumRequiredChatContent: ASDisplayNode, ChatE private let interaction: ChatPanelInterfaceInteraction? private let iconBackground: SimpleLayer - private let icon: UIImageView + private let icon = ComponentView() private let text = ComponentView() private let buttonTitle = ComponentView() private let button: HighlightTrackingButton @@ -1219,8 +1220,7 @@ public final class ChatEmptyNodePremiumRequiredChatContent: ASDisplayNode, ChatE self.interaction = interaction self.iconBackground = SimpleLayer() - self.icon = UIImageView(image: UIImage(bundleImageName: "Chat/Empty Chat/PremiumRequiredIcon")?.withRenderingMode(.alwaysTemplate)) - + self.button = HighlightTrackingButton() self.button.clipsToBounds = true @@ -1230,7 +1230,6 @@ public final class ChatEmptyNodePremiumRequiredChatContent: ASDisplayNode, ChatE super.init() self.layer.addSublayer(self.iconBackground) - self.view.addSubview(self.icon) if !self.isPremiumDisabled { self.view.addSubview(self.button) @@ -1330,11 +1329,28 @@ public final class ChatEmptyNodePremiumRequiredChatContent: ASDisplayNode, ChatE contentsHeight += iconBackgroundSize contentsHeight += iconTextSpacing - self.icon.tintColor = serviceColor.primaryText - if let image = self.icon.image { - transition.updateFrame(view: self.icon, frame: CGRect(origin: CGPoint(x: iconBackgroundFrame.minX + floor((iconBackgroundFrame.width - image.size.width) * 0.5), y: iconBackgroundFrame.minY + floor((iconBackgroundFrame.height - image.size.height) * 0.5)), size: image.size)) + let iconSize = self.icon.update( + transition: .immediate, + component: AnyComponent( + LottieComponent( + content: LottieComponent.AppBundleContent(name: "PremiumRequired"), + color: serviceColor.primaryText, + size: CGSize(width: 120.0, height: 120.0), + loop: true + ) + ), + environment: {}, + containerSize: CGSize(width: maxWidth - sideInset * 2.0, height: 500.0) + ) + let iconFrame = CGRect(origin: CGPoint(x: iconBackgroundFrame.minX + floor((iconBackgroundFrame.width - iconSize.width) * 0.5), y: iconBackgroundFrame.minY + floor((iconBackgroundFrame.height - iconSize.height) * 0.5)), size: iconSize) + if let iconView = self.icon.view { + if iconView.superview == nil { + iconView.isUserInteractionEnabled = false + self.view.addSubview(iconView) + } + iconView.frame = iconFrame } - + let textFrame = CGRect(origin: CGPoint(x: floor((contentsWidth - textSize.width) * 0.5), y: contentsHeight), size: textSize) if let textView = self.text.view { if textView.superview == nil { diff --git a/submodules/TelegramUI/Components/Chat/ChatMessageWebpageBubbleContentNode/Sources/ChatMessageWebpageBubbleContentNode.swift b/submodules/TelegramUI/Components/Chat/ChatMessageWebpageBubbleContentNode/Sources/ChatMessageWebpageBubbleContentNode.swift index 9d73bee8eb..a869fe1543 100644 --- a/submodules/TelegramUI/Components/Chat/ChatMessageWebpageBubbleContentNode/Sources/ChatMessageWebpageBubbleContentNode.swift +++ b/submodules/TelegramUI/Components/Chat/ChatMessageWebpageBubbleContentNode/Sources/ChatMessageWebpageBubbleContentNode.swift @@ -395,7 +395,11 @@ public final class ChatMessageWebpageBubbleContentNode: ChatMessageBubbleContent actionTitle = item.presentationData.strings.Conversation_ViewMessage } case "telegram_user": - actionTitle = item.presentationData.strings.Conversation_UserSendMessage + if webpage.displayUrl.contains("?profile") { + actionTitle = item.presentationData.strings.Conversation_OpenProfile + } else { + actionTitle = item.presentationData.strings.Conversation_UserSendMessage + } case "telegram_channel_request": actionTitle = item.presentationData.strings.Conversation_RequestToJoinChannel case "telegram_chat_request", "telegram_megagroup_request": diff --git a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/EditStories.swift b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/EditStories.swift index bd7d76ca41..9b259b362c 100644 --- a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/EditStories.swift +++ b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/EditStories.swift @@ -83,6 +83,17 @@ public extension MediaEditorScreen { transitionOut: nil ) + var videoPlaybackPosition = videoPlaybackPosition + if cover, case let .file(file) = storyItem.media { + videoPlaybackPosition = 0.0 + for attribute in file.attributes { + if case let .Video(_, _, _, _, coverTime) = attribute { + videoPlaybackPosition = coverTime + break + } + } + } + var updateProgressImpl: ((Float) -> Void)? let controller = MediaEditorScreen( context: context, @@ -248,7 +259,7 @@ public extension MediaEditorScreen { var updatedAttributes: [TelegramMediaFileAttribute] = [] for attribute in file.attributes { if case let .Video(duration, size, flags, preloadSize, _) = attribute { - updatedAttributes.append(.Video(duration: duration, size: size, flags: flags, preloadSize: preloadSize, coverTime: updatedCoverTimestamp)) + updatedAttributes.append(.Video(duration: duration, size: size, flags: flags, preloadSize: preloadSize, coverTime: min(duration, updatedCoverTimestamp))) } else { updatedAttributes.append(attribute) } diff --git a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift index 49f044c0b2..49c5a40cff 100644 --- a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift +++ b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift @@ -2945,7 +2945,11 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate let mediaEditor = MediaEditor(context: self.context, mode: isStickerEditor ? .sticker : .default, subject: effectiveSubject.editorSubject, values: initialValues, hasHistogram: true) if let initialVideoPosition = controller.initialVideoPosition { - mediaEditor.seek(initialVideoPosition, andPlay: true) + if controller.isEditingStoryCover { + mediaEditor.setCoverImageTimestamp(initialVideoPosition) + } else { + mediaEditor.seek(initialVideoPosition, andPlay: true) + } } if case .message = subject, self.context.sharedContext.currentPresentationData.with({$0}).autoNightModeTriggered { mediaEditor.setNightTheme(true) @@ -6293,7 +6297,7 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate let content: UndoOverlayContent = .info( title: nil, - text: presentationData.strings.Story_Editor_TooltipWeatherLimitText.string, + text: presentationData.strings.Story_Editor_TooltipWeatherLimitText, timeout: nil, customUndoText: nil ) diff --git a/submodules/TelegramUI/Resources/Animations/PremiumRequired.tgs b/submodules/TelegramUI/Resources/Animations/PremiumRequired.tgs new file mode 100644 index 0000000000000000000000000000000000000000..036e8ac4d375fecd954e2748401363c87fd3de19 GIT binary patch literal 1676 zcmV;726OoziwFpHH>G6&18rq9s4B`b!4xCM$DLBu6FoEgsX4M~5gK312N6G{tJ z)zxiVU3ytpn|*bOW`{;aeEd~iI;HDsUD}5&R{gZw?k_Y}-Q3(T`LgR)hpxK3TGZA3 z^7E>t?=Qpj<^ip$tHbB&(iR@?KDS(~JDShq^%zE<17-6Iz8TJFv;W~Teaq(Dx zlX2DDx{Vc4W3y36XU5G25lyHu8N41wne>RVDWp@%xwX$-RiCBHVErhR!>AUG-&1+gka6lvCrK@#GnUW?Om4#%3dlN{ zYM_uMzoLcC@bZM@87_Tj97!+A^}6*cPlRWdJ;zKim)#W2nqIZDxD0^<6^zH~V1-sD zqh?TWS|Z2zTp*o=L_lx!M3IDqSK(aEP>wQ~0s_gSC=z?^xCUFqhh)40BMT2Wg0%u! z%7CGgs2oz4xbOi&1LA^ZQ0$-&kT)?$7b*o65KBdu_pOphi6R=UaW8nx86zjANbdBJ z_X*V!J1?YJ=y-~8nU5jVQdWu4pGY+2QK&>@a}c~{|D_bpVAF@rvG}51uU%m?6`xtk z>G|kbcvF;XdhO0(GlGsp&O&J%sB&?EKNCD1J;d0IDH_aC{DUJeDmn#N!W6|-9iifk zs~wnY4mE@lA_Ip3ttc*VP-210{QQrKwj*?t1IHwt(W`qAVrUI)t@bnyPHFK zp~|mzJkhPI;a%)*{vuZ53VVis988t7Lq|8cPK11E3K{s2OM$^(QA#2Aw9VGDnkr6I zHe-HBiu%T6+X0l3z9|)0QGjx|g43^|yEM_NycQ;;JVD<~pb4yzU&B3!lTg9qKGmB5Ht*Y?ah!yB{$LaE@wLmxz7@^ zRnT`R$<&Yej*d^w+Kj4BLcToN_ObhRd01c2L-qCny&r!5@t2D~R@aAJd-0A!`J%aa z)9ya(L9o6lS2>13is9S)iuul7b8G&$7*pgcY31^(Gs6GuAf#KKnsL2@ zes7l#-R-X3GQP~7__5oEJwLx+muL85%7QB=Y Date: Fri, 26 Jul 2024 21:41:03 +0200 Subject: [PATCH 2/8] Various improvements --- .../Telegram-iOS/en.lproj/Localizable.strings | 2 + .../AccountContext/Sources/Premium.swift | 5 ++ .../TelegramEngine/Data/PeersData.swift | 82 ++++++++++++------ .../Sources/StarsTransactionsScreen.swift | 6 +- .../Privacy.imageset/Contents.json | 12 +++ .../Context Menu/Privacy.imageset/privacy.pdf | Bin 0 -> 2542 bytes .../WebUI/Sources/WebAppController.swift | 46 +++++++--- 7 files changed, 110 insertions(+), 43 deletions(-) create mode 100644 submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json create mode 100644 submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/privacy.pdf diff --git a/Telegram/Telegram-iOS/en.lproj/Localizable.strings b/Telegram/Telegram-iOS/en.lproj/Localizable.strings index f55b0b7fea..becb070a68 100644 --- a/Telegram/Telegram-iOS/en.lproj/Localizable.strings +++ b/Telegram/Telegram-iOS/en.lproj/Localizable.strings @@ -12668,3 +12668,5 @@ Sorry for the inconvenience."; "WebApp.PrivacyPolicy" = "Privacy Policy"; "Conversation.OpenProfile" = "OPEN PROFILE"; + +"Stars.Intro.GiftStars" = "Gift Stars to Friends"; diff --git a/submodules/AccountContext/Sources/Premium.swift b/submodules/AccountContext/Sources/Premium.swift index 821887ec3f..52ee4ce8d4 100644 --- a/submodules/AccountContext/Sources/Premium.swift +++ b/submodules/AccountContext/Sources/Premium.swift @@ -139,6 +139,7 @@ public struct PremiumConfiguration { showPremiumGiftInAttachMenu: false, showPremiumGiftInTextField: false, giveawayGiftsPurchaseAvailable: false, + starsGiftsPurchaseAvailable: false, boostsPerGiftCount: 3, audioTransciptionTrialMaxDuration: 300, audioTransciptionTrialCount: 2, @@ -165,6 +166,7 @@ public struct PremiumConfiguration { public let showPremiumGiftInAttachMenu: Bool public let showPremiumGiftInTextField: Bool public let giveawayGiftsPurchaseAvailable: Bool + public let starsGiftsPurchaseAvailable: Bool public let boostsPerGiftCount: Int32 public let audioTransciptionTrialMaxDuration: Int32 public let audioTransciptionTrialCount: Int32 @@ -190,6 +192,7 @@ public struct PremiumConfiguration { showPremiumGiftInAttachMenu: Bool, showPremiumGiftInTextField: Bool, giveawayGiftsPurchaseAvailable: Bool, + starsGiftsPurchaseAvailable: Bool, boostsPerGiftCount: Int32, audioTransciptionTrialMaxDuration: Int32, audioTransciptionTrialCount: Int32, @@ -214,6 +217,7 @@ public struct PremiumConfiguration { self.showPremiumGiftInAttachMenu = showPremiumGiftInAttachMenu self.showPremiumGiftInTextField = showPremiumGiftInTextField self.giveawayGiftsPurchaseAvailable = giveawayGiftsPurchaseAvailable + self.starsGiftsPurchaseAvailable = starsGiftsPurchaseAvailable self.boostsPerGiftCount = boostsPerGiftCount self.audioTransciptionTrialMaxDuration = audioTransciptionTrialMaxDuration self.audioTransciptionTrialCount = audioTransciptionTrialCount @@ -246,6 +250,7 @@ public struct PremiumConfiguration { showPremiumGiftInAttachMenu: data["premium_gift_attach_menu_icon"] as? Bool ?? defaultValue.showPremiumGiftInAttachMenu, showPremiumGiftInTextField: data["premium_gift_text_field_icon"] as? Bool ?? defaultValue.showPremiumGiftInTextField, giveawayGiftsPurchaseAvailable: data["giveaway_gifts_purchase_available"] as? Bool ?? defaultValue.giveawayGiftsPurchaseAvailable, + starsGiftsPurchaseAvailable: data["stars_gifts_enabled"] as? Bool ?? defaultValue.starsGiftsPurchaseAvailable, boostsPerGiftCount: get(data["boosts_per_sent_gift"]) ?? defaultValue.boostsPerGiftCount, audioTransciptionTrialMaxDuration: get(data["transcribe_audio_trial_duration_max"]) ?? defaultValue.audioTransciptionTrialMaxDuration, audioTransciptionTrialCount: get(data["transcribe_audio_trial_weekly_number"]) ?? defaultValue.audioTransciptionTrialCount, diff --git a/submodules/TelegramCore/Sources/TelegramEngine/Data/PeersData.swift b/submodules/TelegramCore/Sources/TelegramEngine/Data/PeersData.swift index 74c34c1c0b..4c6c5e094d 100644 --- a/submodules/TelegramCore/Sources/TelegramEngine/Data/PeersData.swift +++ b/submodules/TelegramCore/Sources/TelegramEngine/Data/PeersData.swift @@ -2076,32 +2076,60 @@ public extension TelegramEngine.EngineData.Item { } } -public struct BotMenu: TelegramEngineDataItem, TelegramEngineMapKeyDataItem, PostboxViewDataItem { -public typealias Result = Optional - -fileprivate var id: EnginePeer.Id -public var mapKey: EnginePeer.Id { -return self.id -} - -public init(id: EnginePeer.Id) { -self.id = id -} - -var key: PostboxViewKey { -return .cachedPeerData(peerId: self.id) -} - -func extract(view: PostboxView) -> Result { -guard let view = view as? CachedPeerDataView else { -preconditionFailure() -} -if let cachedData = view.cachedPeerData as? CachedUserData { -return cachedData.botInfo?.menuButton -} else { -return nil -} -} -} + public struct BotMenu: TelegramEngineDataItem, TelegramEngineMapKeyDataItem, PostboxViewDataItem { + public typealias Result = Optional + + fileprivate var id: EnginePeer.Id + public var mapKey: EnginePeer.Id { + return self.id + } + + public init(id: EnginePeer.Id) { + self.id = id + } + + var key: PostboxViewKey { + return .cachedPeerData(peerId: self.id) + } + + func extract(view: PostboxView) -> Result { + guard let view = view as? CachedPeerDataView else { + preconditionFailure() + } + if let cachedData = view.cachedPeerData as? CachedUserData { + return cachedData.botInfo?.menuButton + } else { + return nil + } + } + } + + public struct BotCommands: TelegramEngineDataItem, TelegramEngineMapKeyDataItem, PostboxViewDataItem { + public typealias Result = Optional<[BotCommand]> + + fileprivate var id: EnginePeer.Id + public var mapKey: EnginePeer.Id { + return self.id + } + + public init(id: EnginePeer.Id) { + self.id = id + } + + var key: PostboxViewKey { + return .cachedPeerData(peerId: self.id) + } + + func extract(view: PostboxView) -> Result { + guard let view = view as? CachedPeerDataView else { + preconditionFailure() + } + if let cachedData = view.cachedPeerData as? CachedUserData { + return cachedData.botInfo?.commands + } else { + return nil + } + } + } } } diff --git a/submodules/TelegramUI/Components/Stars/StarsTransactionsScreen/Sources/StarsTransactionsScreen.swift b/submodules/TelegramUI/Components/Stars/StarsTransactionsScreen/Sources/StarsTransactionsScreen.swift index 04df414332..e6329ee119 100644 --- a/submodules/TelegramUI/Components/Stars/StarsTransactionsScreen/Sources/StarsTransactionsScreen.swift +++ b/submodules/TelegramUI/Components/Stars/StarsTransactionsScreen/Sources/StarsTransactionsScreen.swift @@ -538,7 +538,7 @@ final class StarsTransactionsScreenComponent: Component { component.buy() }, buyAds: nil, - additionalAction: AnyComponent( + additionalAction: premiumConfiguration.starsGiftsPurchaseAvailable ? AnyComponent( Button( content: AnyComponent( HStack([ @@ -548,7 +548,7 @@ final class StarsTransactionsScreenComponent: Component { ), AnyComponentWithIdentity( id: "label", - component: AnyComponent(MultilineTextComponent(text: .plain(NSAttributedString(string: "Gift Stars to Friends", font: Font.regular(17.0), textColor: environment.theme.list.itemAccentColor)))) + component: AnyComponent(MultilineTextComponent(text: .plain(NSAttributedString(string: environment.strings.Stars_Intro_GiftStars, font: Font.regular(17.0), textColor: environment.theme.list.itemAccentColor)))) ) ], spacing: 6.0) @@ -557,7 +557,7 @@ final class StarsTransactionsScreenComponent: Component { component.gift() } ) - ) + ) : nil ) ))] )), diff --git a/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json b/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json new file mode 100644 index 0000000000..638a59cc88 --- /dev/null +++ b/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json @@ -0,0 +1,12 @@ +{ + "images" : [ + { + "filename" : "privacy.pdf", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/privacy.pdf b/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/privacy.pdf new file mode 100644 index 0000000000000000000000000000000000000000..e6d3dcbb39d0d4bc05755e10dcaa6c548e4c92d7 GIT binary patch literal 2542 zcmZWrXH-+^76qh8#Lyk8T!B!8kV2E*TPP9&h~TIJE)a!8lhCUa8Nft}R4GbPP#`o# zY;;8t1cr`RlD zDFh_?bABP{f8q#RLNFC10|?t-JQcJC{Yd^GJA-WqCy*FO4Fa^;;cje*U4cR+gZL0g z1UD_;nJ%j@lJd^b<`59FBf~#yM%jGafe!4k=c1kHFdr;iYxIHByt$vHIJYl-WJGzq zo?l>m`yBe^;|#(~%j`?shxPYQ-+r23%cvuK-9Pf>Rrf2yxN+9$n^*O02m9a7kz>N* zV%pA3BkB9j>tk1u=r?2O=B z^z-sbz@#-f7&^@8W-*r;^o-_0+Ba@DqJwZRU_wN@w&Y>gTq zXo4_83T9GFWg-I-$0)6d@(?6ytB&pOTe#5=JD0l{XyYSq)(jY{kH+hpaf)F016B+RWOpa$fZ z*)h3H^#qgMub$8g8A?q`U*(pg-(#6b~v$Y^C$N9g%1 zKHrEX4auej{-=Vq#z6t)a9w*75ow*<;#f4w*!oP~v4C_Lc!FBDi@1AaL7$@Z$)#$s zsU9c#bG z@Cnts@dwb(e1H2^*S9t7D1IW9vVY4Fs-QKY<)EU23sk!2AZFia50_xfvsKx-RFJIE zFjT1{uQXFW(z-SOiR?{_F1J7yUniZm3#U~2IcFwj_}l~a!DRjy>RSCYqFrQn#+?Im zN|A}5Rjoh2PvBZDza*de@xRbJcVNDrioGqvq5{>Iu%psx5E@GHWVUn=aQ`l^bFAt& zz1Fn==nVNr;ZYF>BmYsGu>2q1z47Q08Cdzo#$@=P(IiV#S)n``m za2zUGMzgrxOzSi4FEAuvqTG;Ya$F6b6@>E(lZ&w1UG!KwU8w_$;5pCh4WSO1^$ zK?0{W#Uvbx^BQ+yy;EHc=A@PNwkGkm?6V5w4SzQpX0Gh6Zudrg-l%$AM2kkZOzH2f zKqV?45xlVFRB4H-LcHI;zAu^*@Z;tQnX_LaYIPLuRa)Oon@Y=wO6V|}k-m-{mY-s( zT!m{htw&n8UcBz;i9e7X!Ji>{xsN)l;%SQRm=X85L6S@fd!Gi99V|L-*SMo3Pw^U`3c^q7Ita{|ohuhJ`to3mEf?TVUDoY?JT_Cv=79U-)*K?4*5>S!a#zoN2 z%?R*UbyafFglg!?T1AeB*+3irxV)ISQ`%$at!}vSWVR4mcrsb{-kdJh_3k}H+uf56LI-4+?(-9U#B8f@?eE$5&*zS?XKmg&258R+| zXV9O3wm0b(ESPhLuhcIO#y;%B>1yO1vneH0ULd+NTKXp)c?&-`5`zquA%o^CC-AB&4!%8 zek^W|JU47xn)bHz{wb4ij3}&;}_J5%~8_@s& literal 0 HcmV?d00001 diff --git a/submodules/WebUI/Sources/WebAppController.swift b/submodules/WebUI/Sources/WebAppController.swift index f6ecc633db..9b32c4a186 100644 --- a/submodules/WebUI/Sources/WebAppController.swift +++ b/submodules/WebUI/Sources/WebAppController.swift @@ -1987,7 +1987,12 @@ public final class WebAppController: ViewController, AttachmentContainable { @objc private func morePressed(node: ContextReferenceContentNode, gesture: ContextGesture?) { let context = self.context - let presentationData = self.presentationData + var presentationData = self.presentationData + if !presentationData.theme.overallDarkAppearance, let headerColor = self.controllerNode.headerColor { + if headerColor.lightness < 0.5 { + presentationData = presentationData.withUpdated(theme: defaultDarkPresentationTheme) + } + } let peerId = self.peerId let botId = self.botId @@ -1998,10 +2003,11 @@ public final class WebAppController: ViewController, AttachmentContainable { let items = combineLatest(queue: Queue.mainQueue(), context.engine.messages.attachMenuBots(), - context.engine.data.get(TelegramEngine.EngineData.Item.Peer.Peer(id: self.botId)) + context.engine.data.get(TelegramEngine.EngineData.Item.Peer.Peer(id: self.botId)), + context.engine.data.get(TelegramEngine.EngineData.Item.Peer.BotCommands(id: self.botId)) ) |> take(1) - |> map { [weak self] attachMenuBots, botPeer -> ContextController.Items in + |> map { [weak self] attachMenuBots, botPeer, botCommands -> ContextController.Items in var items: [ContextMenuItem] = [] let attachMenuBot = attachMenuBots.first(where: { $0.peer.id == botId && !$0.flags.contains(.notActivated) }) @@ -2068,15 +2074,7 @@ public final class WebAppController: ViewController, AttachmentContainable { self?.controllerNode.webView?.reload() }))) - -// items.append(.action(ContextMenuActionItem(text: presentationData.strings.WebApp_PrivacyPolicy, icon: { theme in -// return generateTintedImage(image: UIImage(bundleImageName: "Chat/Context Menu/Reload"), color: theme.contextMenu.primaryColor) -// }, action: { [weak self] c, _ in -// c?.dismiss(completion: nil) -// -// self?.controllerNode.webView?.reload() -// }))) - + items.append(.action(ContextMenuActionItem(text: presentationData.strings.WebApp_TermsOfUse, icon: { theme in return generateTintedImage(image: UIImage(bundleImageName: "Chat/Context Menu/Info"), color: theme.contextMenu.primaryColor) }, action: { [weak self] c, _ in @@ -2096,6 +2094,28 @@ public final class WebAppController: ViewController, AttachmentContainable { }) }))) + if let botCommands { + for command in botCommands { + if command.text == "privacy" { + items.append(.action(ContextMenuActionItem(text: presentationData.strings.WebApp_PrivacyPolicy, icon: { theme in + return generateTintedImage(image: UIImage(bundleImageName: "Chat/Context Menu/Privacy"), color: theme.contextMenu.primaryColor) + }, action: { [weak self] c, _ in + c?.dismiss(completion: nil) + + guard let self else { + return + } + let _ = enqueueMessages(account: self.context.account, peerId: self.botId, messages: [.message(text: "/privacy", attributes: [], inlineStickers: [:], mediaReference: nil, threadId: nil, replyToMessageId: nil, replyToStoryId: nil, localGroupingKey: nil, correlationId: nil, bubbleUpEmojiOrStickersets: [])]).startStandalone() + + if let botPeer, let navigationController = self.getNavigationController() { + (self.parentController() as? AttachmentController)?.minimizeIfNeeded() + self.context.sharedContext.navigateToChatController(NavigateToChatControllerParams(navigationController: navigationController, context: self.context, chatLocation: .peer(botPeer))) + } + }))) + } + } + } + if let _ = attachMenuBot, [.attachMenu, .settings, .generic].contains(source) { items.append(.action(ContextMenuActionItem(text: presentationData.strings.WebApp_RemoveBot, textColor: .destructive, icon: { theme in return generateTintedImage(image: UIImage(bundleImageName: "Chat/Context Menu/Delete"), color: theme.contextMenu.destructiveColor) @@ -2117,7 +2137,7 @@ public final class WebAppController: ViewController, AttachmentContainable { return ContextController.Items(content: .list(items)) } - let contextController = ContextController(presentationData: self.presentationData, source: .reference(WebAppContextReferenceContentSource(controller: self, sourceNode: node)), items: items, gesture: gesture) + let contextController = ContextController(presentationData: presentationData, source: .reference(WebAppContextReferenceContentSource(controller: self, sourceNode: node)), items: items, gesture: gesture) self.presentInGlobalOverlay(contextController) } From 9bb789dc7587b5dbed2291cc60be127d45b59b07 Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Fri, 26 Jul 2024 22:07:41 +0200 Subject: [PATCH 3/8] Various improvements --- .../Telegram-iOS/en.lproj/Localizable.strings | 2 +- .../WebBrowserSettingsController.swift | 2 +- .../Sources/MonetizationBalanceItem.swift | 4 ++-- .../Sources/StatsOverviewItem.swift | 24 +++++++++---------- .../Sources/TonFormat.swift | 16 +++++++++++-- .../Sources/StarsBalanceComponent.swift | 2 +- .../Sources/StarsOverviewItemComponent.swift | 3 ++- .../Sources/StarsUtils.swift | 6 ----- versions.json | 2 +- 9 files changed, 34 insertions(+), 27 deletions(-) delete mode 100644 submodules/TelegramUI/Components/Stars/StarsTransactionsScreen/Sources/StarsUtils.swift diff --git a/Telegram/Telegram-iOS/en.lproj/Localizable.strings b/Telegram/Telegram-iOS/en.lproj/Localizable.strings index becb070a68..ae9452a0bf 100644 --- a/Telegram/Telegram-iOS/en.lproj/Localizable.strings +++ b/Telegram/Telegram-iOS/en.lproj/Localizable.strings @@ -12571,7 +12571,7 @@ Sorry for the inconvenience."; "WebBrowser.AutoLogin.Info" = "Use your Telegram account to automatically log in to websites opened in the in-app browser."; "WebBrowser.ClearCookies" = "Clear Cookies"; -"WebBrowser.ClearCookies.Info" = "Delete all cookies and cache in the Telegram in-app browser. This action will sign you out of most websites."; +"WebBrowser.ClearCookies.Info" = "Delete all cookies in the Telegram in-app browser. This action will sign you out of most websites."; "WebBrowser.ClearCookies.Succeed" = "Cookies cleared."; "WebBrowser.Exceptions.Title" = "NEVER OPEN IN THE IN-APP BROWSER"; diff --git a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift index 455b8d430a..903f4697ab 100644 --- a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift +++ b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift @@ -250,7 +250,7 @@ private func webBrowserSettingsControllerEntries(context: AccountContext, presen if settings.defaultWebBrowser == nil { entries.append(.clearCookies(presentationData.theme, presentationData.strings.WebBrowser_ClearCookies)) - entries.append(.clearCache(presentationData.theme, presentationData.strings.WebBrowser_ClearCache)) +// entries.append(.clearCache(presentationData.theme, presentationData.strings.WebBrowser_ClearCache)) entries.append(.clearCookiesInfo(presentationData.theme, presentationData.strings.WebBrowser_ClearCookies_Info)) entries.append(.exceptionsHeader(presentationData.theme, presentationData.strings.WebBrowser_Exceptions_Title)) diff --git a/submodules/StatisticsUI/Sources/MonetizationBalanceItem.swift b/submodules/StatisticsUI/Sources/MonetizationBalanceItem.swift index 2686024892..01839afd73 100644 --- a/submodules/StatisticsUI/Sources/MonetizationBalanceItem.swift +++ b/submodules/StatisticsUI/Sources/MonetizationBalanceItem.swift @@ -178,10 +178,10 @@ final class MonetizationBalanceItemNode: ListViewItemNode, ItemListItemNode { if let stats = item.stats as? RevenueStats { let cryptoValue = formatTonAmountText(stats.balances.availableBalance, decimalSeparator: item.presentationData.dateTimeFormat.decimalSeparator) amountString = tonAmountAttributedString(cryptoValue, integralFont: integralFont, fractionalFont: fractionalFont, color: item.presentationData.theme.list.itemPrimaryTextColor) - value = stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate))" + value = stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))" } else if let stats = item.stats as? StarsRevenueStats { amountString = NSAttributedString(string: presentationStringsFormattedNumber(Int32(stats.balances.availableBalance), item.presentationData.dateTimeFormat.groupingSeparator), font: integralFont, textColor: item.presentationData.theme.list.itemPrimaryTextColor) - value = stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, divide: false, rate: stats.usdRate))" + value = stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, divide: false, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))" isStars = true } else { fatalError() diff --git a/submodules/StatisticsUI/Sources/StatsOverviewItem.swift b/submodules/StatisticsUI/Sources/StatsOverviewItem.swift index a635f7fe6b..7df6ea96f5 100644 --- a/submodules/StatisticsUI/Sources/StatsOverviewItem.swift +++ b/submodules/StatisticsUI/Sources/StatsOverviewItem.swift @@ -774,7 +774,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, formatTonAmountText(stats.balances.availableBalance, decimalSeparator: item.presentationData.dateTimeFormat.decimalSeparator), item.presentationData.strings.Monetization_StarsProceeds_Available, - (stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate))", .generic), + (stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .ton ) @@ -784,7 +784,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, formatTonAmountText(stats.balances.currentBalance, decimalSeparator: item.presentationData.dateTimeFormat.decimalSeparator), item.presentationData.strings.Monetization_StarsProceeds_Current, - (stats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.currentBalance, rate: stats.usdRate))", .generic), + (stats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.currentBalance, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .ton ) @@ -794,7 +794,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, formatTonAmountText(stats.balances.overallRevenue, decimalSeparator: item.presentationData.dateTimeFormat.decimalSeparator), item.presentationData.strings.Monetization_StarsProceeds_Total, - (stats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.overallRevenue, rate: stats.usdRate))", .generic), + (stats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.overallRevenue, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .ton ) @@ -804,7 +804,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, presentationStringsFormattedNumber(Int32(additionalStats.balances.availableBalance), item.presentationData.dateTimeFormat.groupingSeparator), " ", - (additionalStats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(additionalStats.balances.availableBalance, divide: false, rate: additionalStats.usdRate))", .generic), + (additionalStats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(additionalStats.balances.availableBalance, divide: false, rate: additionalStats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .stars ) @@ -814,7 +814,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, presentationStringsFormattedNumber(Int32(additionalStats.balances.currentBalance), item.presentationData.dateTimeFormat.groupingSeparator), " ", - (additionalStats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(additionalStats.balances.currentBalance, divide: false, rate: additionalStats.usdRate))", .generic), + (additionalStats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(additionalStats.balances.currentBalance, divide: false, rate: additionalStats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .stars ) @@ -824,7 +824,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, presentationStringsFormattedNumber(Int32(additionalStats.balances.overallRevenue), item.presentationData.dateTimeFormat.groupingSeparator), " ", - (additionalStats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(additionalStats.balances.overallRevenue, divide: false, rate: additionalStats.usdRate))", .generic), + (additionalStats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(additionalStats.balances.overallRevenue, divide: false, rate: additionalStats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .stars ) @@ -838,7 +838,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, formatTonAmountText(stats.balances.availableBalance, decimalSeparator: item.presentationData.dateTimeFormat.decimalSeparator), item.presentationData.strings.Monetization_Overview_Available, - (stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate))", .generic), + (stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .ton ) @@ -848,7 +848,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, formatTonAmountText(stats.balances.currentBalance, decimalSeparator: item.presentationData.dateTimeFormat.decimalSeparator), item.presentationData.strings.Monetization_Overview_Current, - (stats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.currentBalance, rate: stats.usdRate))", .generic), + (stats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.currentBalance, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .ton ) @@ -858,7 +858,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, formatTonAmountText(stats.balances.overallRevenue, decimalSeparator: item.presentationData.dateTimeFormat.decimalSeparator), item.presentationData.strings.Monetization_Overview_Total, - (stats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.overallRevenue, rate: stats.usdRate))", .generic), + (stats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.overallRevenue, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .ton ) @@ -873,7 +873,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, presentationStringsFormattedNumber(Int32(stats.balances.availableBalance), item.presentationData.dateTimeFormat.groupingSeparator), item.presentationData.strings.Monetization_StarsProceeds_Available, - (stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate))", .generic), + (stats.balances.availableBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.availableBalance, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .stars ) @@ -883,7 +883,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, presentationStringsFormattedNumber(Int32(stats.balances.currentBalance), item.presentationData.dateTimeFormat.groupingSeparator), item.presentationData.strings.Monetization_StarsProceeds_Current, - (stats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.currentBalance, rate: stats.usdRate))", .generic), + (stats.balances.currentBalance == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.currentBalance, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .stars ) @@ -893,7 +893,7 @@ class StatsOverviewItemNode: ListViewItemNode { item.presentationData, presentationStringsFormattedNumber(Int32(stats.balances.overallRevenue), item.presentationData.dateTimeFormat.groupingSeparator), item.presentationData.strings.Monetization_StarsProceeds_Total, - (stats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.overallRevenue, rate: stats.usdRate))", .generic), + (stats.balances.overallRevenue == 0 ? "" : "≈\(formatTonUsdValue(stats.balances.overallRevenue, rate: stats.usdRate, dateTimeFormat: item.presentationData.dateTimeFormat))", .generic), .stars ) diff --git a/submodules/TelegramStringFormatting/Sources/TonFormat.swift b/submodules/TelegramStringFormatting/Sources/TonFormat.swift index c925081d93..c337430784 100644 --- a/submodules/TelegramStringFormatting/Sources/TonFormat.swift +++ b/submodules/TelegramStringFormatting/Sources/TonFormat.swift @@ -1,5 +1,6 @@ import Foundation import UIKit +import TelegramPresentationData let walletAddressLength: Int = 48 @@ -9,9 +10,20 @@ public func formatTonAddress(_ address: String) -> String { return address } -public func formatTonUsdValue(_ value: Int64, divide: Bool = true, rate: Double) -> String { +public func formatTonUsdValue(_ value: Int64, divide: Bool = true, rate: Double, dateTimeFormat: PresentationDateTimeFormat) -> String { + let decimalSeparator = dateTimeFormat.decimalSeparator let normalizedValue: Double = divide ? Double(value) / 1000000000 : Double(value) - let formattedValue = String(format: "%0.2f", normalizedValue * rate) + var formattedValue = String(format: "%0.2f", normalizedValue * rate) + formattedValue = formattedValue.replacingOccurrences(of: ".", with: decimalSeparator) + if let dotIndex = formattedValue.firstIndex(of: decimalSeparator.first!) { + let integerPartString = formattedValue[.. String { - let formattedValue = String(format: "%0.2f", (Double(value)) * rate) - return "$\(formattedValue)" -} diff --git a/versions.json b/versions.json index 2f50425e88..394e4986a7 100644 --- a/versions.json +++ b/versions.json @@ -1,5 +1,5 @@ { - "app": "10.14.3", + "app": "10.15", "xcode": "15.2", "bazel": "7.1.1", "macos": "13.0" From 0450f35da82f054d29ff9982e57d7c0c7c9d0d13 Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Fri, 26 Jul 2024 22:18:13 +0200 Subject: [PATCH 4/8] Various fixes --- .../Sources/PhotoResources.swift | 33 ++++++++++++------- .../WebBrowserDomainExceptionItem.swift | 2 +- .../WebBrowserSettingsController.swift | 2 +- 3 files changed, 24 insertions(+), 13 deletions(-) diff --git a/submodules/PhotoResources/Sources/PhotoResources.swift b/submodules/PhotoResources/Sources/PhotoResources.swift index 84a72e4897..c3b5f6000d 100644 --- a/submodules/PhotoResources/Sources/PhotoResources.swift +++ b/submodules/PhotoResources/Sources/PhotoResources.swift @@ -56,6 +56,10 @@ public func representationFetchRangeForDisplayAtSize(representation: TelegramMed } public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceUserLocation, customUserContentType: MediaResourceUserContentType? = nil, photoReference: ImageMediaReference, fullRepresentationSize: CGSize = CGSize(width: 1280.0, height: 1280.0), autoFetchFullSize: Bool = false, tryAdditionalRepresentations: Bool = false, synchronousLoad: Bool = false, useMiniThumbnailIfAvailable: Bool = false, forceThumbnail: Bool = false, automaticFetch: Bool = true) -> Signal, NoError> { + return chatMessagePhotoDatas(mediaBox: postbox.mediaBox, userLocation: userLocation, customUserContentType: customUserContentType, photoReference: photoReference, fullRepresentationSize: fullRepresentationSize, autoFetchFullSize: autoFetchFullSize, tryAdditionalRepresentations: tryAdditionalRepresentations, synchronousLoad: synchronousLoad, useMiniThumbnailIfAvailable: useMiniThumbnailIfAvailable, forceThumbnail: forceThumbnail, automaticFetch: automaticFetch) +} + +func chatMessagePhotoDatas(mediaBox: MediaBox, userLocation: MediaResourceUserLocation, customUserContentType: MediaResourceUserContentType? = nil, photoReference: ImageMediaReference, fullRepresentationSize: CGSize = CGSize(width: 1280.0, height: 1280.0), autoFetchFullSize: Bool = false, tryAdditionalRepresentations: Bool = false, synchronousLoad: Bool = false, useMiniThumbnailIfAvailable: Bool = false, forceThumbnail: Bool = false, automaticFetch: Bool = true) -> Signal, NoError> { if !forceThumbnail, let progressiveRepresentation = progressiveImageRepresentation(photoReference.media.representations), progressiveRepresentation.progressiveSizes.count > 1 { enum SizeSource { case miniThumbnail(data: Data) @@ -93,7 +97,7 @@ public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceU case let .miniThumbnail(data): return .single((source, data)) case let .image(size): - return postbox.mediaBox.resourceData(progressiveRepresentation.resource, size: Int64(progressiveRepresentation.progressiveSizes.last!), in: 0 ..< size, mode: .incremental, notifyAboutIncomplete: true, attemptSynchronously: synchronousLoad) + return mediaBox.resourceData(progressiveRepresentation.resource, size: Int64(progressiveRepresentation.progressiveSizes.last!), in: 0 ..< size, mode: .incremental, notifyAboutIncomplete: true, attemptSynchronously: synchronousLoad) |> map { (data, _) -> (SizeSource, Data?) in return (source, data) } @@ -131,9 +135,9 @@ public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceU var fetchDisposable: Disposable? if automaticFetch { if autoFetchFullSize { - fetchDisposable = fetchedMediaResource(mediaBox: postbox.mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(progressiveRepresentation.resource), range: (0 ..< Int64(largestByteSize), .default), statsCategory: .image).start() + fetchDisposable = fetchedMediaResource(mediaBox: mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(progressiveRepresentation.resource), range: (0 ..< Int64(largestByteSize), .default), statsCategory: .image).start() } else if useMiniThumbnailIfAvailable { - fetchDisposable = fetchedMediaResource(mediaBox: postbox.mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(progressiveRepresentation.resource), range: (0 ..< Int64(thumbnailByteSize), .default), statsCategory: .image).start() + fetchDisposable = fetchedMediaResource(mediaBox: mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(progressiveRepresentation.resource), range: (0 ..< Int64(thumbnailByteSize), .default), statsCategory: .image).start() } } @@ -145,8 +149,8 @@ public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceU } if !forceThumbnail || photoReference.media.immediateThumbnailData == nil, let smallestRepresentation = smallestImageRepresentation(photoReference.media.representations), let largestRepresentation = photoReference.media.representationForDisplayAtSize(PixelDimensions(width: Int32(fullRepresentationSize.width), height: Int32(fullRepresentationSize.height))), let fullRepresentation = largestImageRepresentation(photoReference.media.representations) { - let maybeFullSize = postbox.mediaBox.resourceData(largestRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad) - let maybeLargestSize = postbox.mediaBox.resourceData(fullRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad) + let maybeFullSize = mediaBox.resourceData(largestRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad) + let maybeLargestSize = mediaBox.resourceData(fullRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad) let signal = combineLatest(maybeFullSize, maybeLargestSize) |> take(1) @@ -163,16 +167,16 @@ public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceU if let _ = decodedThumbnailData { fetchedThumbnail = .complete() } else { - fetchedThumbnail = fetchedMediaResource(mediaBox: postbox.mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(smallestRepresentation.resource), statsCategory: .image) + fetchedThumbnail = fetchedMediaResource(mediaBox: mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(smallestRepresentation.resource), statsCategory: .image) } - let fetchedFullSize = fetchedMediaResource(mediaBox: postbox.mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(largestRepresentation.resource), statsCategory: .image) + let fetchedFullSize = fetchedMediaResource(mediaBox: mediaBox, userLocation: userLocation, userContentType: customUserContentType ?? .image, reference: photoReference.resourceReference(largestRepresentation.resource), statsCategory: .image) let anyThumbnail: [Signal<(MediaResourceData, ChatMessagePhotoQuality), NoError>] if tryAdditionalRepresentations { anyThumbnail = photoReference.media.representations.filter({ representation in return representation != largestRepresentation }).map({ representation -> Signal<(MediaResourceData, ChatMessagePhotoQuality), NoError> in - return postbox.mediaBox.resourceData(representation.resource) + return mediaBox.resourceData(representation.resource) |> take(1) |> map { data -> (MediaResourceData, ChatMessagePhotoQuality) in if representation.dimensions.width > 200 || representation.dimensions.height > 200 { @@ -193,7 +197,7 @@ public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceU return EmptyDisposable } else { let fetchedDisposable = fetchedThumbnail.start() - let thumbnailDisposable = postbox.mediaBox.resourceData(smallestRepresentation.resource, attemptSynchronously: synchronousLoad).start(next: { next in + let thumbnailDisposable = mediaBox.resourceData(smallestRepresentation.resource, attemptSynchronously: synchronousLoad).start(next: { next in subscriber.putNext(next.size == 0 ? nil : try? Data(contentsOf: URL(fileURLWithPath: next.path), options: [])) }, error: subscriber.putError, completed: subscriber.putCompletion) @@ -222,7 +226,7 @@ public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceU if autoFetchFullSize && !useMiniThumbnailIfAvailable { fullSizeData = Signal, NoError> { subscriber in let fetchedFullSizeDisposable = fetchedFullSize.start() - let fullSizeDisposable = postbox.mediaBox.resourceData(largestRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad).start(next: { next in + let fullSizeDisposable = mediaBox.resourceData(largestRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad).start(next: { next in subscriber.putNext(Tuple(next.size == 0 ? nil : try? Data(contentsOf: URL(fileURLWithPath: next.path), options: []), next.complete)) }, error: subscriber.putError, completed: subscriber.putCompletion) @@ -232,7 +236,7 @@ public func chatMessagePhotoDatas(postbox: Postbox, userLocation: MediaResourceU } } } else { - fullSizeData = postbox.mediaBox.resourceData(largestRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad) + fullSizeData = mediaBox.resourceData(largestRepresentation.resource, option: .complete(waitUntilFetchStatus: false), attemptSynchronously: synchronousLoad) |> map { next -> Tuple2 in return Tuple(next.size == 0 ? nil : try? Data(contentsOf: URL(fileURLWithPath: next.path), options: []), next.complete) } @@ -600,6 +604,13 @@ public func chatMessagePhoto(postbox: Postbox, userLocation: MediaResourceUserLo } } +public func chatMessagePhoto(mediaBox: MediaBox, userLocation: MediaResourceUserLocation, userContentType customUserContentType: MediaResourceUserContentType? = nil, photoReference: ImageMediaReference, synchronousLoad: Bool = false, highQuality: Bool = false) -> Signal<(TransformImageArguments) -> DrawingContext?, NoError> { + return chatMessagePhotoInternal(photoData: chatMessagePhotoDatas(mediaBox: mediaBox, userLocation: userLocation, customUserContentType: customUserContentType, photoReference: photoReference, tryAdditionalRepresentations: true, synchronousLoad: synchronousLoad), synchronousLoad: synchronousLoad) + |> map { _, _, generate in + return generate + } +} + public enum ChatMessagePhotoQuality { case none case blurred diff --git a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserDomainExceptionItem.swift b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserDomainExceptionItem.swift index 3e66f1ff29..869532b3a8 100644 --- a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserDomainExceptionItem.swift +++ b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserDomainExceptionItem.swift @@ -208,7 +208,7 @@ final class WebBrowserDomainExceptionItemNode: ItemListRevealOptionsItemNode, It let iconSize = CGSize(width: 40.0, height: 40.0) var imageSize = iconSize if currentItem?.icon?.id != item.icon?.id, let icon = item.icon { - strongSelf.iconNode.setSignal(chatMessagePhoto(postbox: item.context.account.postbox, userLocation: .other, photoReference: .standalone(media: icon))) + strongSelf.iconNode.setSignal(chatMessagePhoto(mediaBox: item.context.sharedContext.accountManager.mediaBox, userLocation: .other, photoReference: .standalone(media: icon))) } if let icon = item.icon, let dimensions = largestImageRepresentation(icon.representations)?.dimensions.cgSize { imageSize = dimensions.aspectFilled(imageSize) diff --git a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift index 903f4697ab..53c073eae2 100644 --- a/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift +++ b/submodules/SettingsUI/Sources/Data and Storage/WebBrowserSettingsController.swift @@ -479,7 +479,7 @@ private func fetchDomainExceptionInfo(context: AccountContext, url: String) -> S var image: TelegramMediaImage? if let imageData, let parsedImage = UIImage(data: imageData) { let resource = LocalFileMediaResource(fileId: Int64.random(in: Int64.min ... Int64.max)) - context.account.postbox.mediaBox.storeResourceData(resource.id, data: imageData) + context.sharedContext.accountManager.mediaBox.storeResourceData(resource.id, data: imageData) image = TelegramMediaImage( imageId: MediaId(namespace: Namespaces.Media.LocalImage, id: Int64.random(in: Int64.min ... Int64.max)), representations: [ From 32ace10858501b150860771727f5e876437c972e Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Fri, 26 Jul 2024 22:57:42 +0200 Subject: [PATCH 5/8] Various fixes --- .../Telegram-iOS/en.lproj/Localizable.strings | 2 + .../Sources/MediaPickerScreen.swift | 6 ++- .../Sources/MediaPickerTitleView.swift | 44 ++++++++++++++++-- .../Privacy.imageset/Contents.json | 2 +- .../Privacy.imageset/privacy (2).pdf | Bin 0 -> 2500 bytes .../Context Menu/Privacy.imageset/privacy.pdf | Bin 2542 -> 0 bytes 6 files changed, 48 insertions(+), 6 deletions(-) create mode 100644 submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/privacy (2).pdf delete mode 100644 submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/privacy.pdf diff --git a/Telegram/Telegram-iOS/en.lproj/Localizable.strings b/Telegram/Telegram-iOS/en.lproj/Localizable.strings index ae9452a0bf..6c71dc1d97 100644 --- a/Telegram/Telegram-iOS/en.lproj/Localizable.strings +++ b/Telegram/Telegram-iOS/en.lproj/Localizable.strings @@ -12670,3 +12670,5 @@ Sorry for the inconvenience."; "Conversation.OpenProfile" = "OPEN PROFILE"; "Stars.Intro.GiftStars" = "Gift Stars to Friends"; + +"MediaPicker.CreateSticker" = "Create a sticker from a photo"; diff --git a/submodules/MediaPickerUI/Sources/MediaPickerScreen.swift b/submodules/MediaPickerUI/Sources/MediaPickerScreen.swift index d56dcdd359..40cd313cd8 100644 --- a/submodules/MediaPickerUI/Sources/MediaPickerScreen.swift +++ b/submodules/MediaPickerUI/Sources/MediaPickerScreen.swift @@ -1799,9 +1799,13 @@ public final class MediaPickerScreen: ViewController, AttachmentContainable { self.titleView.title = collection.localizedTitle ?? presentationData.strings.Attachment_Gallery } else { switch mode { - case .default, .createSticker: + case .default: self.titleView.title = presentationData.strings.MediaPicker_Recents self.titleView.isEnabled = true + case .createSticker: + self.titleView.title = presentationData.strings.MediaPicker_Recents + self.titleView.subtitle = presentationData.strings.MediaPicker_CreateSticker + self.titleView.isEnabled = true case .story: self.titleView.title = presentationData.strings.MediaPicker_Recents self.titleView.isEnabled = true diff --git a/submodules/MediaPickerUI/Sources/MediaPickerTitleView.swift b/submodules/MediaPickerUI/Sources/MediaPickerTitleView.swift index bd44af71bb..a9d360915b 100644 --- a/submodules/MediaPickerUI/Sources/MediaPickerTitleView.swift +++ b/submodules/MediaPickerUI/Sources/MediaPickerTitleView.swift @@ -10,12 +10,14 @@ final class MediaPickerTitleView: UIView { let contextSourceNode: ContextReferenceContentNode private let buttonNode: HighlightTrackingButtonNode private let titleNode: ImmediateTextNode + private let subtitleNode: ImmediateTextNode private let arrowNode: ASImageNode private let segmentedControlNode: SegmentedControlNode public var theme: PresentationTheme { didSet { self.titleNode.attributedText = NSAttributedString(string: self.title, font: NavigationBar.titleFont, textColor: theme.rootController.navigationBar.primaryTextColor) + self.subtitleNode.attributedText = NSAttributedString(string: self.subtitle, font: Font.regular(12.0), textColor: self.theme.rootController.navigationBar.secondaryTextColor) self.segmentedControlNode.updateTheme(SegmentedControlTheme(theme: self.theme)) } } @@ -23,7 +25,16 @@ final class MediaPickerTitleView: UIView { public var title: String = "" { didSet { if self.title != oldValue { - self.titleNode.attributedText = NSAttributedString(string: self.title, font: NavigationBar.titleFont, textColor: theme.rootController.navigationBar.primaryTextColor) + self.titleNode.attributedText = NSAttributedString(string: self.title, font: NavigationBar.titleFont, textColor: self.theme.rootController.navigationBar.primaryTextColor) + self.setNeedsLayout() + } + } + } + + public var subtitle: String = "" { + didSet { + if self.subtitle != oldValue { + self.subtitleNode.attributedText = NSAttributedString(string: self.subtitle, font: Font.regular(12.0), textColor: self.theme.rootController.navigationBar.secondaryTextColor) self.setNeedsLayout() } } @@ -36,7 +47,7 @@ final class MediaPickerTitleView: UIView { } } - public func updateTitle(title: String, isEnabled: Bool, animated: Bool) { + public func updateTitle(title: String, subtitle: String = "", isEnabled: Bool, animated: Bool) { if animated { if self.title != title { if let snapshotView = self.titleNode.view.snapshotContentTree() { @@ -49,6 +60,17 @@ final class MediaPickerTitleView: UIView { self.titleNode.view.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2) } } + if self.subtitle != subtitle { + if let snapshotView = self.subtitleNode.view.snapshotContentTree() { + snapshotView.frame = self.subtitleNode.frame + self.addSubview(snapshotView) + + snapshotView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, removeOnCompletion: false, completion: { _ in + snapshotView.removeFromSuperview() + }) + self.subtitleNode.view.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2) + } + } if self.isEnabled != isEnabled { if let snapshotView = self.arrowNode.view.snapshotContentTree() { snapshotView.frame = self.arrowNode.frame @@ -62,6 +84,7 @@ final class MediaPickerTitleView: UIView { } } self.title = title + self.subtitle = subtitle self.isEnabled = isEnabled } @@ -76,6 +99,7 @@ final class MediaPickerTitleView: UIView { if self.segmentsHidden != oldValue { let transition = ContainedViewLayoutTransition.animated(duration: 0.2, curve: .easeInOut) transition.updateAlpha(node: self.titleNode, alpha: self.segmentsHidden ? 1.0 : 0.0) + transition.updateAlpha(node: self.subtitleNode, alpha: self.segmentsHidden ? 1.0 : 0.0) transition.updateAlpha(node: self.arrowNode, alpha: self.segmentsHidden ? 1.0 : 0.0) transition.updateAlpha(node: self.segmentedControlNode, alpha: self.segmentsHidden ? 0.0 : 1.0) self.segmentedControlNode.isUserInteractionEnabled = !self.segmentsHidden @@ -115,6 +139,9 @@ final class MediaPickerTitleView: UIView { self.titleNode = ImmediateTextNode() self.titleNode.displaysAsynchronously = false + self.subtitleNode = ImmediateTextNode() + self.subtitleNode.displaysAsynchronously = false + self.arrowNode = ASImageNode() self.arrowNode.displaysAsynchronously = false self.arrowNode.image = generateTintedImage(image: UIImage(bundleImageName: "Media Editor/DownArrow"), color: theme.rootController.navigationBar.secondaryTextColor) @@ -145,6 +172,7 @@ final class MediaPickerTitleView: UIView { self.addSubnode(self.contextSourceNode) self.addSubnode(self.titleNode) + self.addSubnode(self.subtitleNode) self.addSubnode(self.arrowNode) self.addSubnode(self.buttonNode) self.addSubnode(self.segmentedControlNode) @@ -166,10 +194,18 @@ final class MediaPickerTitleView: UIView { self.segmentedControlNode.frame = CGRect(origin: CGPoint(x: floorToScreenPixels((size.width - controlSize.width) / 2.0), y: floorToScreenPixels((size.height - controlSize.height) / 2.0)), size: controlSize) let titleSize = self.titleNode.updateLayout(CGSize(width: 210.0, height: 44.0)) - self.titleNode.frame = CGRect(origin: CGPoint(x: floorToScreenPixels((size.width - titleSize.width) / 2.0), y: floorToScreenPixels((size.height - titleSize.height) / 2.0)), size: titleSize) + let subtitleSize = self.subtitleNode.updateLayout(CGSize(width: 210.0, height: 44.0)) + + var totalHeight: CGFloat = titleSize.height + if subtitleSize.height > 0.0 { + totalHeight += subtitleSize.height + } + + self.titleNode.frame = CGRect(origin: CGPoint(x: floorToScreenPixels((size.width - titleSize.width) / 2.0), y: floorToScreenPixels((size.height - totalHeight) / 2.0)), size: titleSize) + self.subtitleNode.frame = CGRect(origin: CGPoint(x: floorToScreenPixels((size.width - subtitleSize.width) / 2.0), y: floorToScreenPixels((size.height - totalHeight) / 2.0) + subtitleSize.height + 7.0), size: subtitleSize) if let arrowSize = self.arrowNode.image?.size { - self.arrowNode.frame = CGRect(origin: CGPoint(x: self.titleNode.frame.maxX + 5.0, y: floorToScreenPixels((size.height - arrowSize.height) / 2.0) + 1.0 - UIScreenPixel), size: arrowSize) + self.arrowNode.frame = CGRect(origin: CGPoint(x: self.titleNode.frame.maxX + 5.0, y: floorToScreenPixels((size.height - totalHeight) / 2.0) + titleSize.height / 2.0 - arrowSize.height / 2.0 + 1.0 - UIScreenPixel), size: arrowSize) } self.buttonNode.frame = CGRect(origin: .zero, size: size) } diff --git a/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json b/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json index 638a59cc88..6e7b34e21d 100644 --- a/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json +++ b/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/Contents.json @@ -1,7 +1,7 @@ { "images" : [ { - "filename" : "privacy.pdf", + "filename" : "privacy (2).pdf", "idiom" : "universal" } ], diff --git a/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/privacy (2).pdf b/submodules/TelegramUI/Images.xcassets/Chat/Context Menu/Privacy.imageset/privacy (2).pdf new file mode 100644 index 0000000000000000000000000000000000000000..badb2fabc505b01ea105299eda4038ada4089b0d GIT binary patch literal 2500 zcmZXWdpy(a8^@gzL(UY@H_;|(#^!uBR!eP0t56w66Psrn=I~TfOXUc8IVd(6;+B3lM20@{QR<eP-_towqiM?R%EePF z20fSbQj^EG+1xnEU+FnE*weJSIJVd~pNZ)?b)@Mizws{?Z!}d~-tK>xFO;QsDF-jX zs7EVnJNZM)uVnRb8l zqc<->z ziH}OLor@jMrs8BI)b8AewB!COGDzKE>=C?WutWAjWEOOsB@Lmv+niujD9H_RraUL zP6Ow5&~D3i+&a7AGf#44cwopKRL}6I$aGkJ=-TNOk1@IXIlaP< z%WbQNWtpLmw}&Rm7@S>r_43GW{j;tk+dFlYEPdaGcvPI3a42Gwd&Tcg>2O+4QcY&1 z5ae1cQNzWShGFUK63@xhF3!dQHqm3oJc-kHK_6X#J8o+;`#JzQZNQnc zFeKj8SHCF#EX^zV@xfXy=f0w1r9}v+x|g|btlc(B^h6%MD8WBKwd9;zyE)wYV24cc z9;muEX$J4b6!RXxiHqDzR<6XkhZHR&VKLQmtl20B_|b>S;(y_jgSmFtiR1y@p&<=b zIpk>XEqfO+mWHI!^V`N!&E@OXKl21^RT%TVx`WKVl}!a6JthsInS0!sMrCmHB->3T zZNL%P7-sl5JIvuiM<;sTU>VKPZq~j+pHIq~O-SSWmCQd~U1@*6B5HLgD#wmhWTG-8XsSgswHWwGwNkkkF0gv!= zR|`T*RDDP-DR>tE@ZgbhxqLuj8gQ$_b0RYFhRl%yiN>#y~|R zoi9%5p!XH*i~r=6e?hyf$_b@EU7(KTBDy?T6BX&M2f^IvQQYwYK9-WF$# z)aY((Ox0zqf5B=YEl6K^)MI}|TQ4RT&4-BB{mJrB`dZR;+&3dR3_BOv#j>xG9@2@t z{~xFO^P*G^uY+g0O($fI8z84uf5cK_1Zx}ngqS}l*Wg-2-Fgl$lOIl~e{HH2-s9ui z{?$(f9miRbO^pSHBn>-1x@e`8B_EZ`&wZF_-NI z399fE_ru|rwl|Q|l_IVnww= zzR01cFzHt3TN+Nbn@$*1R442q)bV!uvdyLFFAw9HFaqeNl=Y%4(^{{3W1>S#87%&C z(3Q#F$_AwSq!udeff*k&H#g-F8TopS@0C*gC9-#QMbXCd#VvD z535Tt=}P*385zVh--)YkF!@4+g0rFV^y%JIS@y!=DK&DM!qO|0Qi9gCJimhLg*!;P z#!pFe4%K%k2p*s@qVFBWWn;^czM(0as$0wZI(G%QdS6Ve>KHH3DkaSYw(q#-!hlO3 z6El%0s^J-fOM@!KWe0MtMWO?P#%`Hp={F=a&85Ie{(#}HpOM4gW%DMcQuLDvz~?$R^buI zciXny3|JKD&sU3K(W*BXwsI3yQ+L2gif>N$;3uo5;ywz* z{s`RG=wZ1>)y$!GD@Sq7bmv|>L`Q7ib$1+GRTddfwU}od6#VFVy zu)X>&G0Cj|-ZN)dK>fri5w2md=Up-C`=}S*OBj4z=W>mk`g_&5;RSn4zbC^-)8Sww zLk~1OfwRfB-VS-%Pzv`!bA0yVf zVfx!mLV>iO4+;zWF5HPgCj?Uhe@|sli2)!ZzzpRlD zDFh_?bABP{f8q#RLNFC10|?t-JQcJC{Yd^GJA-WqCy*FO4Fa^;;cje*U4cR+gZL0g z1UD_;nJ%j@lJd^b<`59FBf~#yM%jGafe!4k=c1kHFdr;iYxIHByt$vHIJYl-WJGzq zo?l>m`yBe^;|#(~%j`?shxPYQ-+r23%cvuK-9Pf>Rrf2yxN+9$n^*O02m9a7kz>N* zV%pA3BkB9j>tk1u=r?2O=B z^z-sbz@#-f7&^@8W-*r;^o-_0+Ba@DqJwZRU_wN@w&Y>gTq zXo4_83T9GFWg-I-$0)6d@(?6ytB&pOTe#5=JD0l{XyYSq)(jY{kH+hpaf)F016B+RWOpa$fZ z*)h3H^#qgMub$8g8A?q`U*(pg-(#6b~v$Y^C$N9g%1 zKHrEX4auej{-=Vq#z6t)a9w*75ow*<;#f4w*!oP~v4C_Lc!FBDi@1AaL7$@Z$)#$s zsU9c#bG z@Cnts@dwb(e1H2^*S9t7D1IW9vVY4Fs-QKY<)EU23sk!2AZFia50_xfvsKx-RFJIE zFjT1{uQXFW(z-SOiR?{_F1J7yUniZm3#U~2IcFwj_}l~a!DRjy>RSCYqFrQn#+?Im zN|A}5Rjoh2PvBZDza*de@xRbJcVNDrioGqvq5{>Iu%psx5E@GHWVUn=aQ`l^bFAt& zz1Fn==nVNr;ZYF>BmYsGu>2q1z47Q08Cdzo#$@=P(IiV#S)n``m za2zUGMzgrxOzSi4FEAuvqTG;Ya$F6b6@>E(lZ&w1UG!KwU8w_$;5pCh4WSO1^$ zK?0{W#Uvbx^BQ+yy;EHc=A@PNwkGkm?6V5w4SzQpX0Gh6Zudrg-l%$AM2kkZOzH2f zKqV?45xlVFRB4H-LcHI;zAu^*@Z;tQnX_LaYIPLuRa)Oon@Y=wO6V|}k-m-{mY-s( zT!m{htw&n8UcBz;i9e7X!Ji>{xsN)l;%SQRm=X85L6S@fd!Gi99V|L-*SMo3Pw^U`3c^q7Ita{|ohuhJ`to3mEf?TVUDoY?JT_Cv=79U-)*K?4*5>S!a#zoN2 z%?R*UbyafFglg!?T1AeB*+3irxV)ISQ`%$at!}vSWVR4mcrsb{-kdJh_3k}H+uf56LI-4+?(-9U#B8f@?eE$5&*zS?XKmg&258R+| zXV9O3wm0b(ESPhLuhcIO#y;%B>1yO1vneH0ULd+NTKXp)c?&-`5`zquA%o^CC-AB&4!%8 zek^W|JU47xn)bHz{wb4ij3}&;}_J5%~8_@s& From 9df433937e5b4fb1db3ed9a9885ca0bd32071155 Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Sat, 27 Jul 2024 01:01:11 +0200 Subject: [PATCH 6/8] Fix browser t.me handling --- submodules/BrowserUI/Sources/BrowserWebContent.swift | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/submodules/BrowserUI/Sources/BrowserWebContent.swift b/submodules/BrowserUI/Sources/BrowserWebContent.swift index 7efff4450f..0c0f883e0d 100644 --- a/submodules/BrowserUI/Sources/BrowserWebContent.swift +++ b/submodules/BrowserUI/Sources/BrowserWebContent.swift @@ -681,7 +681,7 @@ final class BrowserWebContent: UIView, BrowserContent, WKNavigationDelegate, WKU // }) // } else { if let url = navigationAction.request.url?.absoluteString { - if isTelegramMeLink(url) || isTelegraPhLink(url) { + if (navigationAction.targetFrame == nil || navigationAction.targetFrame?.isMainFrame == true) && (isTelegramMeLink(url) || isTelegraPhLink(url)) { decisionHandler(.cancel, preferences) self.minimize() self.openAppUrl(url) @@ -712,7 +712,7 @@ final class BrowserWebContent: UIView, BrowserContent, WKNavigationDelegate, WKU func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) { if let url = navigationAction.request.url?.absoluteString { - if isTelegramMeLink(url) || isTelegraPhLink(url) { + if (navigationAction.targetFrame == nil || navigationAction.targetFrame?.isMainFrame == true) && (isTelegramMeLink(url) || isTelegraPhLink(url)) { decisionHandler(.cancel) self.minimize() self.openAppUrl(url) From 60196075a6cac2d8aaffeca086e030a9ca974340 Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Sat, 27 Jul 2024 01:21:33 +0200 Subject: [PATCH 7/8] Fix video message layout when minimized container is present --- .../Display/Source/ContainerViewLayout.swift | 4 ++++ .../Navigation/NavigationController.swift | 21 ++++++++++++------- .../Sources/VideoMessageCameraScreen.swift | 2 +- 3 files changed, 19 insertions(+), 8 deletions(-) diff --git a/submodules/Display/Source/ContainerViewLayout.swift b/submodules/Display/Source/ContainerViewLayout.swift index 8325f28258..ba1894abd4 100644 --- a/submodules/Display/Source/ContainerViewLayout.swift +++ b/submodules/Display/Source/ContainerViewLayout.swift @@ -90,6 +90,10 @@ public struct ContainerViewLayout: Equatable { return ContainerViewLayout(size: self.size, metrics: self.metrics, deviceMetrics: self.deviceMetrics, intrinsicInsets: intrinsicInsets, safeInsets: self.safeInsets, additionalInsets: self.additionalInsets, statusBarHeight: self.statusBarHeight, inputHeight: self.inputHeight, inputHeightIsInteractivellyChanging: self.inputHeightIsInteractivellyChanging, inVoiceOver: self.inVoiceOver) } + public func withUpdatedAdditionalInsets(_ additionalInsets: UIEdgeInsets) -> ContainerViewLayout { + return ContainerViewLayout(size: self.size, metrics: self.metrics, deviceMetrics: self.deviceMetrics, intrinsicInsets: self.intrinsicInsets, safeInsets: self.safeInsets, additionalInsets: additionalInsets, statusBarHeight: self.statusBarHeight, inputHeight: self.inputHeight, inputHeightIsInteractivellyChanging: self.inputHeightIsInteractivellyChanging, inVoiceOver: self.inVoiceOver) + } + public func withUpdatedInputHeight(_ inputHeight: CGFloat?) -> ContainerViewLayout { return ContainerViewLayout(size: self.size, metrics: self.metrics, deviceMetrics: self.deviceMetrics, intrinsicInsets: self.intrinsicInsets, safeInsets: self.safeInsets, additionalInsets: self.additionalInsets, statusBarHeight: self.statusBarHeight, inputHeight: inputHeight, inputHeightIsInteractivellyChanging: self.inputHeightIsInteractivellyChanging, inVoiceOver: self.inVoiceOver) } diff --git a/submodules/Display/Source/Navigation/NavigationController.swift b/submodules/Display/Source/Navigation/NavigationController.swift index 7f7156e25d..dd7c033a3a 100644 --- a/submodules/Display/Source/Navigation/NavigationController.swift +++ b/submodules/Display/Source/Navigation/NavigationController.swift @@ -443,7 +443,20 @@ open class NavigationController: UINavigationController, ContainableController, globalScrollToTopNode.frame = CGRect(origin: CGPoint(x: 0.0, y: -1.0), size: CGSize(width: layout.size.width, height: 1.0)) } - let overlayContainerLayout = layout + var overlayContainerLayout = layout + + var updatedSize = layout.size + var updatedIntrinsicInsets = layout.intrinsicInsets + var updatedAdditionalInsets = layout.additionalInsets + if let minimizedContainer = self.minimizedContainer { + if (layout.inputHeight ?? 0.0).isZero { + let minimizedContainerHeight = minimizedContainer.collapsedHeight(layout: layout) + updatedSize.height -= minimizedContainerHeight + updatedIntrinsicInsets.bottom = 0.0 + updatedAdditionalInsets.bottom += minimizedContainerHeight + } + } + overlayContainerLayout = overlayContainerLayout.withUpdatedAdditionalInsets(updatedAdditionalInsets) if let inCallStatusBar = self.inCallStatusBar { let isLandscape = layout.size.width > layout.size.height @@ -843,8 +856,6 @@ open class NavigationController: UINavigationController, ContainableController, layout.additionalInsets.left = max(layout.intrinsicInsets.left, additionalSideInsets.left) layout.additionalInsets.right = max(layout.intrinsicInsets.right, additionalSideInsets.right) - var updatedSize = layout.size - var updatedIntrinsicInsets = layout.intrinsicInsets if case .flat = navigationLayout.root, let minimizedContainer = self.minimizedContainer { if minimizedContainer.supernode !== self.displayNode { if let rootContainer = self.rootContainer, case let .flat(flatContainer) = rootContainer { @@ -857,10 +868,6 @@ open class NavigationController: UINavigationController, ContainableController, self.displayNode.insertSubnode(minimizedContainer, at: 0) } } - if (layout.inputHeight ?? 0.0).isZero { - updatedSize.height -= minimizedContainer.collapsedHeight(layout: layout) - updatedIntrinsicInsets.bottom = 0.0 - } } switch navigationLayout.root { diff --git a/submodules/TelegramUI/Components/VideoMessageCameraScreen/Sources/VideoMessageCameraScreen.swift b/submodules/TelegramUI/Components/VideoMessageCameraScreen/Sources/VideoMessageCameraScreen.swift index 2676399bd6..cd5491a460 100644 --- a/submodules/TelegramUI/Components/VideoMessageCameraScreen/Sources/VideoMessageCameraScreen.swift +++ b/submodules/TelegramUI/Components/VideoMessageCameraScreen/Sources/VideoMessageCameraScreen.swift @@ -1389,7 +1389,7 @@ public class VideoMessageCameraScreen: ViewController { } var backgroundFrame = CGRect(origin: .zero, size: CGSize(width: layout.size.width, height: controller.inputPanelFrame.0.minY)) - if backgroundFrame.maxY < layout.size.height - 100.0 && (layout.inputHeight ?? 0.0).isZero && !controller.inputPanelFrame.1 { + if backgroundFrame.maxY < layout.size.height - 100.0 && (layout.inputHeight ?? 0.0).isZero && !controller.inputPanelFrame.1 && layout.additionalInsets.bottom.isZero { backgroundFrame = CGRect(origin: .zero, size: CGSize(width: layout.size.width, height: layout.size.height - layout.intrinsicInsets.bottom - controller.inputPanelFrame.0.height)) } From d21d943d8d1780deb582ff26f1fc178b59a49794 Mon Sep 17 00:00:00 2001 From: Ilya Laktyushin Date: Mon, 29 Jul 2024 00:53:17 +0200 Subject: [PATCH 8/8] Various improvements --- .../DrawingUI/Sources/DrawingLinkEntityView.swift | 2 +- .../Sources/TwoFactorAuthDataInputScreen.swift | 4 ++-- .../MediaEditorScreen/Sources/CreateLinkScreen.swift | 11 +++++++++-- 3 files changed, 12 insertions(+), 5 deletions(-) diff --git a/submodules/DrawingUI/Sources/DrawingLinkEntityView.swift b/submodules/DrawingUI/Sources/DrawingLinkEntityView.swift index 22d81cd41d..19eeba7632 100644 --- a/submodules/DrawingUI/Sources/DrawingLinkEntityView.swift +++ b/submodules/DrawingUI/Sources/DrawingLinkEntityView.swift @@ -209,7 +209,7 @@ public final class DrawingLinkEntityView: DrawingEntityView, UITextViewDelegate if !self.linkEntity.name.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty { string = self.linkEntity.name.trimmingCharacters(in: .whitespacesAndNewlines).uppercased() } else { - string = self.linkEntity.url.uppercased() + string = self.linkEntity.url.uppercased().replacingOccurrences(of: "http://", with: "").replacingOccurrences(of: "https://", with: "") } let text = NSMutableAttributedString(string: string) let range = NSMakeRange(0, text.length) diff --git a/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift b/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift index 539b78af18..9ec039326d 100644 --- a/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift +++ b/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift @@ -1104,7 +1104,7 @@ private final class TwoFactorDataInputTextNode: ASDisplayNode, UITextFieldDelega self.hideButtonNode.isHidden = confirmation case .email: self.inputNode.textField.keyboardType = .emailAddress - self.inputNode.textField.returnKeyType = .done + self.inputNode.textField.returnKeyType = .next self.hideButtonNode.isHidden = true if #available(iOS 12.0, *) { @@ -1134,7 +1134,7 @@ private final class TwoFactorDataInputTextNode: ASDisplayNode, UITextFieldDelega } case .hint: self.inputNode.textField.keyboardType = .asciiCapable - self.inputNode.textField.returnKeyType = .done + self.inputNode.textField.returnKeyType = .next self.hideButtonNode.isHidden = true self.inputNode.textField.autocorrectionType = .no diff --git a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/CreateLinkScreen.swift b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/CreateLinkScreen.swift index b8afdb5081..8b64da17ae 100644 --- a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/CreateLinkScreen.swift +++ b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/CreateLinkScreen.swift @@ -466,14 +466,21 @@ private final class CreateLinkSheetComponent: CombinedComponent { let text = !self.name.isEmpty ? self.name : self.link var effectiveMedia: TelegramMediaWebpage? - if let webpage = self.webpage, case .Loaded = webpage.content, !self.dismissed { + var webpageHasLargeMedia = false + if let webpage = self.webpage, case let .Loaded(content) = webpage.content, !self.dismissed { effectiveMedia = webpage + + if let isMediaLargeByDefault = content.isMediaLargeByDefault, isMediaLargeByDefault { + webpageHasLargeMedia = true + } else { + webpageHasLargeMedia = true + } } var attributes: [MessageAttribute] = [] attributes.append(TextEntitiesMessageAttribute(entities: [.init(range: 0 ..< (text as NSString).length, type: .Url)])) if !self.dismissed { - attributes.append(WebpagePreviewMessageAttribute(leadingPreview: !self.positionBelowText, forceLargeMedia: self.largeMedia, isManuallyAdded: false, isSafe: true)) + attributes.append(WebpagePreviewMessageAttribute(leadingPreview: !self.positionBelowText, forceLargeMedia: self.largeMedia ?? webpageHasLargeMedia, isManuallyAdded: false, isSafe: true)) } let peerId = PeerId(namespace: Namespaces.Peer.CloudUser, id: PeerId.Id._internalFromInt64Value(1))