diff --git a/Telegram/NotificationService/Serialization.m b/Telegram/NotificationService/Serialization.m
index 3d92dca7b9..ddfa890a93 100644
--- a/Telegram/NotificationService/Serialization.m
+++ b/Telegram/NotificationService/Serialization.m
@@ -3,7 +3,7 @@
@implementation Serialization
- (NSUInteger)currentLayer {
- return 117;
+ return 118;
}
- (id _Nullable)parseMessage:(NSData * _Nullable)data {
diff --git a/Telegram/Telegram-iOS/Info.plist b/Telegram/Telegram-iOS/Info.plist
index f66daefe49..a34aee90c5 100644
--- a/Telegram/Telegram-iOS/Info.plist
+++ b/Telegram/Telegram-iOS/Info.plist
@@ -264,6 +264,7 @@
onionhttp
ucbrowser
dolphin
+ instagram-stories
LSRequiresIPhoneOS
diff --git a/Telegram/Telegram-iOS/InfoBazel.plist b/Telegram/Telegram-iOS/InfoBazel.plist
index e7ca119cd8..ae1b92de45 100644
--- a/Telegram/Telegram-iOS/InfoBazel.plist
+++ b/Telegram/Telegram-iOS/InfoBazel.plist
@@ -98,6 +98,7 @@
onionhttp
ucbrowser
dolphin
+ instagram-stories
LSRequiresIPhoneOS
diff --git a/submodules/AnimatedStickerNode/BUCK b/submodules/AnimatedStickerNode/BUCK
index bdc95d5051..1e6a948afa 100644
--- a/submodules/AnimatedStickerNode/BUCK
+++ b/submodules/AnimatedStickerNode/BUCK
@@ -12,6 +12,7 @@ static_library(
"//submodules/YuvConversion:YuvConversion",
"//submodules/GZip:GZip",
"//submodules/rlottie:RLottieBinding",
+ "//submodules/MediaResources:MediaResources",
],
frameworks = [
"$SDKROOT/System/Library/Frameworks/Foundation.framework",
diff --git a/submodules/AnimatedStickerNode/BUILD b/submodules/AnimatedStickerNode/BUILD
index bf1ba42bdd..655f34543c 100644
--- a/submodules/AnimatedStickerNode/BUILD
+++ b/submodules/AnimatedStickerNode/BUILD
@@ -13,6 +13,7 @@ swift_library(
"//submodules/YuvConversion:YuvConversion",
"//submodules/GZip:GZip",
"//submodules/rlottie:RLottieBinding",
+ "//submodules/MediaResources:MediaResources",
],
visibility = [
"//visibility:public",
diff --git a/submodules/AnimatedStickerNode/Sources/AnimatedStickerNode.swift b/submodules/AnimatedStickerNode/Sources/AnimatedStickerNode.swift
index ebbf1292e8..b8f4989a31 100644
--- a/submodules/AnimatedStickerNode/Sources/AnimatedStickerNode.swift
+++ b/submodules/AnimatedStickerNode/Sources/AnimatedStickerNode.swift
@@ -6,6 +6,7 @@ import AsyncDisplayKit
import RLottieBinding
import GZip
import YuvConversion
+import MediaResources
private let sharedQueue = Queue()
private let sharedStoreQueue = Queue.concurrentDefaultQueue()
@@ -438,7 +439,7 @@ private final class AnimatedStickerDirectFrameSourceCache {
private var scratchBuffer: Data
private var decodeBuffer: Data
- init?(queue: Queue, pathPrefix: String, width: Int, height: Int, frameCount: Int) {
+ init?(queue: Queue, pathPrefix: String, width: Int, height: Int, frameCount: Int, fitzModifier: EmojiFitzModifier?) {
self.queue = queue
self.storeQueue = sharedStoreQueue
@@ -446,7 +447,13 @@ private final class AnimatedStickerDirectFrameSourceCache {
self.width = width
self.height = height
- let path = "\(pathPrefix)_\(width):\(height).stickerframecache"
+ let suffix : String
+ if let fitzModifier = fitzModifier {
+ suffix = "_fitz\(fitzModifier.rawValue)"
+ } else {
+ suffix = ""
+ }
+ let path = "\(pathPrefix)_\(width):\(height)\(suffix).stickerframecache"
var file = ManagedFileImpl(queue: queue, path: path, mode: .readwrite)
if let file = file {
self.file = file
@@ -594,7 +601,7 @@ private final class AnimatedStickerDirectFrameSource: AnimatedStickerFrameSource
return self.currentFrame % self.frameCount
}
- init?(queue: Queue, data: Data, width: Int, height: Int, cachePathPrefix: String?) {
+ init?(queue: Queue, data: Data, width: Int, height: Int, cachePathPrefix: String?, fitzModifier: EmojiFitzModifier?) {
self.queue = queue
self.data = data
self.width = width
@@ -602,7 +609,9 @@ private final class AnimatedStickerDirectFrameSource: AnimatedStickerFrameSource
self.bytesPerRow = (4 * Int(width) + 15) & (~15)
self.currentFrame = 0
let rawData = TGGUnzipData(data, 8 * 1024 * 1024) ?? data
- guard let animation = LottieInstance(data: rawData, cacheKey: "") else {
+ let decompressedData = transformedWithFitzModifier(data: rawData, fitzModifier: fitzModifier)
+
+ guard let animation = LottieInstance(data: decompressedData, cacheKey: "") else {
return nil
}
self.animation = animation
@@ -611,7 +620,7 @@ private final class AnimatedStickerDirectFrameSource: AnimatedStickerFrameSource
self.frameRate = Int(animation.frameRate)
self.cache = cachePathPrefix.flatMap { cachePathPrefix in
- AnimatedStickerDirectFrameSourceCache(queue: queue, pathPrefix: cachePathPrefix, width: width, height: height, frameCount: frameCount)
+ AnimatedStickerDirectFrameSourceCache(queue: queue, pathPrefix: cachePathPrefix, width: width, height: height, frameCount: frameCount, fitzModifier: fitzModifier)
}
}
@@ -698,11 +707,15 @@ public struct AnimatedStickerStatus: Equatable {
}
public protocol AnimatedStickerNodeSource {
+ var fitzModifier: EmojiFitzModifier? { get }
+
func cachedDataPath(width: Int, height: Int) -> Signal<(String, Bool), NoError>
func directDataPath() -> Signal
}
public final class AnimatedStickerNodeLocalFileSource: AnimatedStickerNodeSource {
+ public var fitzModifier: EmojiFitzModifier? = nil
+
public let path: String
public init(path: String) {
@@ -733,8 +746,8 @@ public final class AnimatedStickerNode: ASDisplayNode {
private let timer = Atomic(value: nil)
private let frameSource = Atomic?>(value: nil)
- private var directData: (Data, String, Int, Int, String?)?
- private var cachedData: (Data, Bool)?
+ private var directData: (Data, String, Int, Int, String?, EmojiFitzModifier?)?
+ private var cachedData: (Data, Bool, EmojiFitzModifier?)?
private var renderer: (AnimationRenderer & ASDisplayNode)?
@@ -809,7 +822,7 @@ public final class AnimatedStickerNode: ASDisplayNode {
return
}
if let directData = try? Data(contentsOf: URL(fileURLWithPath: path), options: [.mappedRead]) {
- strongSelf.directData = (directData, path, width, height, cachePathPrefix)
+ strongSelf.directData = (directData, path, width, height, cachePathPrefix, source.fitzModifier)
}
if case let .still(position) = playbackMode {
strongSelf.seekTo(position)
@@ -830,9 +843,9 @@ public final class AnimatedStickerNode: ASDisplayNode {
return
}
if let data = try? Data(contentsOf: URL(fileURLWithPath: path), options: [.mappedRead]) {
- if let (_, currentComplete) = strongSelf.cachedData {
+ if let (_, currentComplete, _) = strongSelf.cachedData {
if !currentComplete {
- strongSelf.cachedData = (data, complete)
+ strongSelf.cachedData = (data, complete, source.fitzModifier)
strongSelf.frameSource.with { frameSource in
frameSource?.with { frameSource in
if let frameSource = frameSource.value as? AnimatedStickerCachedFrameSource {
@@ -842,7 +855,7 @@ public final class AnimatedStickerNode: ASDisplayNode {
}
}
} else {
- strongSelf.cachedData = (data, complete)
+ strongSelf.cachedData = (data, complete, source.fitzModifier)
if strongSelf.isPlaying {
strongSelf.play()
} else if strongSelf.canDisplayFirstFrame {
@@ -892,8 +905,8 @@ public final class AnimatedStickerNode: ASDisplayNode {
if maybeFrameSource == nil {
let notifyUpdated: (() -> Void)? = nil
if let directData = directData {
- maybeFrameSource = AnimatedStickerDirectFrameSource(queue: queue, data: directData.0, width: directData.2, height: directData.3, cachePathPrefix: directData.4)
- } else if let (cachedData, cachedDataComplete) = cachedData {
+ maybeFrameSource = AnimatedStickerDirectFrameSource(queue: queue, data: directData.0, width: directData.2, height: directData.3, cachePathPrefix: directData.4, fitzModifier: directData.5)
+ } else if let (cachedData, cachedDataComplete, _) = cachedData {
if #available(iOS 9.0, *) {
maybeFrameSource = AnimatedStickerCachedFrameSource(queue: queue, data: cachedData, complete: cachedDataComplete, notifyUpdated: {
notifyUpdated?()
@@ -964,8 +977,8 @@ public final class AnimatedStickerNode: ASDisplayNode {
var maybeFrameSource: AnimatedStickerFrameSource?
let notifyUpdated: (() -> Void)? = nil
if let directData = directData {
- maybeFrameSource = AnimatedStickerDirectFrameSource(queue: queue, data: directData.0, width: directData.2, height: directData.3, cachePathPrefix: directData.4)
- } else if let (cachedData, cachedDataComplete) = cachedData {
+ maybeFrameSource = AnimatedStickerDirectFrameSource(queue: queue, data: directData.0, width: directData.2, height: directData.3, cachePathPrefix: directData.4, fitzModifier: directData.5)
+ } else if let (cachedData, cachedDataComplete, _) = cachedData {
if #available(iOS 9.0, *) {
maybeFrameSource = AnimatedStickerCachedFrameSource(queue: queue, data: cachedData, complete: cachedDataComplete, notifyUpdated: {
notifyUpdated?()
@@ -1054,11 +1067,11 @@ public final class AnimatedStickerNode: ASDisplayNode {
} else {
var maybeFrameSource: AnimatedStickerFrameSource?
if let directData = directData {
- maybeFrameSource = AnimatedStickerDirectFrameSource(queue: queue, data: directData.0, width: directData.2, height: directData.3, cachePathPrefix: directData.4)
+ maybeFrameSource = AnimatedStickerDirectFrameSource(queue: queue, data: directData.0, width: directData.2, height: directData.3, cachePathPrefix: directData.4, fitzModifier: directData.5)
if case .end = position {
maybeFrameSource?.skipToEnd()
}
- } else if let (cachedData, cachedDataComplete) = cachedData {
+ } else if let (cachedData, cachedDataComplete, _) = cachedData {
if #available(iOS 9.0, *) {
maybeFrameSource = AnimatedStickerCachedFrameSource(queue: queue, data: cachedData, complete: cachedDataComplete, notifyUpdated: {})
}
diff --git a/submodules/AnimatedStickerNode/Sources/FitzModifier.swift b/submodules/AnimatedStickerNode/Sources/FitzModifier.swift
new file mode 100644
index 0000000000..b033905a2c
--- /dev/null
+++ b/submodules/AnimatedStickerNode/Sources/FitzModifier.swift
@@ -0,0 +1,76 @@
+import Foundation
+import UIKit
+import MediaResources
+
+let colorKeyRegex = try? NSRegularExpression(pattern: "\"k\":\\[[\\d\\.]+\\,[\\d\\.]+\\,[\\d\\.]+\\,[\\d\\.]+\\]")
+
+public func transformedWithFitzModifier(data: Data, fitzModifier: EmojiFitzModifier?) -> Data {
+ if let fitzModifier = fitzModifier, var string = String(data: data, encoding: .utf8) {
+ let colors: [UIColor] = [0xf77e41, 0xffb139, 0xffd140, 0xffdf79].map { UIColor(rgb: $0) }
+ let replacementColors: [UIColor]
+ switch fitzModifier {
+ case .type12:
+ replacementColors = [0xca907a, 0xedc5a5, 0xf7e3c3, 0xfbefd6].map { UIColor(rgb: $0) }
+ case .type3:
+ replacementColors = [0xaa7c60, 0xc8a987, 0xddc89f, 0xe6d6b2].map { UIColor(rgb: $0) }
+ case .type4:
+ replacementColors = [0x8c6148, 0xad8562, 0xc49e76, 0xd4b188].map { UIColor(rgb: $0) }
+ case .type5:
+ replacementColors = [0x6e3c2c, 0x925a34, 0xa16e46, 0xac7a52].map { UIColor(rgb: $0) }
+ case .type6:
+ replacementColors = [0x291c12, 0x472a22, 0x573b30, 0x68493c].map { UIColor(rgb: $0) }
+ }
+
+ func colorToString(_ color: UIColor) -> String {
+ var r: CGFloat = 0.0
+ var g: CGFloat = 0.0
+ var b: CGFloat = 0.0
+ if color.getRed(&r, green: &g, blue: &b, alpha: nil) {
+ return "\"k\":[\(r),\(g),\(b),1]"
+ }
+ return ""
+ }
+
+ func match(_ a: Double, _ b: Double, eps: Double) -> Bool {
+ return abs(a - b) < eps
+ }
+
+ var replacements: [(NSTextCheckingResult, String)] = []
+
+ if let colorKeyRegex = colorKeyRegex {
+ let results = colorKeyRegex.matches(in: string, range: NSRange(string.startIndex..., in: string))
+ for result in results.reversed() {
+ if let range = Range(result.range, in: string) {
+ let substring = String(string[range])
+ let color = substring[substring.index(string.startIndex, offsetBy: "\"k\":[".count) ..< substring.index(before: substring.endIndex)]
+ let components = color.split(separator: ",")
+ if components.count == 4, let r = Double(components[0]), let g = Double(components[1]), let b = Double(components[2]), let a = Double(components[3]) {
+ if match(a, 1.0, eps: 0.01) {
+ for i in 0 ..< colors.count {
+ let color = colors[i]
+ var cr: CGFloat = 0.0
+ var cg: CGFloat = 0.0
+ var cb: CGFloat = 0.0
+ if color.getRed(&cr, green: &cg, blue: &cb, alpha: nil) {
+ if match(r, Double(cr), eps: 0.01) && match(g, Double(cg), eps: 0.01) && match(b, Double(cb), eps: 0.01) {
+ replacements.append((result, colorToString(replacementColors[i])))
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+
+ for (result, text) in replacements {
+ if let range = Range(result.range, in: string) {
+ string = string.replacingCharacters(in: range, with: text)
+ }
+ }
+
+ return string.data(using: .utf8) ?? data
+ } else {
+ return data
+ }
+}
diff --git a/submodules/CountrySelectionUI/BUCK b/submodules/CountrySelectionUI/BUCK
index d42c4ed704..03763af9f3 100644
--- a/submodules/CountrySelectionUI/BUCK
+++ b/submodules/CountrySelectionUI/BUCK
@@ -9,6 +9,7 @@ static_library(
"//submodules/SSignalKit/SwiftSignalKit:SwiftSignalKit#shared",
"//submodules/AsyncDisplayKit:AsyncDisplayKit#shared",
"//submodules/Display:Display#shared",
+ "//submodules/TelegramCore:TelegramCore#shared",
"//submodules/TelegramPresentationData:TelegramPresentationData",
"//submodules/TelegramStringFormatting:TelegramStringFormatting",
"//submodules/SearchBarNode:SearchBarNode",
diff --git a/submodules/CountrySelectionUI/BUILD b/submodules/CountrySelectionUI/BUILD
index 7fcc859b8b..368cd0b914 100644
--- a/submodules/CountrySelectionUI/BUILD
+++ b/submodules/CountrySelectionUI/BUILD
@@ -10,6 +10,7 @@ swift_library(
"//submodules/SSignalKit/SwiftSignalKit:SwiftSignalKit",
"//submodules/AsyncDisplayKit:AsyncDisplayKit",
"//submodules/Display:Display",
+ "//submodules/TelegramCore:TelegramCore",
"//submodules/TelegramPresentationData:TelegramPresentationData",
"//submodules/TelegramStringFormatting:TelegramStringFormatting",
"//submodules/SearchBarNode:SearchBarNode",
diff --git a/submodules/CountrySelectionUI/Sources/AuthorizationSequenceCountrySelectionController.swift b/submodules/CountrySelectionUI/Sources/AuthorizationSequenceCountrySelectionController.swift
index 13e2fdbe3c..eadca6c645 100644
--- a/submodules/CountrySelectionUI/Sources/AuthorizationSequenceCountrySelectionController.swift
+++ b/submodules/CountrySelectionUI/Sources/AuthorizationSequenceCountrySelectionController.swift
@@ -2,12 +2,14 @@ import Foundation
import UIKit
import Display
import AsyncDisplayKit
+import SwiftSignalKit
import TelegramPresentationData
import TelegramStringFormatting
import SearchBarNode
import AppBundle
+import TelegramCore
-private func loadCountryCodes() -> [(String, Int)] {
+private func loadCountryCodes() -> [Country] {
guard let filePath = getAppBundle().path(forResource: "PhoneCountries", ofType: "txt") else {
return []
}
@@ -21,10 +23,12 @@ private func loadCountryCodes() -> [(String, Int)] {
let delimiter = ";"
let endOfLine = "\n"
- var result: [(String, Int)] = []
+ var result: [Country] = []
var currentLocation = data.startIndex
+ let locale = Locale(identifier: "en-US")
+
while true {
guard let codeRange = data.range(of: delimiter, options: [], range: currentLocation ..< data.endIndex) else {
break
@@ -40,8 +44,9 @@ private func loadCountryCodes() -> [(String, Int)] {
let maybeNameRange = data.range(of: endOfLine, options: [], range: idRange.upperBound ..< data.endIndex)
+ let countryName = locale.localizedString(forIdentifier: countryId) ?? ""
if let countryCodeInt = Int(countryCode) {
- result.append((countryId, countryCodeInt))
+ result.append(Country(code: countryId, defaultName: countryName, name: countryName, countryCodes: [Country.CountryCode(code: countryCode, prefixes: [], patterns: [])]))
}
if let maybeNameRange = maybeNameRange {
@@ -54,7 +59,14 @@ private func loadCountryCodes() -> [(String, Int)] {
return result
}
-private let countryCodes: [(String, Int)] = loadCountryCodes()
+private var countryCodes: [Country] = loadCountryCodes()
+
+public func loadServerCountryCodes(network: Network) {
+ let _ = (getCountriesList(network: network, langCode: "")
+ |> deliverOnMainQueue).start(next: { countries in
+ countryCodes = countries
+ })
+}
private final class AuthorizationSequenceCountrySelectionNavigationContentNode: NavigationBarContentNode {
private let theme: PresentationTheme
@@ -117,8 +129,8 @@ private final class AuthorizationSequenceCountrySelectionNavigationContentNode:
public final class AuthorizationSequenceCountrySelectionController: ViewController {
public static func lookupCountryNameById(_ id: String, strings: PresentationStrings) -> String? {
- for (itemId, _) in countryCodes {
- if id == itemId {
+ for country in countryCodes {
+ if id == country.code {
let locale = localeWithStrings(strings)
if let countryName = locale.localizedString(forRegionCode: id) {
return countryName
@@ -131,9 +143,22 @@ public final class AuthorizationSequenceCountrySelectionController: ViewControll
}
public static func lookupCountryIdByCode(_ code: Int) -> String? {
- for (itemId, itemCode) in countryCodes {
- if itemCode == code {
- return itemId
+ for country in countryCodes {
+ for countryCode in country.countryCodes {
+ if countryCode.code == "\(code)" {
+ return country.code
+ }
+ }
+ }
+ return nil
+ }
+
+ public static func lookupPatternByCode(_ code: Int) -> String? {
+ for country in countryCodes {
+ for countryCode in country.countryCodes {
+ if countryCode.code == "\(code)" {
+ return countryCode.patterns.first
+ }
}
}
return nil
diff --git a/submodules/Display/Source/Font.swift b/submodules/Display/Source/Font.swift
index 0a9779afb6..674197bfea 100644
--- a/submodules/Display/Source/Font.swift
+++ b/submodules/Display/Source/Font.swift
@@ -22,6 +22,7 @@ public struct Font {
public static let bold = Traits(rawValue: 1 << 0)
public static let italic = Traits(rawValue: 1 << 1)
+ public static let monospacedNumbers = Traits(rawValue: 1 << 2)
}
public enum Weight {
@@ -43,6 +44,15 @@ public struct Font {
symbolicTraits.insert(.traitItalic)
}
var updatedDescriptor: UIFontDescriptor? = descriptor.withSymbolicTraits(symbolicTraits)
+ if traits.contains(.monospacedNumbers) {
+ updatedDescriptor = descriptor.addingAttributes([
+ UIFontDescriptor.AttributeName.featureSettings: [
+ [UIFontDescriptor.FeatureKey.featureIdentifier:
+ kNumberSpacingType,
+ UIFontDescriptor.FeatureKey.typeIdentifier:
+ kMonospacedNumbersSelector]
+ ]])
+ }
switch design {
case .serif:
updatedDescriptor = updatedDescriptor?.withDesign(.serif)
diff --git a/submodules/LegacyComponents/Sources/TGMediaPickerGalleryVideoItemView.m b/submodules/LegacyComponents/Sources/TGMediaPickerGalleryVideoItemView.m
index 84c7f381d7..208a6df4a3 100644
--- a/submodules/LegacyComponents/Sources/TGMediaPickerGalleryVideoItemView.m
+++ b/submodules/LegacyComponents/Sources/TGMediaPickerGalleryVideoItemView.m
@@ -1461,13 +1461,13 @@
NSMutableArray *actions = [[NSMutableArray alloc] init];
NSString *text = [self itemIsLivePhoto] ? TGLocalized(@"MediaPicker.LivePhotoDescription") : TGLocalized(@"MediaPicker.VideoMuteDescription");
[actions addObject:@{@"title":text}];
- _tooltipContainerView.menuView.forceArrowOnTop = true;
+ _tooltipContainerView.menuView.forceArrowOnTop = false;
_tooltipContainerView.menuView.multiline = true;
[_tooltipContainerView.menuView setButtonsAndActions:actions watcherHandle:nil];
_tooltipContainerView.menuView.buttonHighlightDisabled = true;
[_tooltipContainerView.menuView sizeToFit];
- CGRect iconViewFrame = CGRectMake(12, 188 + _safeAreaInset.top, 40, 40);
+ CGRect iconViewFrame = CGRectMake(12, self.frame.size.height - 192.0 - _safeAreaInset.bottom, 40, 40);
[_tooltipContainerView showMenuFromRect:iconViewFrame animated:false];
}
diff --git a/submodules/PeerInfoUI/Sources/ChannelOwnershipTransferController.swift b/submodules/PeerInfoUI/Sources/ChannelOwnershipTransferController.swift
index b8ff2dde96..2dc4cd0c0f 100644
--- a/submodules/PeerInfoUI/Sources/ChannelOwnershipTransferController.swift
+++ b/submodules/PeerInfoUI/Sources/ChannelOwnershipTransferController.swift
@@ -173,12 +173,12 @@ private final class ChannelOwnershipTransferPasswordFieldNode: ASDisplayNode, UI
}
}
-private final class ChannelOwnershipTransferAlertContentNode: AlertContentNode {
+public final class ChannelOwnershipTransferAlertContentNode: AlertContentNode {
private let strings: PresentationStrings
private let titleNode: ASTextNode
private let textNode: ASTextNode
- let inputFieldNode: ChannelOwnershipTransferPasswordFieldNode
+ fileprivate let inputFieldNode: ChannelOwnershipTransferPasswordFieldNode
private let actionNodesSeparator: ASDisplayNode
private let actionNodes: [TextAlertContentActionNode]
@@ -190,18 +190,25 @@ private final class ChannelOwnershipTransferAlertContentNode: AlertContentNode {
private let hapticFeedback = HapticFeedback()
- var complete: (() -> Void)? {
+ public var complete: (() -> Void)? {
didSet {
self.inputFieldNode.complete = self.complete
}
}
- override var dismissOnOutsideTap: Bool {
+ public var theme: PresentationTheme {
+ didSet {
+ self.inputFieldNode.updateTheme(self.theme)
+ }
+ }
+
+ public override var dismissOnOutsideTap: Bool {
return self.isUserInteractionEnabled
}
- init(theme: AlertControllerTheme, ptheme: PresentationTheme, strings: PresentationStrings, actions: [TextAlertAction]) {
+ public init(theme: AlertControllerTheme, ptheme: PresentationTheme, strings: PresentationStrings, actions: [TextAlertAction]) {
self.strings = strings
+ self.theme = ptheme
self.titleNode = ASTextNode()
self.titleNode.maximumNumberOfLines = 2
@@ -258,19 +265,19 @@ private final class ChannelOwnershipTransferAlertContentNode: AlertContentNode {
self.disposable.dispose()
}
- func dismissInput() {
+ public func dismissInput() {
self.inputFieldNode.deactivateInput()
}
- var password: String {
+ public var password: String {
return self.inputFieldNode.password
}
- func updateIsChecking(_ checking: Bool) {
+ public func updateIsChecking(_ checking: Bool) {
self.inputFieldNode.updateIsChecking(checking)
}
- override func updateTheme(_ theme: AlertControllerTheme) {
+ public override func updateTheme(_ theme: AlertControllerTheme) {
self.titleNode.attributedText = NSAttributedString(string: self.strings.Channel_OwnershipTransfer_EnterPassword, font: Font.bold(17.0), textColor: theme.primaryColor, paragraphAlignment: .center)
self.textNode.attributedText = NSAttributedString(string: self.strings.Channel_OwnershipTransfer_EnterPasswordText, font: Font.regular(13.0), textColor: theme.primaryColor, paragraphAlignment: .center)
@@ -281,13 +288,13 @@ private final class ChannelOwnershipTransferAlertContentNode: AlertContentNode {
for separatorNode in self.actionVerticalSeparators {
separatorNode.backgroundColor = theme.separatorColor
}
-
+
if let size = self.validLayout {
_ = self.updateLayout(size: size, transition: .immediate)
}
}
- override func updateLayout(size: CGSize, transition: ContainedViewLayoutTransition) -> CGSize {
+ public override func updateLayout(size: CGSize, transition: ContainedViewLayoutTransition) -> CGSize {
var size = size
size.width = min(size.width, 270.0)
let measureSize = CGSize(width: size.width - 16.0 * 2.0, height: CGFloat.greatestFiniteMagnitude)
@@ -400,7 +407,7 @@ private final class ChannelOwnershipTransferAlertContentNode: AlertContentNode {
return resultSize
}
- func animateError() {
+ public func animateError() {
self.inputFieldNode.updateIsInvalid()
self.inputFieldNode.layer.addShakeAnimation()
self.hapticFeedback.error()
diff --git a/submodules/PhoneInputNode/Sources/PhoneInputNode.swift b/submodules/PhoneInputNode/Sources/PhoneInputNode.swift
index 47bdad1865..f68af967e8 100644
--- a/submodules/PhoneInputNode/Sources/PhoneInputNode.swift
+++ b/submodules/PhoneInputNode/Sources/PhoneInputNode.swift
@@ -76,9 +76,24 @@ private func cleanSuffix(_ text: String) -> String {
return result
}
+extension String {
+ func applyPatternOnNumbers(pattern: String, replacementCharacter: Character) -> String {
+ var pureNumber = self.replacingOccurrences( of: "[^0-9]", with: "", options: .regularExpression)
+ for index in 0 ..< pattern.count {
+ guard index < pureNumber.count else { return pureNumber }
+ let stringIndex = String.Index(encodedOffset: index)
+ let patternCharacter = pattern[stringIndex]
+ guard patternCharacter != replacementCharacter else { continue }
+ pureNumber.insert(patternCharacter, at: stringIndex)
+ }
+ return pureNumber
+ }
+}
+
public final class PhoneInputNode: ASDisplayNode, UITextFieldDelegate {
public let countryCodeField: TextFieldNode
public let numberField: TextFieldNode
+ public let placeholderNode: ImmediateTextNode
public var previousCountryCodeText = "+"
public var previousNumberText = ""
@@ -151,13 +166,33 @@ public final class PhoneInputNode: ASDisplayNode, UITextFieldDelegate {
private let phoneFormatter = InteractivePhoneFormatter()
+ public var mask: NSAttributedString? {
+ didSet {
+ self.updatePlaceholder()
+ }
+ }
+
+ private func updatePlaceholder() {
+ if let mask = self.mask {
+ let mutableMask = NSMutableAttributedString(attributedString: mask)
+ mutableMask.replaceCharacters(in: NSRange(location: 0, length: mask.string.count), with: mask.string.replacingOccurrences(of: "X", with: "-"))
+ mutableMask.addAttribute(.foregroundColor, value: UIColor.clear, range: NSRange(location: 0, length: min(self.numberField.textField.text?.count ?? 0, mask.string.count)))
+ self.placeholderNode.attributedText = mutableMask
+ } else {
+ self.placeholderNode.attributedText = NSAttributedString(string: "")
+ }
+ let _ = self.placeholderNode.updateLayout(CGSize(width: self.frame.size.width, height: CGFloat.greatestFiniteMagnitude))
+ }
+
private let fontSize: CGFloat
public init(fontSize: CGFloat = 20.0) {
self.fontSize = fontSize
+ let font = Font.with(size: fontSize, design: .regular, traits: [.monospacedNumbers])
+
self.countryCodeField = TextFieldNode()
- self.countryCodeField.textField.font = Font.regular(fontSize)
+ self.countryCodeField.textField.font = font
self.countryCodeField.textField.textAlignment = .center
self.countryCodeField.textField.returnKeyType = .next
if #available(iOSApplicationExtension 10.0, iOS 10.0, *) {
@@ -167,18 +202,21 @@ public final class PhoneInputNode: ASDisplayNode, UITextFieldDelegate {
self.countryCodeField.textField.keyboardType = .numberPad
}
+ self.placeholderNode = ImmediateTextNode()
+
self.numberField = TextFieldNode()
- self.numberField.textField.font = Font.regular(fontSize)
+ self.numberField.textField.font = font
if #available(iOSApplicationExtension 10.0, iOS 10.0, *) {
self.numberField.textField.keyboardType = .asciiCapableNumberPad
self.numberField.textField.textContentType = .telephoneNumber
} else {
self.numberField.textField.keyboardType = .numberPad
}
-
+ self.numberField.textField.defaultTextAttributes = [NSAttributedString.Key.font: font, NSAttributedString.Key.kern: 2.0]
super.init()
self.addSubnode(self.countryCodeField)
+ self.addSubnode(self.placeholderNode)
self.addSubnode(self.numberField)
self.numberField.textField.didDeleteBackwardWhileEmpty = { [weak self] in
@@ -223,8 +261,9 @@ public final class PhoneInputNode: ASDisplayNode, UITextFieldDelegate {
private func updateNumber(_ inputText: String, tryRestoringInputPosition: Bool = true, forceNotifyCountryCodeUpdated: Bool = false) {
let (regionPrefix, text) = self.phoneFormatter.updateText(inputText)
+
var realRegionPrefix: String
- let numberText: String
+ var numberText: String
if let regionPrefix = regionPrefix, !regionPrefix.isEmpty, regionPrefix != "+" {
realRegionPrefix = cleanSuffix(regionPrefix)
if !realRegionPrefix.hasPrefix("+") {
@@ -239,6 +278,10 @@ public final class PhoneInputNode: ASDisplayNode, UITextFieldDelegate {
numberText = ""
}
+ if let mask = self.mask {
+ numberText = numberText.applyPatternOnNumbers(pattern: mask.string, replacementCharacter: "X")
+ }
+
var focusOnNumber = false
if realRegionPrefix != self.countryCodeField.textField.text {
self.countryCodeField.textField.text = realRegionPrefix
@@ -296,5 +339,7 @@ public final class PhoneInputNode: ASDisplayNode, UITextFieldDelegate {
if focusOnNumber && !self.numberField.textField.isFirstResponder {
self.numberField.textField.becomeFirstResponder()
}
+
+ self.updatePlaceholder()
}
}
diff --git a/submodules/ShareController/Sources/ShareController.swift b/submodules/ShareController/Sources/ShareController.swift
index c87d6f1d32..f9ceae7bb1 100644
--- a/submodules/ShareController/Sources/ShareController.swift
+++ b/submodules/ShareController/Sources/ShareController.swift
@@ -593,6 +593,27 @@ public final class ShareController: ViewController {
}
self.controllerNode.shareExternal = { [weak self] in
if let strongSelf = self {
+ if case let .messages(messages) = strongSelf.subject, let message = messages.first, let peer = message.peers[message.id.peerId] {
+ let renderer = MessageStoryRenderer(context: strongSelf.currentContext, messages: messages)
+
+ let layout = ContainerViewLayout(size: CGSize(width: 414.0, height: 896.0), metrics: LayoutMetrics(widthClass: .compact, heightClass: .compact), deviceMetrics: .iPhoneX, intrinsicInsets: UIEdgeInsets(), safeInsets: UIEdgeInsets(), statusBarHeight: 0.0, inputHeight: nil, inputHeightIsInteractivellyChanging: false, inVoiceOver: false)
+ renderer.update(layout: layout) { image in
+ if let data = image?.pngData() {
+ let pasteboardItems: [[String: Any]] = [["com.instagram.sharedSticker.backgroundImage": data,
+ "com.instagram.sharedSticker.contentURL": "https://t.me/\(peer.addressName ?? "")/\(message.id.id)"]]
+ if #available(iOS 10.0, *) {
+ UIPasteboard.general.setItems(pasteboardItems, options: [.expirationDate: Date().addingTimeInterval(5 * 60)])
+ } else {
+// UIPasteboard.general.setItems(pasteboardItems)
+ }
+ strongSelf.sharedContext.applicationBindings.openUrl("instagram-stories://share")
+ }
+ }
+
+ return .complete()
+ }
+
+
var collectableItems: [CollectableExternalShareItem] = []
switch strongSelf.subject {
case let .url(text):
@@ -865,3 +886,137 @@ public final class ShareController: ViewController {
}))
}
}
+
+
+class MessageStoryRenderer {
+ private let context: AccountContext
+ private let presentationData: PresentationData
+ private let messages: [Message]
+
+ let containerNode: ASDisplayNode
+ private let instantChatBackgroundNode: WallpaperBackgroundNode
+ private let messagesContainerNode: ASDisplayNode
+ private var dateHeaderNode: ListViewItemHeaderNode?
+ private var messageNodes: [ListViewItemNode]?
+ private let addressNode: ImmediateTextNode
+
+ init(context: AccountContext, messages: [Message]) {
+ self.context = context
+ self.presentationData = context.sharedContext.currentPresentationData.with { $0 }
+ self.messages = messages
+
+ self.containerNode = ASDisplayNode()
+
+ self.instantChatBackgroundNode = WallpaperBackgroundNode()
+ self.instantChatBackgroundNode.displaysAsynchronously = false
+ self.instantChatBackgroundNode.image = chatControllerBackgroundImage(theme: presentationData.theme, wallpaper: .builtin(WallpaperSettings()), mediaBox: context.sharedContext.accountManager.mediaBox, knockoutMode: context.sharedContext.immediateExperimentalUISettings.knockoutWallpaper)
+
+ self.messagesContainerNode = ASDisplayNode()
+ self.messagesContainerNode.clipsToBounds = true
+ self.messagesContainerNode.transform = CATransform3DMakeScale(1.0, -1.0, 1.0)
+
+ let message = messages.first!
+ let addressName = message.peers[message.id.peerId]?.addressName ?? ""
+
+ self.addressNode = ImmediateTextNode()
+ self.addressNode.displaysAsynchronously = false
+ self.addressNode.attributedText = NSAttributedString(string: "t.me/\(addressName)/\(message.id.id)", font: Font.medium(14.0), textColor: UIColor(rgb: 0xa8b7c4))
+// self.addressNode.textShadowColor = .black
+
+ self.containerNode.addSubnode(self.instantChatBackgroundNode)
+ self.containerNode.addSubnode(self.messagesContainerNode)
+ self.containerNode.addSubnode(self.addressNode)
+ }
+
+ func update(layout: ContainerViewLayout, completion: @escaping (UIImage?) -> Void) {
+ self.updateMessagesLayout(layout: layout)
+
+ Queue.mainQueue().after(0.01) {
+ UIGraphicsBeginImageContextWithOptions(layout.size, false, 3.0)
+ self.containerNode.view.drawHierarchy(in: CGRect(origin: CGPoint(), size: layout.size), afterScreenUpdates: true)
+ let img = UIGraphicsGetImageFromCurrentImageContext()
+ UIGraphicsEndImageContext()
+ completion(img)
+ }
+ }
+
+ private func updateMessagesLayout(layout: ContainerViewLayout) {
+ let size = layout.size
+ self.containerNode.frame = CGRect(origin: CGPoint(), size: layout.size)
+ self.instantChatBackgroundNode.frame = CGRect(origin: CGPoint(), size: layout.size)
+ self.instantChatBackgroundNode.updateLayout(size: size, transition: .immediate)
+ self.messagesContainerNode.frame = CGRect(origin: CGPoint(), size: layout.size)
+
+ let addressLayout = self.addressNode.updateLayout(size)
+
+ let theme = self.presentationData.theme.withUpdated(preview: true)
+ let headerItem = self.context.sharedContext.makeChatMessageDateHeaderItem(context: self.context, timestamp: self.messages.first?.timestamp ?? 0, theme: theme, strings: self.presentationData.strings, wallpaper: self.presentationData.chatWallpaper, fontSize: self.presentationData.chatFontSize, chatBubbleCorners: self.presentationData.chatBubbleCorners, dateTimeFormat: self.presentationData.dateTimeFormat, nameOrder: self.presentationData.nameDisplayOrder)
+
+ var items: [ListViewItem] = []
+ let sampleMessages: [Message] = self.messages
+
+ items = sampleMessages.reversed().map { message in
+ self.context.sharedContext.makeChatMessagePreviewItem(context: self.context, message: message, theme: theme, strings: self.presentationData.strings, wallpaper: self.presentationData.theme.chat.defaultWallpaper, fontSize: self.presentationData.chatFontSize, chatBubbleCorners: self.presentationData.chatBubbleCorners, dateTimeFormat: self.presentationData.dateTimeFormat, nameOrder: self.presentationData.nameDisplayOrder, forcedResourceStatus: nil, tapMessage: nil, clickThroughMessage: nil)
+ }
+
+ let inset: CGFloat = 16.0
+ let width = layout.size.width - inset * 2.0
+ let params = ListViewItemLayoutParams(width: width, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right, availableHeight: layout.size.height)
+ if let messageNodes = self.messageNodes {
+ for i in 0 ..< items.count {
+ let itemNode = messageNodes[i]
+ items[i].updateNode(async: { $0() }, node: {
+ return itemNode
+ }, params: params, previousItem: i == 0 ? nil : items[i - 1], nextItem: i == (items.count - 1) ? nil : items[i + 1], animation: .None, completion: { (layout, apply) in
+ let nodeFrame = CGRect(origin: CGPoint(x: 0.0, y: floor((size.height - layout.size.height) / 2.0)), size: CGSize(width: width, height: layout.size.height))
+
+ itemNode.contentSize = layout.contentSize
+ itemNode.insets = layout.insets
+ itemNode.frame = nodeFrame
+ itemNode.isUserInteractionEnabled = false
+
+ apply(ListViewItemApply(isOnScreen: true))
+ })
+ }
+ } else {
+ var messageNodes: [ListViewItemNode] = []
+ for i in 0 ..< items.count {
+ var itemNode: ListViewItemNode?
+ items[i].nodeConfiguredForParams(async: { $0() }, params: params, synchronousLoads: true, previousItem: i == 0 ? nil : items[i - 1], nextItem: i == (items.count - 1) ? nil : items[i + 1], completion: { node, apply in
+ itemNode = node
+ apply().1(ListViewItemApply(isOnScreen: true))
+ })
+ itemNode!.subnodeTransform = CATransform3DMakeScale(-1.0, 1.0, 1.0)
+ itemNode!.isUserInteractionEnabled = false
+ messageNodes.append(itemNode!)
+ self.messagesContainerNode.addSubnode(itemNode!)
+ }
+ self.messageNodes = messageNodes
+ }
+
+ var bottomOffset: CGFloat = 0.0
+ if let messageNodes = self.messageNodes {
+ for itemNode in messageNodes {
+ itemNode.frame = CGRect(origin: CGPoint(x: inset, y: floor((size.height - itemNode.frame.height) / 2.0)), size: itemNode.frame.size)
+ bottomOffset += itemNode.frame.maxY
+ itemNode.updateFrame(itemNode.frame, within: layout.size)
+ }
+ }
+
+ self.addressNode.frame = CGRect(origin: CGPoint(x: inset + 16.0, y: bottomOffset + 3.0), size: CGSize(width: addressLayout.width, height: addressLayout.height + 3.0))
+
+ let dateHeaderNode: ListViewItemHeaderNode
+ if let currentDateHeaderNode = self.dateHeaderNode {
+ dateHeaderNode = currentDateHeaderNode
+ headerItem.updateNode(dateHeaderNode, previous: nil, next: headerItem)
+ } else {
+ dateHeaderNode = headerItem.node()
+ dateHeaderNode.subnodeTransform = CATransform3DMakeScale(-1.0, 1.0, 1.0)
+ self.messagesContainerNode.addSubnode(dateHeaderNode)
+ self.dateHeaderNode = dateHeaderNode
+ }
+
+ dateHeaderNode.frame = CGRect(origin: CGPoint(x: 0.0, y: bottomOffset), size: CGSize(width: layout.size.width, height: headerItem.height))
+ dateHeaderNode.updateLayout(size: self.containerNode.frame.size, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right)
+ }
+}
diff --git a/submodules/SyncCore/Sources/ReplyMarkupMessageAttribute.swift b/submodules/SyncCore/Sources/ReplyMarkupMessageAttribute.swift
index c72fdced40..d1eb42c27c 100644
--- a/submodules/SyncCore/Sources/ReplyMarkupMessageAttribute.swift
+++ b/submodules/SyncCore/Sources/ReplyMarkupMessageAttribute.swift
@@ -3,7 +3,7 @@ import Postbox
public enum ReplyMarkupButtonAction: PostboxCoding, Equatable {
case text
case url(String)
- case callback(MemoryBuffer)
+ case callback(requiresPassword: Bool, data: MemoryBuffer)
case requestPhone
case requestMap
case switchInline(samePeer: Bool, query: String)
@@ -19,7 +19,7 @@ public enum ReplyMarkupButtonAction: PostboxCoding, Equatable {
case 1:
self = .url(decoder.decodeStringForKey("u", orElse: ""))
case 2:
- self = .callback(decoder.decodeBytesForKey("d") ?? MemoryBuffer())
+ self = .callback(requiresPassword: decoder.decodeInt32ForKey("p", orElse: 0) != 0, data: decoder.decodeBytesForKey("d") ?? MemoryBuffer())
case 3:
self = .requestPhone
case 4:
@@ -46,8 +46,9 @@ public enum ReplyMarkupButtonAction: PostboxCoding, Equatable {
case let .url(url):
encoder.encodeInt32(1, forKey: "v")
encoder.encodeString(url, forKey: "u")
- case let .callback(data):
+ case let .callback(requiresPassword, data):
encoder.encodeInt32(2, forKey: "v")
+ encoder.encodeInt32(requiresPassword ? 1 : 0, forKey: "p")
encoder.encodeBytes(data, forKey: "d")
case .requestPhone:
encoder.encodeInt32(3, forKey: "v")
diff --git a/submodules/TelegramAnimatedStickerNode/Sources/AnimatedStickerUtils.swift b/submodules/TelegramAnimatedStickerNode/Sources/AnimatedStickerUtils.swift
index 206574e171..d39c63244e 100644
--- a/submodules/TelegramAnimatedStickerNode/Sources/AnimatedStickerUtils.swift
+++ b/submodules/TelegramAnimatedStickerNode/Sources/AnimatedStickerUtils.swift
@@ -12,79 +12,7 @@ import MediaResources
import MobileCoreServices
import MediaResources
import YuvConversion
-
-let colorKeyRegex = try? NSRegularExpression(pattern: "\"k\":\\[[\\d\\.]+\\,[\\d\\.]+\\,[\\d\\.]+\\,[\\d\\.]+\\]")
-
-private func transformedWithFitzModifier(data: Data, fitzModifier: EmojiFitzModifier?) -> Data {
- if let fitzModifier = fitzModifier, var string = String(data: data, encoding: .utf8) {
- var colors: [UIColor] = [0xf77e41, 0xffb139, 0xffd140, 0xffdf79].map { UIColor(rgb: $0) }
- let replacementColors: [UIColor]
- switch fitzModifier {
- case .type12:
- replacementColors = [0xca907a, 0xedc5a5, 0xf7e3c3, 0xfbefd6].map { UIColor(rgb: $0) }
- case .type3:
- replacementColors = [0xaa7c60, 0xc8a987, 0xddc89f, 0xe6d6b2].map { UIColor(rgb: $0) }
- case .type4:
- replacementColors = [0x8c6148, 0xad8562, 0xc49e76, 0xd4b188].map { UIColor(rgb: $0) }
- case .type5:
- replacementColors = [0x6e3c2c, 0x925a34, 0xa16e46, 0xac7a52].map { UIColor(rgb: $0) }
- case .type6:
- replacementColors = [0x291c12, 0x472a22, 0x573b30, 0x68493c].map { UIColor(rgb: $0) }
- }
-
- func colorToString(_ color: UIColor) -> String {
- var r: CGFloat = 0.0
- var g: CGFloat = 0.0
- var b: CGFloat = 0.0
- if color.getRed(&r, green: &g, blue: &b, alpha: nil) {
- return "\"k\":[\(r),\(g),\(b),1]"
- }
- return ""
- }
-
- func match(_ a: Double, _ b: Double, eps: Double) -> Bool {
- return abs(a - b) < eps
- }
-
- var replacements: [(NSTextCheckingResult, String)] = []
-
- if let colorKeyRegex = colorKeyRegex {
- let results = colorKeyRegex.matches(in: string, range: NSRange(string.startIndex..., in: string))
- for result in results.reversed() {
- if let range = Range(result.range, in: string) {
- let substring = String(string[range])
- let color = substring[substring.index(string.startIndex, offsetBy: "\"k\":[".count) ..< substring.index(before: substring.endIndex)]
- let components = color.split(separator: ",")
- if components.count == 4, let r = Double(components[0]), let g = Double(components[1]), let b = Double(components[2]), let a = Double(components[3]) {
- if match(a, 1.0, eps: 0.01) {
- for i in 0 ..< colors.count {
- let color = colors[i]
- var cr: CGFloat = 0.0
- var cg: CGFloat = 0.0
- var cb: CGFloat = 0.0
- if color.getRed(&cr, green: &cg, blue: &cb, alpha: nil) {
- if match(r, Double(cr), eps: 0.01) && match(g, Double(cg), eps: 0.01) && match(b, Double(cb), eps: 0.01) {
- replacements.append((result, colorToString(replacementColors[i])))
- }
- }
- }
- }
- }
- }
- }
- }
-
- for (result, text) in replacements {
- if let range = Range(result.range, in: string) {
- string = string.replacingCharacters(in: range, with: text)
- }
- }
-
- return string.data(using: .utf8) ?? data
- } else {
- return data
- }
-}
+import AnimatedStickerNode
public func fetchCompressedLottieFirstFrameAJpeg(data: Data, size: CGSize, fitzModifier: EmojiFitzModifier? = nil, cacheKey: String) -> Signal {
return Signal({ subscriber in
diff --git a/submodules/TelegramApi/Sources/Api0.swift b/submodules/TelegramApi/Sources/Api0.swift
index f36922f701..7eb6f16d2b 100644
--- a/submodules/TelegramApi/Sources/Api0.swift
+++ b/submodules/TelegramApi/Sources/Api0.swift
@@ -255,6 +255,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[889491791] = { return Api.Update.parse_updateDialogFilters($0) }
dict[643940105] = { return Api.Update.parse_updatePhoneCallSignalingData($0) }
dict[1708307556] = { return Api.Update.parse_updateChannelParticipant($0) }
+ dict[1854571743] = { return Api.Update.parse_updateChannelMessageForwards($0) }
dict[136574537] = { return Api.messages.VotesList.parse_votesList($0) }
dict[1558266229] = { return Api.PopularContact.parse_popularContact($0) }
dict[-373643672] = { return Api.FolderPeer.parse_folderPeer($0) }
@@ -273,7 +274,6 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[-994444869] = { return Api.Error.parse_error($0) }
dict[-1560655744] = { return Api.KeyboardButton.parse_keyboardButton($0) }
dict[629866245] = { return Api.KeyboardButton.parse_keyboardButtonUrl($0) }
- dict[1748655686] = { return Api.KeyboardButton.parse_keyboardButtonCallback($0) }
dict[-1318425559] = { return Api.KeyboardButton.parse_keyboardButtonRequestPhone($0) }
dict[-59151553] = { return Api.KeyboardButton.parse_keyboardButtonRequestGeoLocation($0) }
dict[90744648] = { return Api.KeyboardButton.parse_keyboardButtonSwitchInline($0) }
@@ -282,6 +282,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[280464681] = { return Api.KeyboardButton.parse_keyboardButtonUrlAuth($0) }
dict[-802258988] = { return Api.KeyboardButton.parse_inputKeyboardButtonUrlAuth($0) }
dict[-1144565411] = { return Api.KeyboardButton.parse_keyboardButtonRequestPoll($0) }
+ dict[901503851] = { return Api.KeyboardButton.parse_keyboardButtonCallback($0) }
dict[-748155807] = { return Api.ContactStatus.parse_contactStatus($0) }
dict[1679398724] = { return Api.SecureFile.parse_secureFileEmpty($0) }
dict[-534283678] = { return Api.SecureFile.parse_secureFile($0) }
@@ -387,6 +388,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[1694474197] = { return Api.messages.Chats.parse_chats($0) }
dict[-1663561404] = { return Api.messages.Chats.parse_chatsSlice($0) }
dict[482797855] = { return Api.InputSingleMedia.parse_inputSingleMedia($0) }
+ dict[1831138451] = { return Api.MessageViews.parse_messageViews($0) }
dict[218751099] = { return Api.InputPrivacyRule.parse_inputPrivacyValueAllowContacts($0) }
dict[407582158] = { return Api.InputPrivacyRule.parse_inputPrivacyValueAllowAll($0) }
dict[320652927] = { return Api.InputPrivacyRule.parse_inputPrivacyValueAllowUsers($0) }
@@ -447,6 +449,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[-524237339] = { return Api.PageTableRow.parse_pageTableRow($0) }
dict[-40996577] = { return Api.DraftMessage.parse_draftMessage($0) }
dict[453805082] = { return Api.DraftMessage.parse_draftMessageEmpty($0) }
+ dict[-77073091] = { return Api.help.Country.parse_country($0) }
dict[418631927] = { return Api.StatsGroupTopPoster.parse_statsGroupTopPoster($0) }
dict[-2128640689] = { return Api.account.SentEmailCode.parse_sentEmailCode($0) }
dict[-1038136962] = { return Api.EncryptedFile.parse_encryptedFileEmpty($0) }
@@ -519,6 +522,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[-914167110] = { return Api.CdnPublicKey.parse_cdnPublicKey($0) }
dict[53231223] = { return Api.InputGame.parse_inputGameID($0) }
dict[-1020139510] = { return Api.InputGame.parse_inputGameShortName($0) }
+ dict[1107543535] = { return Api.help.CountryCode.parse_countryCode($0) }
dict[-1502174430] = { return Api.InputMessage.parse_inputMessageID($0) }
dict[-1160215659] = { return Api.InputMessage.parse_inputMessageReplyTo($0) }
dict[-2037963464] = { return Api.InputMessage.parse_inputMessagePinned($0) }
@@ -598,7 +602,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[-1820043071] = { return Api.User.parse_user($0) }
dict[-2082087340] = { return Api.Message.parse_messageEmpty($0) }
dict[-1642487306] = { return Api.Message.parse_messageService($0) }
- dict[1160515173] = { return Api.Message.parse_message($0) }
+ dict[-181507201] = { return Api.Message.parse_message($0) }
dict[831924812] = { return Api.StatsGroupTopInviter.parse_statsGroupTopInviter($0) }
dict[186120336] = { return Api.messages.RecentStickers.parse_recentStickersNotModified($0) }
dict[586395571] = { return Api.messages.RecentStickers.parse_recentStickers($0) }
@@ -683,6 +687,7 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[364538944] = { return Api.messages.Dialogs.parse_dialogs($0) }
dict[1910543603] = { return Api.messages.Dialogs.parse_dialogsSlice($0) }
dict[-253500010] = { return Api.messages.Dialogs.parse_dialogsNotModified($0) }
+ dict[-1986399595] = { return Api.stats.MessageStats.parse_messageStats($0) }
dict[-709641735] = { return Api.EmojiKeyword.parse_emojiKeyword($0) }
dict[594408994] = { return Api.EmojiKeyword.parse_emojiKeywordDeleted($0) }
dict[-290921362] = { return Api.upload.CdnFile.parse_cdnFileReuploadNeeded($0) }
@@ -789,6 +794,8 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[1041346555] = { return Api.updates.ChannelDifference.parse_channelDifferenceEmpty($0) }
dict[543450958] = { return Api.updates.ChannelDifference.parse_channelDifference($0) }
dict[-1531132162] = { return Api.updates.ChannelDifference.parse_channelDifferenceTooLong($0) }
+ dict[-1815339214] = { return Api.help.CountriesList.parse_countriesListNotModified($0) }
+ dict[-2016381538] = { return Api.help.CountriesList.parse_countriesList($0) }
dict[-309659827] = { return Api.channels.AdminLogResults.parse_adminLogResults($0) }
dict[-264117680] = { return Api.ChatOnlines.parse_chatOnlines($0) }
dict[488313413] = { return Api.InputAppEvent.parse_inputAppEvent($0) }
@@ -1106,6 +1113,8 @@ public struct Api {
_1.serialize(buffer, boxed)
case let _1 as Api.InputSingleMedia:
_1.serialize(buffer, boxed)
+ case let _1 as Api.MessageViews:
+ _1.serialize(buffer, boxed)
case let _1 as Api.InputPrivacyRule:
_1.serialize(buffer, boxed)
case let _1 as Api.messages.DhConfig:
@@ -1148,6 +1157,8 @@ public struct Api {
_1.serialize(buffer, boxed)
case let _1 as Api.DraftMessage:
_1.serialize(buffer, boxed)
+ case let _1 as Api.help.Country:
+ _1.serialize(buffer, boxed)
case let _1 as Api.StatsGroupTopPoster:
_1.serialize(buffer, boxed)
case let _1 as Api.account.SentEmailCode:
@@ -1226,6 +1237,8 @@ public struct Api {
_1.serialize(buffer, boxed)
case let _1 as Api.InputGame:
_1.serialize(buffer, boxed)
+ case let _1 as Api.help.CountryCode:
+ _1.serialize(buffer, boxed)
case let _1 as Api.InputMessage:
_1.serialize(buffer, boxed)
case let _1 as Api.PhoneCallProtocol:
@@ -1366,6 +1379,8 @@ public struct Api {
_1.serialize(buffer, boxed)
case let _1 as Api.messages.Dialogs:
_1.serialize(buffer, boxed)
+ case let _1 as Api.stats.MessageStats:
+ _1.serialize(buffer, boxed)
case let _1 as Api.EmojiKeyword:
_1.serialize(buffer, boxed)
case let _1 as Api.upload.CdnFile:
@@ -1442,6 +1457,8 @@ public struct Api {
_1.serialize(buffer, boxed)
case let _1 as Api.updates.ChannelDifference:
_1.serialize(buffer, boxed)
+ case let _1 as Api.help.CountriesList:
+ _1.serialize(buffer, boxed)
case let _1 as Api.channels.AdminLogResults:
_1.serialize(buffer, boxed)
case let _1 as Api.ChatOnlines:
diff --git a/submodules/TelegramApi/Sources/Api1.swift b/submodules/TelegramApi/Sources/Api1.swift
index 025d00a4aa..5a30fc3b91 100644
--- a/submodules/TelegramApi/Sources/Api1.swift
+++ b/submodules/TelegramApi/Sources/Api1.swift
@@ -6038,6 +6038,7 @@ public extension Api {
case updateDialogFilters
case updatePhoneCallSignalingData(phoneCallId: Int64, data: Buffer)
case updateChannelParticipant(flags: Int32, channelId: Int32, date: Int32, userId: Int32, prevParticipant: Api.ChannelParticipant?, newParticipant: Api.ChannelParticipant?, qts: Int32)
+ case updateChannelMessageForwards(channelId: Int32, id: Int32, forwards: Int32)
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
@@ -6730,6 +6731,14 @@ public extension Api {
if Int(flags) & Int(1 << 1) != 0 {newParticipant!.serialize(buffer, true)}
serializeInt32(qts, buffer: buffer, boxed: false)
break
+ case .updateChannelMessageForwards(let channelId, let id, let forwards):
+ if boxed {
+ buffer.appendInt32(1854571743)
+ }
+ serializeInt32(channelId, buffer: buffer, boxed: false)
+ serializeInt32(id, buffer: buffer, boxed: false)
+ serializeInt32(forwards, buffer: buffer, boxed: false)
+ break
}
}
@@ -6899,6 +6908,8 @@ public extension Api {
return ("updatePhoneCallSignalingData", [("phoneCallId", phoneCallId), ("data", data)])
case .updateChannelParticipant(let flags, let channelId, let date, let userId, let prevParticipant, let newParticipant, let qts):
return ("updateChannelParticipant", [("flags", flags), ("channelId", channelId), ("date", date), ("userId", userId), ("prevParticipant", prevParticipant), ("newParticipant", newParticipant), ("qts", qts)])
+ case .updateChannelMessageForwards(let channelId, let id, let forwards):
+ return ("updateChannelMessageForwards", [("channelId", channelId), ("id", id), ("forwards", forwards)])
}
}
@@ -8277,6 +8288,23 @@ public extension Api {
return nil
}
}
+ public static func parse_updateChannelMessageForwards(_ reader: BufferReader) -> Update? {
+ var _1: Int32?
+ _1 = reader.readInt32()
+ var _2: Int32?
+ _2 = reader.readInt32()
+ var _3: Int32?
+ _3 = reader.readInt32()
+ let _c1 = _1 != nil
+ let _c2 = _2 != nil
+ let _c3 = _3 != nil
+ if _c1 && _c2 && _c3 {
+ return Api.Update.updateChannelMessageForwards(channelId: _1!, id: _2!, forwards: _3!)
+ }
+ else {
+ return nil
+ }
+ }
}
public enum PopularContact: TypeConstructorDescription {
@@ -8732,7 +8760,6 @@ public extension Api {
public enum KeyboardButton: TypeConstructorDescription {
case keyboardButton(text: String)
case keyboardButtonUrl(text: String, url: String)
- case keyboardButtonCallback(text: String, data: Buffer)
case keyboardButtonRequestPhone(text: String)
case keyboardButtonRequestGeoLocation(text: String)
case keyboardButtonSwitchInline(flags: Int32, text: String, query: String)
@@ -8741,6 +8768,7 @@ public extension Api {
case keyboardButtonUrlAuth(flags: Int32, text: String, fwdText: String?, url: String, buttonId: Int32)
case inputKeyboardButtonUrlAuth(flags: Int32, text: String, fwdText: String?, url: String, bot: Api.InputUser)
case keyboardButtonRequestPoll(flags: Int32, quiz: Api.Bool?, text: String)
+ case keyboardButtonCallback(flags: Int32, text: String, data: Buffer)
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
@@ -8757,13 +8785,6 @@ public extension Api {
serializeString(text, buffer: buffer, boxed: false)
serializeString(url, buffer: buffer, boxed: false)
break
- case .keyboardButtonCallback(let text, let data):
- if boxed {
- buffer.appendInt32(1748655686)
- }
- serializeString(text, buffer: buffer, boxed: false)
- serializeBytes(data, buffer: buffer, boxed: false)
- break
case .keyboardButtonRequestPhone(let text):
if boxed {
buffer.appendInt32(-1318425559)
@@ -8824,6 +8845,14 @@ public extension Api {
if Int(flags) & Int(1 << 0) != 0 {quiz!.serialize(buffer, true)}
serializeString(text, buffer: buffer, boxed: false)
break
+ case .keyboardButtonCallback(let flags, let text, let data):
+ if boxed {
+ buffer.appendInt32(901503851)
+ }
+ serializeInt32(flags, buffer: buffer, boxed: false)
+ serializeString(text, buffer: buffer, boxed: false)
+ serializeBytes(data, buffer: buffer, boxed: false)
+ break
}
}
@@ -8833,8 +8862,6 @@ public extension Api {
return ("keyboardButton", [("text", text)])
case .keyboardButtonUrl(let text, let url):
return ("keyboardButtonUrl", [("text", text), ("url", url)])
- case .keyboardButtonCallback(let text, let data):
- return ("keyboardButtonCallback", [("text", text), ("data", data)])
case .keyboardButtonRequestPhone(let text):
return ("keyboardButtonRequestPhone", [("text", text)])
case .keyboardButtonRequestGeoLocation(let text):
@@ -8851,6 +8878,8 @@ public extension Api {
return ("inputKeyboardButtonUrlAuth", [("flags", flags), ("text", text), ("fwdText", fwdText), ("url", url), ("bot", bot)])
case .keyboardButtonRequestPoll(let flags, let quiz, let text):
return ("keyboardButtonRequestPoll", [("flags", flags), ("quiz", quiz), ("text", text)])
+ case .keyboardButtonCallback(let flags, let text, let data):
+ return ("keyboardButtonCallback", [("flags", flags), ("text", text), ("data", data)])
}
}
@@ -8879,20 +8908,6 @@ public extension Api {
return nil
}
}
- public static func parse_keyboardButtonCallback(_ reader: BufferReader) -> KeyboardButton? {
- var _1: String?
- _1 = parseString(reader)
- var _2: Buffer?
- _2 = parseBytes(reader)
- let _c1 = _1 != nil
- let _c2 = _2 != nil
- if _c1 && _c2 {
- return Api.KeyboardButton.keyboardButtonCallback(text: _1!, data: _2!)
- }
- else {
- return nil
- }
- }
public static func parse_keyboardButtonRequestPhone(_ reader: BufferReader) -> KeyboardButton? {
var _1: String?
_1 = parseString(reader)
@@ -9021,6 +9036,23 @@ public extension Api {
return nil
}
}
+ public static func parse_keyboardButtonCallback(_ reader: BufferReader) -> KeyboardButton? {
+ var _1: Int32?
+ _1 = reader.readInt32()
+ var _2: String?
+ _2 = parseString(reader)
+ var _3: Buffer?
+ _3 = parseBytes(reader)
+ let _c1 = _1 != nil
+ let _c2 = _2 != nil
+ let _c3 = _3 != nil
+ if _c1 && _c2 && _c3 {
+ return Api.KeyboardButton.keyboardButtonCallback(flags: _1!, text: _2!, data: _3!)
+ }
+ else {
+ return nil
+ }
+ }
}
public enum ContactStatus: TypeConstructorDescription {
@@ -11718,6 +11750,44 @@ public extension Api {
}
}
+ }
+ public enum MessageViews: TypeConstructorDescription {
+ case messageViews(views: Int32, forwards: Int32)
+
+ public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
+ switch self {
+ case .messageViews(let views, let forwards):
+ if boxed {
+ buffer.appendInt32(1831138451)
+ }
+ serializeInt32(views, buffer: buffer, boxed: false)
+ serializeInt32(forwards, buffer: buffer, boxed: false)
+ break
+ }
+ }
+
+ public func descriptionFields() -> (String, [(String, Any)]) {
+ switch self {
+ case .messageViews(let views, let forwards):
+ return ("messageViews", [("views", views), ("forwards", forwards)])
+ }
+ }
+
+ public static func parse_messageViews(_ reader: BufferReader) -> MessageViews? {
+ var _1: Int32?
+ _1 = reader.readInt32()
+ var _2: Int32?
+ _2 = reader.readInt32()
+ let _c1 = _1 != nil
+ let _c2 = _2 != nil
+ if _c1 && _c2 {
+ return Api.MessageViews.messageViews(views: _1!, forwards: _2!)
+ }
+ else {
+ return nil
+ }
+ }
+
}
public enum InputPrivacyRule: TypeConstructorDescription {
case inputPrivacyValueAllowContacts
@@ -17092,7 +17162,7 @@ public extension Api {
public enum Message: TypeConstructorDescription {
case messageEmpty(id: Int32)
case messageService(flags: Int32, id: Int32, fromId: Int32?, toId: Api.Peer, replyToMsgId: Int32?, date: Int32, action: Api.MessageAction)
- case message(flags: Int32, id: Int32, fromId: Int32?, toId: Api.Peer, fwdFrom: Api.MessageFwdHeader?, viaBotId: Int32?, replyToMsgId: Int32?, date: Int32, message: String, media: Api.MessageMedia?, replyMarkup: Api.ReplyMarkup?, entities: [Api.MessageEntity]?, views: Int32?, editDate: Int32?, postAuthor: String?, groupedId: Int64?, restrictionReason: [Api.RestrictionReason]?)
+ case message(flags: Int32, id: Int32, fromId: Int32?, toId: Api.Peer, fwdFrom: Api.MessageFwdHeader?, viaBotId: Int32?, replyToMsgId: Int32?, date: Int32, message: String, media: Api.MessageMedia?, replyMarkup: Api.ReplyMarkup?, entities: [Api.MessageEntity]?, views: Int32?, forwards: Int32?, editDate: Int32?, postAuthor: String?, groupedId: Int64?, restrictionReason: [Api.RestrictionReason]?)
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
@@ -17114,9 +17184,9 @@ public extension Api {
serializeInt32(date, buffer: buffer, boxed: false)
action.serialize(buffer, true)
break
- case .message(let flags, let id, let fromId, let toId, let fwdFrom, let viaBotId, let replyToMsgId, let date, let message, let media, let replyMarkup, let entities, let views, let editDate, let postAuthor, let groupedId, let restrictionReason):
+ case .message(let flags, let id, let fromId, let toId, let fwdFrom, let viaBotId, let replyToMsgId, let date, let message, let media, let replyMarkup, let entities, let views, let forwards, let editDate, let postAuthor, let groupedId, let restrictionReason):
if boxed {
- buffer.appendInt32(1160515173)
+ buffer.appendInt32(-181507201)
}
serializeInt32(flags, buffer: buffer, boxed: false)
serializeInt32(id, buffer: buffer, boxed: false)
@@ -17135,6 +17205,7 @@ public extension Api {
item.serialize(buffer, true)
}}
if Int(flags) & Int(1 << 10) != 0 {serializeInt32(views!, buffer: buffer, boxed: false)}
+ if Int(flags) & Int(1 << 10) != 0 {serializeInt32(forwards!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 15) != 0 {serializeInt32(editDate!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 16) != 0 {serializeString(postAuthor!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 17) != 0 {serializeInt64(groupedId!, buffer: buffer, boxed: false)}
@@ -17153,8 +17224,8 @@ public extension Api {
return ("messageEmpty", [("id", id)])
case .messageService(let flags, let id, let fromId, let toId, let replyToMsgId, let date, let action):
return ("messageService", [("flags", flags), ("id", id), ("fromId", fromId), ("toId", toId), ("replyToMsgId", replyToMsgId), ("date", date), ("action", action)])
- case .message(let flags, let id, let fromId, let toId, let fwdFrom, let viaBotId, let replyToMsgId, let date, let message, let media, let replyMarkup, let entities, let views, let editDate, let postAuthor, let groupedId, let restrictionReason):
- return ("message", [("flags", flags), ("id", id), ("fromId", fromId), ("toId", toId), ("fwdFrom", fwdFrom), ("viaBotId", viaBotId), ("replyToMsgId", replyToMsgId), ("date", date), ("message", message), ("media", media), ("replyMarkup", replyMarkup), ("entities", entities), ("views", views), ("editDate", editDate), ("postAuthor", postAuthor), ("groupedId", groupedId), ("restrictionReason", restrictionReason)])
+ case .message(let flags, let id, let fromId, let toId, let fwdFrom, let viaBotId, let replyToMsgId, let date, let message, let media, let replyMarkup, let entities, let views, let forwards, let editDate, let postAuthor, let groupedId, let restrictionReason):
+ return ("message", [("flags", flags), ("id", id), ("fromId", fromId), ("toId", toId), ("fwdFrom", fwdFrom), ("viaBotId", viaBotId), ("replyToMsgId", replyToMsgId), ("date", date), ("message", message), ("media", media), ("replyMarkup", replyMarkup), ("entities", entities), ("views", views), ("forwards", forwards), ("editDate", editDate), ("postAuthor", postAuthor), ("groupedId", groupedId), ("restrictionReason", restrictionReason)])
}
}
@@ -17240,14 +17311,16 @@ public extension Api {
var _13: Int32?
if Int(_1!) & Int(1 << 10) != 0 {_13 = reader.readInt32() }
var _14: Int32?
- if Int(_1!) & Int(1 << 15) != 0 {_14 = reader.readInt32() }
- var _15: String?
- if Int(_1!) & Int(1 << 16) != 0 {_15 = parseString(reader) }
- var _16: Int64?
- if Int(_1!) & Int(1 << 17) != 0 {_16 = reader.readInt64() }
- var _17: [Api.RestrictionReason]?
+ if Int(_1!) & Int(1 << 10) != 0 {_14 = reader.readInt32() }
+ var _15: Int32?
+ if Int(_1!) & Int(1 << 15) != 0 {_15 = reader.readInt32() }
+ var _16: String?
+ if Int(_1!) & Int(1 << 16) != 0 {_16 = parseString(reader) }
+ var _17: Int64?
+ if Int(_1!) & Int(1 << 17) != 0 {_17 = reader.readInt64() }
+ var _18: [Api.RestrictionReason]?
if Int(_1!) & Int(1 << 22) != 0 {if let _ = reader.readInt32() {
- _17 = Api.parseVector(reader, elementSignature: 0, elementType: Api.RestrictionReason.self)
+ _18 = Api.parseVector(reader, elementSignature: 0, elementType: Api.RestrictionReason.self)
} }
let _c1 = _1 != nil
let _c2 = _2 != nil
@@ -17262,12 +17335,13 @@ public extension Api {
let _c11 = (Int(_1!) & Int(1 << 6) == 0) || _11 != nil
let _c12 = (Int(_1!) & Int(1 << 7) == 0) || _12 != nil
let _c13 = (Int(_1!) & Int(1 << 10) == 0) || _13 != nil
- let _c14 = (Int(_1!) & Int(1 << 15) == 0) || _14 != nil
- let _c15 = (Int(_1!) & Int(1 << 16) == 0) || _15 != nil
- let _c16 = (Int(_1!) & Int(1 << 17) == 0) || _16 != nil
- let _c17 = (Int(_1!) & Int(1 << 22) == 0) || _17 != nil
- if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 && _c8 && _c9 && _c10 && _c11 && _c12 && _c13 && _c14 && _c15 && _c16 && _c17 {
- return Api.Message.message(flags: _1!, id: _2!, fromId: _3, toId: _4!, fwdFrom: _5, viaBotId: _6, replyToMsgId: _7, date: _8!, message: _9!, media: _10, replyMarkup: _11, entities: _12, views: _13, editDate: _14, postAuthor: _15, groupedId: _16, restrictionReason: _17)
+ let _c14 = (Int(_1!) & Int(1 << 10) == 0) || _14 != nil
+ let _c15 = (Int(_1!) & Int(1 << 15) == 0) || _15 != nil
+ let _c16 = (Int(_1!) & Int(1 << 16) == 0) || _16 != nil
+ let _c17 = (Int(_1!) & Int(1 << 17) == 0) || _17 != nil
+ let _c18 = (Int(_1!) & Int(1 << 22) == 0) || _18 != nil
+ if _c1 && _c2 && _c3 && _c4 && _c5 && _c6 && _c7 && _c8 && _c9 && _c10 && _c11 && _c12 && _c13 && _c14 && _c15 && _c16 && _c17 && _c18 {
+ return Api.Message.message(flags: _1!, id: _2!, fromId: _3, toId: _4!, fwdFrom: _5, viaBotId: _6, replyToMsgId: _7, date: _8!, message: _9!, media: _10, replyMarkup: _11, entities: _12, views: _13, forwards: _14, editDate: _15, postAuthor: _16, groupedId: _17, restrictionReason: _18)
}
else {
return nil
diff --git a/submodules/TelegramApi/Sources/Api2.swift b/submodules/TelegramApi/Sources/Api2.swift
index c24dccef69..16c442f2ff 100644
--- a/submodules/TelegramApi/Sources/Api2.swift
+++ b/submodules/TelegramApi/Sources/Api2.swift
@@ -810,6 +810,42 @@ public struct stats {
}
}
+ public enum MessageStats: TypeConstructorDescription {
+ case messageStats(viewsGraph: Api.StatsGraph)
+
+ public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
+ switch self {
+ case .messageStats(let viewsGraph):
+ if boxed {
+ buffer.appendInt32(-1986399595)
+ }
+ viewsGraph.serialize(buffer, true)
+ break
+ }
+ }
+
+ public func descriptionFields() -> (String, [(String, Any)]) {
+ switch self {
+ case .messageStats(let viewsGraph):
+ return ("messageStats", [("viewsGraph", viewsGraph)])
+ }
+ }
+
+ public static func parse_messageStats(_ reader: BufferReader) -> MessageStats? {
+ var _1: Api.StatsGraph?
+ if let signature = reader.readInt32() {
+ _1 = Api.parse(reader, signature: signature) as? Api.StatsGraph
+ }
+ let _c1 = _1 != nil
+ if _c1 {
+ return Api.stats.MessageStats.messageStats(viewsGraph: _1!)
+ }
+ else {
+ return nil
+ }
+ }
+
+ }
}
}
public extension Api {
@@ -1965,6 +2001,58 @@ public struct help {
}
}
+ }
+ public enum Country: TypeConstructorDescription {
+ case country(iso2: String, defaultName: String, name: String, countryCodes: [Api.help.CountryCode])
+
+ public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
+ switch self {
+ case .country(let iso2, let defaultName, let name, let countryCodes):
+ if boxed {
+ buffer.appendInt32(-77073091)
+ }
+ serializeString(iso2, buffer: buffer, boxed: false)
+ serializeString(defaultName, buffer: buffer, boxed: false)
+ serializeString(name, buffer: buffer, boxed: false)
+ buffer.appendInt32(481674261)
+ buffer.appendInt32(Int32(countryCodes.count))
+ for item in countryCodes {
+ item.serialize(buffer, true)
+ }
+ break
+ }
+ }
+
+ public func descriptionFields() -> (String, [(String, Any)]) {
+ switch self {
+ case .country(let iso2, let defaultName, let name, let countryCodes):
+ return ("country", [("iso2", iso2), ("defaultName", defaultName), ("name", name), ("countryCodes", countryCodes)])
+ }
+ }
+
+ public static func parse_country(_ reader: BufferReader) -> Country? {
+ var _1: String?
+ _1 = parseString(reader)
+ var _2: String?
+ _2 = parseString(reader)
+ var _3: String?
+ _3 = parseString(reader)
+ var _4: [Api.help.CountryCode]?
+ if let _ = reader.readInt32() {
+ _4 = Api.parseVector(reader, elementSignature: 0, elementType: Api.help.CountryCode.self)
+ }
+ let _c1 = _1 != nil
+ let _c2 = _2 != nil
+ let _c3 = _3 != nil
+ let _c4 = _4 != nil
+ if _c1 && _c2 && _c3 && _c4 {
+ return Api.help.Country.country(iso2: _1!, defaultName: _2!, name: _3!, countryCodes: _4!)
+ }
+ else {
+ return nil
+ }
+ }
+
}
public enum PromoData: TypeConstructorDescription {
case promoDataEmpty(expires: Int32)
@@ -2117,6 +2205,64 @@ public struct help {
}
}
+ }
+ public enum CountryCode: TypeConstructorDescription {
+ case countryCode(flags: Int32, countryCode: String, prefixes: [String]?, patterns: [String]?)
+
+ public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
+ switch self {
+ case .countryCode(let flags, let countryCode, let prefixes, let patterns):
+ if boxed {
+ buffer.appendInt32(1107543535)
+ }
+ serializeInt32(flags, buffer: buffer, boxed: false)
+ serializeString(countryCode, buffer: buffer, boxed: false)
+ if Int(flags) & Int(1 << 0) != 0 {buffer.appendInt32(481674261)
+ buffer.appendInt32(Int32(prefixes!.count))
+ for item in prefixes! {
+ serializeString(item, buffer: buffer, boxed: false)
+ }}
+ if Int(flags) & Int(1 << 1) != 0 {buffer.appendInt32(481674261)
+ buffer.appendInt32(Int32(patterns!.count))
+ for item in patterns! {
+ serializeString(item, buffer: buffer, boxed: false)
+ }}
+ break
+ }
+ }
+
+ public func descriptionFields() -> (String, [(String, Any)]) {
+ switch self {
+ case .countryCode(let flags, let countryCode, let prefixes, let patterns):
+ return ("countryCode", [("flags", flags), ("countryCode", countryCode), ("prefixes", prefixes), ("patterns", patterns)])
+ }
+ }
+
+ public static func parse_countryCode(_ reader: BufferReader) -> CountryCode? {
+ var _1: Int32?
+ _1 = reader.readInt32()
+ var _2: String?
+ _2 = parseString(reader)
+ var _3: [String]?
+ if Int(_1!) & Int(1 << 0) != 0 {if let _ = reader.readInt32() {
+ _3 = Api.parseVector(reader, elementSignature: -1255641564, elementType: String.self)
+ } }
+ var _4: [String]?
+ if Int(_1!) & Int(1 << 1) != 0 {if let _ = reader.readInt32() {
+ _4 = Api.parseVector(reader, elementSignature: -1255641564, elementType: String.self)
+ } }
+ 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
+ if _c1 && _c2 && _c3 && _c4 {
+ return Api.help.CountryCode.countryCode(flags: _1!, countryCode: _2!, prefixes: _3, patterns: _4)
+ }
+ else {
+ return nil
+ }
+ }
+
}
public enum Support: TypeConstructorDescription {
case support(phoneNumber: String, user: Api.User)
@@ -2316,5 +2462,61 @@ public struct help {
}
}
+ public enum CountriesList: TypeConstructorDescription {
+ case countriesListNotModified
+ case countriesList(countries: [Api.help.Country], hash: Int32)
+
+ public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
+ switch self {
+ case .countriesListNotModified:
+ if boxed {
+ buffer.appendInt32(-1815339214)
+ }
+
+ break
+ case .countriesList(let countries, let hash):
+ if boxed {
+ buffer.appendInt32(-2016381538)
+ }
+ buffer.appendInt32(481674261)
+ buffer.appendInt32(Int32(countries.count))
+ for item in countries {
+ item.serialize(buffer, true)
+ }
+ serializeInt32(hash, buffer: buffer, boxed: false)
+ break
+ }
+ }
+
+ public func descriptionFields() -> (String, [(String, Any)]) {
+ switch self {
+ case .countriesListNotModified:
+ return ("countriesListNotModified", [])
+ case .countriesList(let countries, let hash):
+ return ("countriesList", [("countries", countries), ("hash", hash)])
+ }
+ }
+
+ public static func parse_countriesListNotModified(_ reader: BufferReader) -> CountriesList? {
+ return Api.help.CountriesList.countriesListNotModified
+ }
+ public static func parse_countriesList(_ reader: BufferReader) -> CountriesList? {
+ var _1: [Api.help.Country]?
+ if let _ = reader.readInt32() {
+ _1 = Api.parseVector(reader, elementSignature: 0, elementType: Api.help.Country.self)
+ }
+ var _2: Int32?
+ _2 = reader.readInt32()
+ let _c1 = _1 != nil
+ let _c2 = _2 != nil
+ if _c1 && _c2 {
+ return Api.help.CountriesList.countriesList(countries: _1!, hash: _2!)
+ }
+ else {
+ return nil
+ }
+ }
+
+ }
}
}
diff --git a/submodules/TelegramApi/Sources/Api3.swift b/submodules/TelegramApi/Sources/Api3.swift
index c79744cf01..f2e20a21b1 100644
--- a/submodules/TelegramApi/Sources/Api3.swift
+++ b/submodules/TelegramApi/Sources/Api3.swift
@@ -2243,26 +2243,6 @@ public extension Api {
})
}
- public static func getMessagesViews(peer: Api.InputPeer, id: [Int32], increment: Api.Bool) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<[Int32]>) {
- let buffer = Buffer()
- buffer.appendInt32(-993483427)
- peer.serialize(buffer, true)
- buffer.appendInt32(481674261)
- buffer.appendInt32(Int32(id.count))
- for item in id {
- serializeInt32(item, buffer: buffer, boxed: false)
- }
- increment.serialize(buffer, true)
- return (FunctionDescription(name: "messages.getMessagesViews", parameters: [("peer", peer), ("id", id), ("increment", increment)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> [Int32]? in
- let reader = BufferReader(buffer)
- var result: [Int32]?
- if let _ = reader.readInt32() {
- result = Api.parseVector(reader, elementSignature: -1471112230, elementType: Int32.self)
- }
- return result
- })
- }
-
public static func editChatAdmin(chatId: Int32, userId: Api.InputUser, isAdmin: Api.Bool) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
let buffer = Buffer()
buffer.appendInt32(-1444503762)
@@ -2429,23 +2409,6 @@ public extension Api {
})
}
- public static func getBotCallbackAnswer(flags: Int32, peer: Api.InputPeer, msgId: Int32, data: Buffer?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
- let buffer = Buffer()
- buffer.appendInt32(-2130010132)
- serializeInt32(flags, buffer: buffer, boxed: false)
- peer.serialize(buffer, true)
- serializeInt32(msgId, buffer: buffer, boxed: false)
- if Int(flags) & Int(1 << 0) != 0 {serializeBytes(data!, buffer: buffer, boxed: false)}
- return (FunctionDescription(name: "messages.getBotCallbackAnswer", parameters: [("flags", flags), ("peer", peer), ("msgId", msgId), ("data", data)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.messages.BotCallbackAnswer? in
- let reader = BufferReader(buffer)
- var result: Api.messages.BotCallbackAnswer?
- if let signature = reader.readInt32() {
- result = Api.parse(reader, signature: signature) as? Api.messages.BotCallbackAnswer
- }
- return result
- })
- }
-
public static func setBotCallbackAnswer(flags: Int32, queryId: Int64, message: String?, url: String?, cacheTime: Int32) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
let buffer = Buffer()
buffer.appendInt32(-712043766)
@@ -3718,6 +3681,44 @@ public extension Api {
return result
})
}
+
+ public static func getBotCallbackAnswer(flags: Int32, peer: Api.InputPeer, msgId: Int32, data: Buffer?, password: Api.InputCheckPasswordSRP?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ let buffer = Buffer()
+ buffer.appendInt32(-1824339449)
+ serializeInt32(flags, buffer: buffer, boxed: false)
+ peer.serialize(buffer, true)
+ serializeInt32(msgId, buffer: buffer, boxed: false)
+ if Int(flags) & Int(1 << 0) != 0 {serializeBytes(data!, buffer: buffer, boxed: false)}
+ if Int(flags) & Int(1 << 2) != 0 {password!.serialize(buffer, true)}
+ return (FunctionDescription(name: "messages.getBotCallbackAnswer", parameters: [("flags", flags), ("peer", peer), ("msgId", msgId), ("data", data), ("password", password)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.messages.BotCallbackAnswer? in
+ let reader = BufferReader(buffer)
+ var result: Api.messages.BotCallbackAnswer?
+ if let signature = reader.readInt32() {
+ result = Api.parse(reader, signature: signature) as? Api.messages.BotCallbackAnswer
+ }
+ return result
+ })
+ }
+
+ public static func getMessagesViews(peer: Api.InputPeer, id: [Int32], increment: Api.Bool) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<[Api.MessageViews]>) {
+ let buffer = Buffer()
+ buffer.appendInt32(-39035462)
+ peer.serialize(buffer, true)
+ buffer.appendInt32(481674261)
+ buffer.appendInt32(Int32(id.count))
+ for item in id {
+ serializeInt32(item, buffer: buffer, boxed: false)
+ }
+ increment.serialize(buffer, true)
+ return (FunctionDescription(name: "messages.getMessagesViews", parameters: [("peer", peer), ("id", id), ("increment", increment)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> [Api.MessageViews]? in
+ let reader = BufferReader(buffer)
+ var result: [Api.MessageViews]?
+ if let _ = reader.readInt32() {
+ result = Api.parseVector(reader, elementSignature: 0, elementType: Api.MessageViews.self)
+ }
+ return result
+ })
+ }
}
public struct channels {
public static func readHistory(channel: Api.InputChannel, maxId: Int32) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
@@ -4450,6 +4451,41 @@ public extension Api {
return result
})
}
+
+ public static func getMessagePublicForwards(channel: Api.InputChannel, msgId: Int32, offsetRate: Int32, offsetPeer: Api.InputPeer, offsetId: Int32, limit: Int32) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ let buffer = Buffer()
+ buffer.appendInt32(1445996571)
+ channel.serialize(buffer, true)
+ serializeInt32(msgId, buffer: buffer, boxed: false)
+ serializeInt32(offsetRate, buffer: buffer, boxed: false)
+ offsetPeer.serialize(buffer, true)
+ serializeInt32(offsetId, buffer: buffer, boxed: false)
+ serializeInt32(limit, buffer: buffer, boxed: false)
+ return (FunctionDescription(name: "stats.getMessagePublicForwards", parameters: [("channel", channel), ("msgId", msgId), ("offsetRate", offsetRate), ("offsetPeer", offsetPeer), ("offsetId", offsetId), ("limit", limit)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.messages.Messages? in
+ let reader = BufferReader(buffer)
+ var result: Api.messages.Messages?
+ if let signature = reader.readInt32() {
+ result = Api.parse(reader, signature: signature) as? Api.messages.Messages
+ }
+ return result
+ })
+ }
+
+ public static func getMessageStats(flags: Int32, channel: Api.InputChannel, msgId: Int32) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ let buffer = Buffer()
+ buffer.appendInt32(-1226791947)
+ serializeInt32(flags, buffer: buffer, boxed: false)
+ channel.serialize(buffer, true)
+ serializeInt32(msgId, buffer: buffer, boxed: false)
+ return (FunctionDescription(name: "stats.getMessageStats", parameters: [("flags", flags), ("channel", channel), ("msgId", msgId)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.stats.MessageStats? in
+ let reader = BufferReader(buffer)
+ var result: Api.stats.MessageStats?
+ if let signature = reader.readInt32() {
+ result = Api.parse(reader, signature: signature) as? Api.stats.MessageStats
+ }
+ return result
+ })
+ }
}
public struct auth {
public static func checkPhone(phoneNumber: String) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
@@ -5369,34 +5405,6 @@ public extension Api {
})
}
- public static func getPromoData() -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
- let buffer = Buffer()
- buffer.appendInt32(-1063816159)
-
- return (FunctionDescription(name: "help.getPromoData", parameters: []), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.help.PromoData? in
- let reader = BufferReader(buffer)
- var result: Api.help.PromoData?
- if let signature = reader.readInt32() {
- result = Api.parse(reader, signature: signature) as? Api.help.PromoData
- }
- return result
- })
- }
-
- public static func hidePromoData(peer: Api.InputPeer) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
- let buffer = Buffer()
- buffer.appendInt32(505748629)
- peer.serialize(buffer, true)
- return (FunctionDescription(name: "help.hidePromoData", parameters: [("peer", peer)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Bool? in
- let reader = BufferReader(buffer)
- var result: Api.Bool?
- if let signature = reader.readInt32() {
- result = Api.parse(reader, signature: signature) as? Api.Bool
- }
- return result
- })
- }
-
public static func editUserInfo(userId: Api.InputUser, message: String, entities: [Api.MessageEntity]) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
let buffer = Buffer()
buffer.appendInt32(1723407216)
@@ -5431,6 +5439,34 @@ public extension Api {
})
}
+ public static func getPromoData() -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ let buffer = Buffer()
+ buffer.appendInt32(-1063816159)
+
+ return (FunctionDescription(name: "help.getPromoData", parameters: []), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.help.PromoData? in
+ let reader = BufferReader(buffer)
+ var result: Api.help.PromoData?
+ if let signature = reader.readInt32() {
+ result = Api.parse(reader, signature: signature) as? Api.help.PromoData
+ }
+ return result
+ })
+ }
+
+ public static func hidePromoData(peer: Api.InputPeer) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ let buffer = Buffer()
+ buffer.appendInt32(505748629)
+ peer.serialize(buffer, true)
+ return (FunctionDescription(name: "help.hidePromoData", parameters: [("peer", peer)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Bool? in
+ let reader = BufferReader(buffer)
+ var result: Api.Bool?
+ if let signature = reader.readInt32() {
+ result = Api.parse(reader, signature: signature) as? Api.Bool
+ }
+ return result
+ })
+ }
+
public static func dismissSuggestion(suggestion: String) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
let buffer = Buffer()
buffer.appendInt32(125807007)
@@ -5444,6 +5480,21 @@ public extension Api {
return result
})
}
+
+ public static func getCountriesList(langCode: String, hash: Int32) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ let buffer = Buffer()
+ buffer.appendInt32(1935116200)
+ serializeString(langCode, buffer: buffer, boxed: false)
+ serializeInt32(hash, buffer: buffer, boxed: false)
+ return (FunctionDescription(name: "help.getCountriesList", parameters: [("langCode", langCode), ("hash", hash)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.help.CountriesList? in
+ let reader = BufferReader(buffer)
+ var result: Api.help.CountriesList?
+ if let signature = reader.readInt32() {
+ result = Api.parse(reader, signature: signature) as? Api.help.CountriesList
+ }
+ return result
+ })
+ }
}
public struct updates {
public static func getState() -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
@@ -6802,11 +6853,14 @@ public extension Api {
})
}
- public static func updateProfilePhoto(id: Api.InputPhoto) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ public static func uploadProfilePhoto(flags: Int32, file: Api.InputFile?, video: Api.InputFile?, videoStartTs: Double?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
let buffer = Buffer()
- buffer.appendInt32(1926525996)
- id.serialize(buffer, true)
- return (FunctionDescription(name: "photos.updateProfilePhoto", parameters: [("id", id)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.photos.Photo? in
+ buffer.appendInt32(-1980559511)
+ serializeInt32(flags, buffer: buffer, boxed: false)
+ if Int(flags) & Int(1 << 0) != 0 {file!.serialize(buffer, true)}
+ if Int(flags) & Int(1 << 1) != 0 {video!.serialize(buffer, true)}
+ if Int(flags) & Int(1 << 2) != 0 {serializeDouble(videoStartTs!, buffer: buffer, boxed: false)}
+ return (FunctionDescription(name: "photos.uploadProfilePhoto", parameters: [("flags", flags), ("file", file), ("video", video), ("videoStartTs", videoStartTs)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.photos.Photo? in
let reader = BufferReader(buffer)
var result: Api.photos.Photo?
if let signature = reader.readInt32() {
@@ -6816,14 +6870,11 @@ public extension Api {
})
}
- public static func uploadProfilePhoto(flags: Int32, file: Api.InputFile?, video: Api.InputFile?, videoStartTs: Double?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
+ public static func updateProfilePhoto(id: Api.InputPhoto) -> (FunctionDescription, Buffer, DeserializeFunctionResponse) {
let buffer = Buffer()
- buffer.appendInt32(-1980559511)
- serializeInt32(flags, buffer: buffer, boxed: false)
- if Int(flags) & Int(1 << 0) != 0 {file!.serialize(buffer, true)}
- if Int(flags) & Int(1 << 1) != 0 {video!.serialize(buffer, true)}
- if Int(flags) & Int(1 << 2) != 0 {serializeDouble(videoStartTs!, buffer: buffer, boxed: false)}
- return (FunctionDescription(name: "photos.uploadProfilePhoto", parameters: [("flags", flags), ("file", file), ("video", video), ("videoStartTs", videoStartTs)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.photos.Photo? in
+ buffer.appendInt32(1926525996)
+ id.serialize(buffer, true)
+ return (FunctionDescription(name: "photos.updateProfilePhoto", parameters: [("id", id)]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.photos.Photo? in
let reader = BufferReader(buffer)
var result: Api.photos.Photo?
if let signature = reader.readInt32() {
diff --git a/submodules/TelegramCallsUI/Sources/CallControllerNode.swift b/submodules/TelegramCallsUI/Sources/CallControllerNode.swift
index 1d41983b99..7936699d85 100644
--- a/submodules/TelegramCallsUI/Sources/CallControllerNode.swift
+++ b/submodules/TelegramCallsUI/Sources/CallControllerNode.swift
@@ -1272,6 +1272,10 @@ final class CallControllerNode: ViewControllerTracingNode, CallControllerNodePro
func containerLayoutUpdated(_ layout: ContainerViewLayout, navigationBarHeight: CGFloat, transition: ContainedViewLayoutTransition) {
self.validLayout = (layout, navigationBarHeight)
+ if !self.hasVideoNodes {
+ self.isUIHidden = false
+ }
+
var isUIHidden = self.isUIHidden
switch self.callState?.state {
case .terminated, .terminating:
diff --git a/submodules/TelegramCore/Sources/AccountViewTracker.swift b/submodules/TelegramCore/Sources/AccountViewTracker.swift
index c439133ebb..9f166ff156 100644
--- a/submodules/TelegramCore/Sources/AccountViewTracker.swift
+++ b/submodules/TelegramCore/Sources/AccountViewTracker.swift
@@ -591,7 +591,7 @@ public final class AccountViewTracker {
if let peer = transaction.getPeer(peerId), let inputPeer = apiInputPeer(peer) {
return account.network.request(Api.functions.messages.getMessagesViews(peer: inputPeer, id: messageIds.map { $0.id }, increment: .boolTrue))
|> map(Optional.init)
- |> `catch` { _ -> Signal<[Int32]?, NoError> in
+ |> `catch` { _ -> Signal<[Api.MessageViews]?, NoError> in
return .single(nil)
}
|> mapToSignal { viewCounts -> Signal in
@@ -599,20 +599,7 @@ public final class AccountViewTracker {
return account.postbox.transaction { transaction -> Void in
for i in 0 ..< messageIds.count {
if i < viewCounts.count {
- let views = viewCounts[i]
- do {
- transaction.updateMessage(messageIds[i], update: { currentMessage in
- let storeForwardInfo = currentMessage.forwardInfo.flatMap(StoreMessageForwardInfo.init)
- var attributes = currentMessage.attributes
- loop: for j in 0 ..< attributes.count {
- if let attribute = attributes[j] as? ViewCountMessageAttribute {
- attributes[j] = ViewCountMessageAttribute(count: max(attribute.count, Int(views)))
- }
- }
- return .update(StoreMessage(id: currentMessage.id, globallyUniqueId: currentMessage.globallyUniqueId, groupingKey: currentMessage.groupingKey, timestamp: currentMessage.timestamp, flags: StoreMessageFlags(currentMessage.flags), tags: currentMessage.tags, globalTags: currentMessage.globalTags, localTags: currentMessage.localTags, forwardInfo: storeForwardInfo, authorId: currentMessage.author?.id, text: currentMessage.text, attributes: attributes, media: currentMessage.media))
- })
- }
- /*if case let .messageViews(views, forwards) = viewCounts[i] {
+ if case let .messageViews(views, forwards) = viewCounts[i] {
transaction.updateMessage(messageIds[i], update: { currentMessage in
let storeForwardInfo = currentMessage.forwardInfo.flatMap(StoreMessageForwardInfo.init)
var attributes = currentMessage.attributes
@@ -626,7 +613,7 @@ public final class AccountViewTracker {
}
return .update(StoreMessage(id: currentMessage.id, globallyUniqueId: currentMessage.globallyUniqueId, groupingKey: currentMessage.groupingKey, timestamp: currentMessage.timestamp, flags: StoreMessageFlags(currentMessage.flags), tags: currentMessage.tags, globalTags: currentMessage.globalTags, localTags: currentMessage.localTags, forwardInfo: storeForwardInfo, authorId: currentMessage.author?.id, text: currentMessage.text, attributes: attributes, media: currentMessage.media))
})
- }*/
+ }
}
}
}
diff --git a/submodules/TelegramCore/Sources/ChannelOwnershipTransfer.swift b/submodules/TelegramCore/Sources/ChannelOwnershipTransfer.swift
index b66c178ffb..023130be15 100644
--- a/submodules/TelegramCore/Sources/ChannelOwnershipTransfer.swift
+++ b/submodules/TelegramCore/Sources/ChannelOwnershipTransfer.swift
@@ -67,7 +67,7 @@ public func checkOwnershipTranfserAvailability(postbox: Postbox, network: Networ
}
|> mapToSignal { updates -> Signal in
accountStateManager.addUpdates(updates)
- return.complete()
+ return .complete()
}
}
}
diff --git a/submodules/TelegramCore/Sources/Countries.swift b/submodules/TelegramCore/Sources/Countries.swift
new file mode 100644
index 0000000000..9d1349f6fb
--- /dev/null
+++ b/submodules/TelegramCore/Sources/Countries.swift
@@ -0,0 +1,72 @@
+import Foundation
+import Postbox
+import SwiftSignalKit
+import TelegramApi
+
+import SyncCore
+
+public struct Country {
+ public struct CountryCode {
+ public let code: String
+ public let prefixes: [String]
+ public let patterns: [String]
+
+ public init(code: String, prefixes: [String], patterns: [String]) {
+ self.code = code
+ self.prefixes = prefixes
+ self.patterns = patterns
+ }
+ }
+
+ public let code: String
+ public let defaultName: String
+ public let name: String
+ public let countryCodes: [CountryCode]
+
+ public init(code: String, defaultName: String, name: String, countryCodes: [CountryCode]) {
+ self.code = code
+ self.defaultName = defaultName
+ self.name = name
+ self.countryCodes = countryCodes
+ }
+}
+
+public func getCountriesList(network: Network, langCode: String) -> Signal<[Country], NoError> {
+ return network.request(Api.functions.help.getCountriesList(langCode: langCode, hash: 0))
+ |> map(Optional.init)
+ |> `catch` { _ -> Signal in
+ return .single(nil)
+ }
+ |> map { result in
+ if let result = result {
+ switch result {
+ case let .countriesList(apiCountries, hash):
+ return apiCountries.map { Country(apiCountry: $0) }
+ case .countriesListNotModified:
+ return []
+ }
+ } else {
+ return []
+ }
+ }
+}
+
+extension Country.CountryCode {
+ init(apiCountryCode: Api.help.CountryCode) {
+ switch apiCountryCode {
+ case let .countryCode(_, countryCode, apiPrefixes, apiPatterns):
+ let prefixes: [String] = apiPrefixes.flatMap { $0 } ?? []
+ let patterns: [String] = apiPatterns.flatMap { $0 } ?? []
+ self.init(code: countryCode, prefixes: prefixes, patterns: patterns)
+ }
+ }
+}
+
+extension Country {
+ init(apiCountry: Api.help.Country) {
+ switch apiCountry {
+ case let .country(iso2, defaultName, name, countryCodes):
+ self.init(code: iso2, defaultName: defaultName, name: name, countryCodes: countryCodes.map { Country.CountryCode(apiCountryCode: $0) })
+ }
+ }
+}
diff --git a/submodules/TelegramCore/Sources/ReplyMarkupMessageAttribute.swift b/submodules/TelegramCore/Sources/ReplyMarkupMessageAttribute.swift
index 587ee1be42..3f42956000 100644
--- a/submodules/TelegramCore/Sources/ReplyMarkupMessageAttribute.swift
+++ b/submodules/TelegramCore/Sources/ReplyMarkupMessageAttribute.swift
@@ -9,11 +9,11 @@ extension ReplyMarkupButton {
switch apiButton {
case let .keyboardButton(text):
self.init(title: text, titleWhenForwarded: nil, action: .text)
- case let .keyboardButtonCallback(text, data):
+ case let .keyboardButtonCallback(flags, text, data):
let memory = malloc(data.size)!
memcpy(memory, data.data, data.size)
let dataBuffer = MemoryBuffer(memory: memory, capacity: data.size, length: data.size, freeWhenDone: true)
- self.init(title: text, titleWhenForwarded: nil, action: .callback(dataBuffer))
+ self.init(title: text, titleWhenForwarded: nil, action: .callback(requiresPassword: (flags & (1 << 0)) != 0, data: dataBuffer))
case let .keyboardButtonRequestGeoLocation(text):
self.init(title: text, titleWhenForwarded: nil, action: .requestMap)
case let .keyboardButtonRequestPhone(text):
diff --git a/submodules/TelegramCore/Sources/RequestMessageActionCallback.swift b/submodules/TelegramCore/Sources/RequestMessageActionCallback.swift
index 7631d4bee6..5aa33db84d 100644
--- a/submodules/TelegramCore/Sources/RequestMessageActionCallback.swift
+++ b/submodules/TelegramCore/Sources/RequestMessageActionCallback.swift
@@ -3,8 +3,6 @@ import Postbox
import SwiftSignalKit
import TelegramApi
import MtProtoKit
-
-
import SyncCore
public enum MessageActionCallbackResult {
@@ -14,8 +12,69 @@ public enum MessageActionCallbackResult {
case url(String)
}
-public func requestMessageActionCallback(account: Account, messageId: MessageId, isGame:Bool, data: MemoryBuffer?) -> Signal {
+public enum MessageActionCallbackError {
+ case generic
+ case twoStepAuthMissing
+ case twoStepAuthTooFresh(Int32)
+ case authSessionTooFresh(Int32)
+ case limitExceeded
+ case requestPassword
+ case invalidPassword
+ case restricted
+ case userBlocked
+}
+
+public func requestMessageActionCallbackPasswordCheck(account: Account, messageId: MessageId, isGame: Bool, data: MemoryBuffer?) -> Signal {
return account.postbox.loadedPeerWithId(messageId.peerId)
+ |> castError(MessageActionCallbackError.self)
+ |> take(1)
+ |> mapToSignal { peer in
+ if let inputPeer = apiInputPeer(peer) {
+ var flags: Int32 = 0
+ var dataBuffer: Buffer?
+ if let data = data {
+ flags |= Int32(1 << 0)
+ dataBuffer = Buffer(data: data.makeData())
+ }
+ if isGame {
+ flags |= Int32(1 << 1)
+ }
+
+ return account.network.request(Api.functions.messages.getBotCallbackAnswer(flags: flags, peer: inputPeer, msgId: messageId.id, data: dataBuffer, password: .inputCheckPasswordEmpty))
+ |> mapError { error -> MessageActionCallbackError in
+ if error.errorDescription == "PASSWORD_HASH_INVALID" {
+ return .requestPassword
+ } else if error.errorDescription == "PASSWORD_MISSING" {
+ return .twoStepAuthMissing
+ } else if error.errorDescription.hasPrefix("PASSWORD_TOO_FRESH_") {
+ let timeout = String(error.errorDescription[error.errorDescription.index(error.errorDescription.startIndex, offsetBy: "PASSWORD_TOO_FRESH_".count)...])
+ if let value = Int32(timeout) {
+ return .twoStepAuthTooFresh(value)
+ }
+ } else if error.errorDescription.hasPrefix("SESSION_TOO_FRESH_") {
+ let timeout = String(error.errorDescription[error.errorDescription.index(error.errorDescription.startIndex, offsetBy: "SESSION_TOO_FRESH_".count)...])
+ if let value = Int32(timeout) {
+ return .authSessionTooFresh(value)
+ }
+ } else if error.errorDescription == "USER_PRIVACY_RESTRICTED" {
+ return .restricted
+ } else if error.errorDescription == "USER_BLOCKED" {
+ return .userBlocked
+ }
+ return .generic
+ }
+ |> mapToSignal { _ -> Signal in
+ return .complete()
+ }
+ } else {
+ return .fail(.generic)
+ }
+ }
+}
+
+public func requestMessageActionCallback(account: Account, messageId: MessageId, isGame :Bool, password: String?, data: MemoryBuffer?) -> Signal {
+ return account.postbox.loadedPeerWithId(messageId.peerId)
+ |> castError(MessageActionCallbackError.self)
|> take(1)
|> mapToSignal { peer in
if let inputPeer = apiInputPeer(peer) {
@@ -28,28 +87,79 @@ public func requestMessageActionCallback(account: Account, messageId: MessageId,
if isGame {
flags |= Int32(1 << 1)
}
- return account.network.request(Api.functions.messages.getBotCallbackAnswer(flags: flags, peer: inputPeer, msgId: messageId.id, data: dataBuffer))
- |> map(Optional.init)
- |> `catch` { _ -> Signal in
- return .single(nil)
- }
- |> map { result -> MessageActionCallbackResult in
- guard let result = result else {
- return .none
+
+ let checkPassword: Signal
+ if let password = password, !password.isEmpty {
+ flags |= Int32(1 << 2)
+
+ checkPassword = twoStepAuthData(account.network)
+ |> mapError { error -> MessageActionCallbackError in
+ if error.errorDescription.hasPrefix("FLOOD_WAIT") {
+ return .limitExceeded
+ } else {
+ return .generic
+ }
}
- switch result {
- case let .botCallbackAnswer(flags, message, url, cacheTime):
- if let message = message {
- if (flags & (1 << 1)) != 0 {
- return .alert(message)
- } else {
- return .toast(message)
- }
- } else if let url = url {
- return .url(url)
- } else {
- return .none
+ |> mapToSignal { authData -> Signal in
+ if let currentPasswordDerivation = authData.currentPasswordDerivation, let srpSessionData = authData.srpSessionData {
+ guard let kdfResult = passwordKDF(encryptionProvider: account.network.encryptionProvider, password: password, derivation: currentPasswordDerivation, srpSessionData: srpSessionData) else {
+ return .fail(.generic)
}
+ return .single(.inputCheckPasswordSRP(srpId: kdfResult.id, A: Buffer(data: kdfResult.A), M1: Buffer(data: kdfResult.M1)))
+ } else {
+ return .fail(.twoStepAuthMissing)
+ }
+ }
+ } else {
+ checkPassword = .single(nil)
+ }
+
+ return checkPassword
+ |> mapToSignal { password -> Signal in
+ return account.network.request(Api.functions.messages.getBotCallbackAnswer(flags: flags, peer: inputPeer, msgId: messageId.id, data: dataBuffer, password: password))
+ |> map(Optional.init)
+ |> mapError { error -> MessageActionCallbackError in
+ if error.errorDescription.hasPrefix("FLOOD_WAIT") {
+ return .limitExceeded
+ } else if error.errorDescription == "PASSWORD_HASH_INVALID" {
+ return .invalidPassword
+ } else if error.errorDescription == "PASSWORD_MISSING" {
+ return .twoStepAuthMissing
+ } else if error.errorDescription.hasPrefix("PASSWORD_TOO_FRESH_") {
+ let timeout = String(error.errorDescription[error.errorDescription.index(error.errorDescription.startIndex, offsetBy: "PASSWORD_TOO_FRESH_".count)...])
+ if let value = Int32(timeout) {
+ return .twoStepAuthTooFresh(value)
+ }
+ } else if error.errorDescription.hasPrefix("SESSION_TOO_FRESH_") {
+ let timeout = String(error.errorDescription[error.errorDescription.index(error.errorDescription.startIndex, offsetBy: "SESSION_TOO_FRESH_".count)...])
+ if let value = Int32(timeout) {
+ return .authSessionTooFresh(value)
+ }
+ } else if error.errorDescription == "USER_PRIVACY_RESTRICTED" {
+ return .restricted
+ } else if error.errorDescription == "USER_BLOCKED" {
+ return .userBlocked
+ }
+ return .generic
+ }
+ |> map { result -> MessageActionCallbackResult in
+ guard let result = result else {
+ return .none
+ }
+ switch result {
+ case let .botCallbackAnswer(flags, message, url, cacheTime):
+ if let message = message {
+ if (flags & (1 << 1)) != 0 {
+ return .alert(message)
+ } else {
+ return .toast(message)
+ }
+ } else if let url = url {
+ return .url(url)
+ } else {
+ return .none
+ }
+ }
}
}
} else {
diff --git a/submodules/TelegramCore/Sources/Serialization.swift b/submodules/TelegramCore/Sources/Serialization.swift
index eee8616a22..9d7dec93c3 100644
--- a/submodules/TelegramCore/Sources/Serialization.swift
+++ b/submodules/TelegramCore/Sources/Serialization.swift
@@ -210,7 +210,7 @@ public class BoxedMessage: NSObject {
public class Serialization: NSObject, MTSerialization {
public func currentLayer() -> UInt {
- return 117
+ return 118
}
public func parseMessage(_ data: Data!) -> Any! {
diff --git a/submodules/TelegramCore/Sources/StoreMessage_Telegram.swift b/submodules/TelegramCore/Sources/StoreMessage_Telegram.swift
index aa1ec9bd2e..fd4d4f3d25 100644
--- a/submodules/TelegramCore/Sources/StoreMessage_Telegram.swift
+++ b/submodules/TelegramCore/Sources/StoreMessage_Telegram.swift
@@ -136,7 +136,7 @@ func apiMessagePeerId(_ messsage: Api.Message) -> PeerId? {
func apiMessagePeerIds(_ message: Api.Message) -> [PeerId] {
switch message {
- case let .message(flags, _, fromId, toId, fwdHeader, viaBotId, _, _, _, media, _, entities, _, _, _, _, _):
+ case let .message(flags, _, fromId, toId, fwdHeader, viaBotId, _, _, _, media, _, entities, _, _, _, _, _, _):
let peerId: PeerId
switch toId {
case let .peerUser(userId):
@@ -240,7 +240,7 @@ func apiMessagePeerIds(_ message: Api.Message) -> [PeerId] {
func apiMessageAssociatedMessageIds(_ message: Api.Message) -> [MessageId]? {
switch message {
- case let .message(flags, _, fromId, toId, _, _, replyToMsgId, _, _, _, _, _, _, _, _, _, _):
+ case let .message(flags, _, fromId, toId, _, _, replyToMsgId, _, _, _, _, _, _, _, _, _, _, _):
if let replyToMsgId = replyToMsgId {
let peerId: PeerId
switch toId {
@@ -398,7 +398,7 @@ func messageTextEntitiesFromApiEntities(_ entities: [Api.MessageEntity]) -> [Mes
extension StoreMessage {
convenience init?(apiMessage: Api.Message, namespace: MessageId.Namespace = Namespaces.Message.Cloud) {
switch apiMessage {
- case let .message(flags, id, fromId, toId, fwdFrom, viaBotId, replyToMsgId, date, message, media, replyMarkup, entities, views, editDate, postAuthor, groupingId, restrictionReason):
+ case let .message(flags, id, fromId, toId, fwdFrom, viaBotId, replyToMsgId, date, message, media, replyMarkup, entities, views, forwards, editDate, postAuthor, groupingId, restrictionReason):
let peerId: PeerId
var authorId: PeerId?
switch toId {
@@ -517,14 +517,16 @@ extension StoreMessage {
attributes.append(ReplyMessageAttribute(messageId: MessageId(peerId: peerId, namespace: Namespaces.Message.Cloud, id: replyToMsgId)))
}
- if let views = views, namespace != Namespaces.Message.ScheduledCloud {
- attributes.append(ViewCountMessageAttribute(count: Int(views)))
+ if namespace != Namespaces.Message.ScheduledCloud {
+ if let views = views {
+ attributes.append(ViewCountMessageAttribute(count: Int(views)))
+ }
+
+ if let forwards = forwards {
+ attributes.append(ForwardCountMessageAttribute(count: Int(forwards)))
+ }
}
- /*if let forwards = forwards, namespace != Namespaces.Message.ScheduledCloud {
- attributes.append(ForwardCountMessageAttribute(count: Int(forwards)))
- }*/
-
if let editDate = editDate {
attributes.append(EditedMessageAttribute(date: editDate, isHidden: (flags & (1 << 21)) != 0))
}
diff --git a/submodules/TelegramCore/Sources/UpdateMessageService.swift b/submodules/TelegramCore/Sources/UpdateMessageService.swift
index 34cd793682..7ca077332f 100644
--- a/submodules/TelegramCore/Sources/UpdateMessageService.swift
+++ b/submodules/TelegramCore/Sources/UpdateMessageService.swift
@@ -58,7 +58,7 @@ class UpdateMessageService: NSObject, MTMessageService {
self.putNext(groups)
}
case let .updateShortChatMessage(flags, id, fromId, chatId, message, pts, ptsCount, date, fwdFrom, viaBotId, replyToMsgId, entities):
- let generatedMessage = Api.Message.message(flags: flags, id: id, fromId: fromId, toId: Api.Peer.peerChat(chatId: chatId), fwdFrom: fwdFrom, viaBotId: viaBotId, replyToMsgId: replyToMsgId, date: date, message: message, media: Api.MessageMedia.messageMediaEmpty, replyMarkup: nil, entities: entities, views: nil, editDate: nil, postAuthor: nil, groupedId: nil, restrictionReason: nil)
+ let generatedMessage = Api.Message.message(flags: flags, id: id, fromId: fromId, toId: Api.Peer.peerChat(chatId: chatId), fwdFrom: fwdFrom, viaBotId: viaBotId, replyToMsgId: replyToMsgId, date: date, message: message, media: Api.MessageMedia.messageMediaEmpty, replyMarkup: nil, entities: entities, views: nil, forwards: nil, editDate: nil, postAuthor: nil, groupedId: nil, restrictionReason: nil)
let update = Api.Update.updateNewMessage(message: generatedMessage, pts: pts, ptsCount: ptsCount)
let groups = groupUpdates([update], users: [], chats: [], date: date, seqRange: nil)
if groups.count != 0 {
@@ -75,7 +75,7 @@ class UpdateMessageService: NSObject, MTMessageService {
generatedToId = Api.Peer.peerUser(userId: self.peerId.id)
}
- let generatedMessage = Api.Message.message(flags: flags, id: id, fromId: generatedFromId, toId: generatedToId, fwdFrom: fwdFrom, viaBotId: viaBotId, replyToMsgId: replyToMsgId, date: date, message: message, media: Api.MessageMedia.messageMediaEmpty, replyMarkup: nil, entities: entities, views: nil, editDate: nil, postAuthor: nil, groupedId: nil, restrictionReason: nil)
+ let generatedMessage = Api.Message.message(flags: flags, id: id, fromId: generatedFromId, toId: generatedToId, fwdFrom: fwdFrom, viaBotId: viaBotId, replyToMsgId: replyToMsgId, date: date, message: message, media: Api.MessageMedia.messageMediaEmpty, replyMarkup: nil, entities: entities, views: nil, forwards: nil, editDate: nil, postAuthor: nil, groupedId: nil, restrictionReason: nil)
let update = Api.Update.updateNewMessage(message: generatedMessage, pts: pts, ptsCount: ptsCount)
let groups = groupUpdates([update], users: [], chats: [], date: date, seqRange: nil)
if groups.count != 0 {
diff --git a/submodules/TelegramPresentationData/Sources/PresentationStrings.swift b/submodules/TelegramPresentationData/Sources/PresentationStrings.swift
index f574819ef3..dd235e125f 100644
--- a/submodules/TelegramPresentationData/Sources/PresentationStrings.swift
+++ b/submodules/TelegramPresentationData/Sources/PresentationStrings.swift
@@ -5004,337 +5004,338 @@ public final class PresentationStrings: Equatable {
public var Channel_Setup_TypePublicHelp: String { return self._s[4517]! }
public var Passport_Identity_EditInternalPassport: String { return self._s[4518]! }
public var PhotoEditor_Skip: String { return self._s[4519]! }
- public func MessageTimer_ShortMinutes(_ value: Int32) -> String {
+ public func ServiceMessage_GameScoreSimple(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[0 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func StickerPack_AddStickerCount(_ value: Int32) -> String {
+ public func ForwardedGifs(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[1 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PUSH_MESSAGE_PHOTOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[2 * 6 + Int(form.rawValue)]!, _1, _2)
+ public func Conversation_LiveLocationMembersCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[2 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func OldChannels_InactiveYear(_ value: Int32) -> String {
+ public func MessageTimer_ShortSeconds(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[3 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func Media_ShareItem(_ value: Int32) -> String {
+ public func MessageTimer_Years(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[4 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func AttachmentMenu_SendPhoto(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[5 * 6 + Int(form.rawValue)]!, stringValue)
+ public func PUSH_CHAT_MESSAGE_FWDS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[5 * 6 + Int(form.rawValue)]!, _2, _1, _3)
}
- public func Call_Seconds(_ value: Int32) -> String {
+ public func Notification_GameScoreExtended(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[6 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func Notification_GameScoreSelfExtended(_ value: Int32) -> String {
+ public func StickerPack_AddStickerCount(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[7 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func Watch_UserInfo_Mute(_ value: Int32) -> String {
+ public func OldChannels_Leave(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[8 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PUSH_CHANNEL_MESSAGE_PHOTOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[9 * 6 + Int(form.rawValue)]!, _1, _2)
+ public func OldChannels_InactiveMonth(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[9 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func MuteFor_Hours(_ value: Int32) -> String {
+ public func Stats_GroupTopPosterChars(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[10 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func InviteText_ContactsCountText(_ value: Int32) -> String {
+ public func MessageTimer_ShortMinutes(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[11 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func ForwardedAudios(_ value: Int32) -> String {
+ public func Contacts_InviteContacts(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[12 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func Notification_GameScoreSelfSimple(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[13 * 6 + Int(form.rawValue)]!, stringValue)
+ public func PUSH_CHANNEL_MESSAGE_VIDEOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[13 * 6 + Int(form.rawValue)]!, _1, _2)
}
- public func SharedMedia_Video(_ value: Int32) -> String {
+ public func Stats_GroupTopPosterMessages(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[14 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PUSH_MESSAGE_VIDEOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ public func MessageTimer_Months(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[15 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PUSH_CHANNEL_MESSAGES(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[15 * 6 + Int(form.rawValue)]!, _1, _2)
- }
- public func Invitation_Members(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[16 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_ShortHours(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[17 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PollResults_ShowMore(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[18 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func LiveLocation_MenuChatsCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[19 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func OldChannels_InactiveWeek(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[20 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Map_ETAMinutes(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[21 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Wallet_Updated_MinutesAgo(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[22 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedStickers(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[23 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func StickerPack_RemoveStickerCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[24 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Conversation_LiveLocationMembersCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[25 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PUSH_CHAT_MESSAGE_FWDS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[26 * 6 + Int(form.rawValue)]!, _2, _1, _3)
- }
- public func Notifications_Exceptions(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[27 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PUSH_CHAT_MESSAGES(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[28 * 6 + Int(form.rawValue)]!, _2, _1, _3)
- }
- public func AttachmentMenu_SendGif(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[29 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func SharedMedia_Generic(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[30 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PUSH_CHAT_MESSAGE_ROUNDS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[31 * 6 + Int(form.rawValue)]!, _2, _1, _3)
- }
- public func PUSH_CHANNEL_MESSAGE_FWDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[32 * 6 + Int(form.rawValue)]!, _1, _2)
- }
- public func Conversation_StatusMembers(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[33 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MuteExpires_Minutes(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[34 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Call_ShortSeconds(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[35 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ServiceMessage_GameScoreSelfSimple(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[36 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func GroupInfo_ParticipantCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[37 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Call_ShortMinutes(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[38 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MuteFor_Days(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[39 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func SharedMedia_Photo(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[40 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupShowMoreTopPosters(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[41 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_MessageViews(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[42 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func QuickSend_Photos(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[43 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Contacts_ImportersCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[44 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedPhotos(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[45 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedAuthorsOthers(_ selector: Int32, _ _0: String, _ _1: String) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[46 * 6 + Int(form.rawValue)]!, _0, _1)
- }
- public func StickerPack_StickerCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[47 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Conversation_StatusSubscribers(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[48 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Notifications_ExceptionMuteExpires_Minutes(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[49 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MuteExpires_Days(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[50 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func AttachmentMenu_SendVideo(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[51 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_MessageForwards(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[52 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func StickerPack_AddMaskCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[53 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Media_ShareVideo(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[54 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Watch_LastSeen_MinutesAgo(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[55 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PUSH_MESSAGES(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[56 * 6 + Int(form.rawValue)]!, _1, _2)
- }
- public func Notification_GameScoreSimple(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[57 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func SharedMedia_File(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[58 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ChatListFilter_ShowMoreChats(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[59 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func UserCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[60 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PUSH_CHAT_MESSAGE_VIDEOS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[61 * 6 + Int(form.rawValue)]!, _2, _1, _3)
+ return String(format: self._ps[16 * 6 + Int(form.rawValue)]!, _1, _2)
}
public func Call_Minutes(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[62 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[17 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_GroupTopInviterInvites(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[18 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessageTimer_ShortHours(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[19 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessageTimer_Minutes(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[20 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Conversation_StatusOnline(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[21 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func LiveLocation_MenuChatsCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[22 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func AttachmentMenu_SendVideo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[23 * 6 + Int(form.rawValue)]!, stringValue)
}
public func Wallet_Updated_HoursAgo(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[63 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[24 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func LastSeen_MinutesAgo(_ value: Int32) -> String {
+ public func PUSH_MESSAGE_PHOTOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[25 * 6 + Int(form.rawValue)]!, _1, _2)
+ }
+ public func Notifications_ExceptionMuteExpires_Hours(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[64 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[26 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func SharedMedia_DeleteItemsConfirmation(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[27 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Wallet_Updated_MinutesAgo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[28 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Forward_ConfirmMultipleFiles(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[29 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessageTimer_Hours(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[30 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MuteExpires_Days(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[31 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func VoiceOver_Chat_ContactPhoneNumberCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[32 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Notifications_Exceptions(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[33 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ChatList_SelectedChats(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[34 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ServiceMessage_GameScoreExtended(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[35 * 6 + Int(form.rawValue)]!, stringValue)
}
public func Passport_Scans(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[65 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[36 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func ChatList_DeletedChats(_ value: Int32) -> String {
+ public func PUSH_MESSAGE_FWDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[37 * 6 + Int(form.rawValue)]!, _1, _2)
+ }
+ public func LiveLocationUpdated_MinutesAgo(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[66 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[38 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PeopleNearby_ShowMorePeople(_ value: Int32) -> String {
+ public func PUSH_CHAT_MESSAGE_PHOTOS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[39 * 6 + Int(form.rawValue)]!, _2, _1, _3)
+ }
+ public func MessageTimer_ShortDays(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[40 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedVideos(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[41 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Watch_LastSeen_HoursAgo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[42 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Call_ShortSeconds(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[43 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessageTimer_Days(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[44 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ServiceMessage_GameScoreSelfSimple(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[45 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func LastSeen_MinutesAgo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[46 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func UserCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[47 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessagePoll_QuizCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[48 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedAuthorsOthers(_ selector: Int32, _ _0: String, _ _1: String) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[49 * 6 + Int(form.rawValue)]!, _0, _1)
+ }
+ public func Map_ETAMinutes(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[50 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Conversation_StatusSubscribers(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[51 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ChatList_DeleteConfirmation(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[52 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MuteExpires_Minutes(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[53 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Notification_GameScoreSelfSimple(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[54 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PrivacyLastSeenSettings_AddUsers(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[55 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func InviteText_ContactsCountText(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[56 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ServiceMessage_GameScoreSelfExtended(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[57 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func StickerPack_RemoveStickerCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[58 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_GroupTopAdminKicks(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[59 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedLocations(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[60 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedMessages(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[61 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Media_ShareVideo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[62 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func QuickSend_Photos(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[63 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func OldChannels_InactiveWeek(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[64 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PUSH_CHAT_MESSAGE_ROUNDS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[65 * 6 + Int(form.rawValue)]!, _2, _1, _3)
+ }
+ public func PUSH_CHAT_MESSAGE_VIDEOS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[66 * 6 + Int(form.rawValue)]!, _2, _1, _3)
+ }
+ public func Conversation_StatusMembers(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[67 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func VoiceOver_Chat_PollVotes(_ value: Int32) -> String {
+ public func Contacts_ImportersCount(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[68 * 6 + Int(form.rawValue)]!, stringValue)
@@ -5344,356 +5345,355 @@ public final class PresentationStrings: Equatable {
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[69 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PUSH_MESSAGE_FWDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[70 * 6 + Int(form.rawValue)]!, _1, _2)
- }
- public func PUSH_MESSAGE_ROUNDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[71 * 6 + Int(form.rawValue)]!, _1, _2)
- }
- public func PUSH_CHANNEL_MESSAGE_ROUNDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[72 * 6 + Int(form.rawValue)]!, _1, _2)
- }
- public func ForwardedVideos(_ value: Int32) -> String {
+ public func OldChannels_InactiveYear(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[73 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[70 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func ServiceMessage_GameScoreExtended(_ value: Int32) -> String {
+ public func Notifications_ExceptionMuteExpires_Minutes(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[74 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[71 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func Media_SharePhoto(_ value: Int32) -> String {
+ public func ChatList_DeletedChats(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[75 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Chat_DeleteMessagesConfirmation(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[76 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedMessages(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[77 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func AttachmentMenu_SendItem(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[78 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ChatList_MessagePhotos(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[79 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func OldChannels_InactiveMonth(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[80 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ChatList_SelectedChats(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[81 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func VoiceOver_Chat_ContactPhoneNumberCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[82 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedFiles(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[83 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessagePoll_VotedCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[84 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupTopPosterChars(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[85 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Conversation_SelectedMessages(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[86 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ServiceMessage_GameScoreSimple(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[87 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Contacts_InviteContacts(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[88 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func LastSeen_HoursAgo(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[89 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func SharedMedia_Link(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[90 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_ShortSeconds(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[91 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupTopAdminKicks(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[92 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedVideoMessages(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[93 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_Hours(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[94 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Notifications_ExceptionMuteExpires_Days(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[95 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedLocations(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[96 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Theme_UsersCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[97 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessagePoll_QuizCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[98 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupShowMoreTopAdmins(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[99 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func CreatePoll_AddMoreOptions(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[100 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MuteExpires_Hours(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[101 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ChatList_DeleteConfirmation(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[102 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func GroupInfo_ShowMoreMembers(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[103 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_Years(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[104 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func VoiceOver_Chat_ContactEmailCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[105 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func LiveLocationUpdated_MinutesAgo(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[106 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedGifs(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[107 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Wallpaper_DeleteConfirmation(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[108 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupShowMoreTopInviters(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[109 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_Seconds(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[110 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PUSH_CHAT_MESSAGE_PHOTOS(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[111 * 6 + Int(form.rawValue)]!, _2, _1, _3)
+ return String(format: self._ps[72 * 6 + Int(form.rawValue)]!, stringValue)
}
public func VoiceOver_Chat_PollOptionCount(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[112 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[73 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PUSH_CHANNEL_MESSAGES(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[113 * 6 + Int(form.rawValue)]!, _1, _2)
- }
- public func Map_ETAHours(_ value: Int32) -> String {
+ public func StickerPack_AddMaskCount(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[114 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func PasscodeSettings_FailedAttempts(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[115 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Notifications_ExceptionMuteExpires_Hours(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[116 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ForwardedContacts(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[117 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_Weeks(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[118 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func InstantPage_Views(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[119 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupTopAdminBans(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[120 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func SharedMedia_DeleteItemsConfirmation(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[121 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[74 * 6 + Int(form.rawValue)]!, stringValue)
}
public func StickerPack_RemoveMaskCount(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[122 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[75 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func MessageTimer_Minutes(_ value: Int32) -> String {
+ public func Invitation_Members(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[123 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ChatList_MessageVideos(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[124 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupTopPosterMessages(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[125 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func ServiceMessage_GameScoreSelfExtended(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[126 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Stats_GroupTopInviterInvites(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[127 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_ShortWeeks(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[128 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func OldChannels_GroupFormat(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[129 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func DialogList_LiveLocationChatsCount(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[130 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Notification_GameScoreExtended(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[131 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func Conversation_StatusOnline(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[132 * 6 + Int(form.rawValue)]!, stringValue)
- }
- public func MessageTimer_Days(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[133 * 6 + Int(form.rawValue)]!, stringValue)
+ return String(format: self._ps[76 * 6 + Int(form.rawValue)]!, stringValue)
}
public func Stats_GroupTopAdminDeletions(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[77 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Media_ShareItem(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[78 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func AttachmentMenu_SendGif(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[79 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedFiles(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[80 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func InstantPage_Views(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[81 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedContacts(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[82 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessageTimer_ShortWeeks(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[83 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func LastSeen_HoursAgo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[84 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_GroupTopAdminBans(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[85 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_GroupShowMoreTopInviters(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[86 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_GroupShowMoreTopPosters(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[87 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Call_Seconds(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[88 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessageTimer_Seconds(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[89 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Chat_DeleteMessagesConfirmation(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[90 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_MessageViews(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[91 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Media_SharePhoto(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[92 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Watch_LastSeen_MinutesAgo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[93 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func CreatePoll_AddMoreOptions(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[94 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PUSH_CHAT_MESSAGES(_ selector: Int32, _ _2: String, _ _1: String, _ _3: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[95 * 6 + Int(form.rawValue)]!, _2, _1, _3)
+ }
+ public func PUSH_CHANNEL_MESSAGE_FWDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[96 * 6 + Int(form.rawValue)]!, _1, _2)
+ }
+ public func ChatList_MessagePhotos(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[97 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_MessageForwards(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[98 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func AttachmentMenu_SendPhoto(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[99 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func StickerPack_StickerCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[100 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedAudios(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[101 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func VoiceOver_Chat_ContactEmailCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[102 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func SharedMedia_Photo(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[103 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func SharedMedia_Link(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[104 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Call_ShortMinutes(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[105 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ForwardedVideoMessages(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[106 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func SharedMedia_Generic(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[107 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessagePoll_VotedCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[108 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Notifications_ExceptionMuteExpires_Days(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[109 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func SharedMedia_Video(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[110 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Notification_GameScoreSimple(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[111 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Stats_GroupShowMoreTopAdmins(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[112 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Notification_GameScoreSelfExtended(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[113 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PUSH_CHANNEL_MESSAGE_PHOTOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[114 * 6 + Int(form.rawValue)]!, _1, _2)
+ }
+ public func AttachmentMenu_SendItem(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[115 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MuteExpires_Hours(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[116 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func DialogList_LiveLocationChatsCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[117 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func ChatListFilter_ShowMoreChats(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[118 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PUSH_MESSAGE_VIDEOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[119 * 6 + Int(form.rawValue)]!, _1, _2)
+ }
+ public func ForwardedPhotos(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[120 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PUSH_CHANNEL_MESSAGE_ROUNDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[121 * 6 + Int(form.rawValue)]!, _1, _2)
+ }
+ public func PUSH_MESSAGE_ROUNDS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[122 * 6 + Int(form.rawValue)]!, _1, _2)
+ }
+ public func MuteFor_Days(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[123 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func OldChannels_GroupFormat(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[124 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func SharedMedia_File(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[125 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PollResults_ShowMore(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[126 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Watch_UserInfo_Mute(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[127 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func GroupInfo_ShowMoreMembers(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[128 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func PeopleNearby_ShowMorePeople(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[129 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Wallpaper_DeleteConfirmation(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[130 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func MessageTimer_Weeks(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[131 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func Theme_UsersCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[132 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func GroupInfo_ParticipantCount(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[133 * 6 + Int(form.rawValue)]!, stringValue)
+ }
+ public func VoiceOver_Chat_PollVotes(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[134 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func Watch_LastSeen_HoursAgo(_ value: Int32) -> String {
+ public func Conversation_SelectedMessages(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[135 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func MessageTimer_Months(_ value: Int32) -> String {
+ public func ChatList_MessageVideos(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[136 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func MessageTimer_ShortDays(_ value: Int32) -> String {
+ public func MuteFor_Hours(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[137 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PrivacyLastSeenSettings_AddUsers(_ value: Int32) -> String {
- let form = getPluralizationForm(self.lc, value)
- let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
- return String(format: self._ps[138 * 6 + Int(form.rawValue)]!, stringValue)
+ public func PUSH_MESSAGES(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
+ let form = getPluralizationForm(self.lc, selector)
+ return String(format: self._ps[138 * 6 + Int(form.rawValue)]!, _1, _2)
}
- public func OldChannels_Leave(_ value: Int32) -> String {
+ public func ForwardedStickers(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[139 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func PUSH_CHANNEL_MESSAGE_VIDEOS(_ selector: Int32, _ _1: String, _ _2: Int32) -> String {
- let form = getPluralizationForm(self.lc, selector)
- return String(format: self._ps[140 * 6 + Int(form.rawValue)]!, _1, _2)
+ public func Map_ETAHours(_ value: Int32) -> String {
+ let form = getPluralizationForm(self.lc, value)
+ let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
+ return String(format: self._ps[140 * 6 + Int(form.rawValue)]!, stringValue)
}
- public func Forward_ConfirmMultipleFiles(_ value: Int32) -> String {
+ public func PasscodeSettings_FailedAttempts(_ value: Int32) -> String {
let form = getPluralizationForm(self.lc, value)
let stringValue = presentationStringsFormattedNumber(value, self.groupingSeparator)
return String(format: self._ps[141 * 6 + Int(form.rawValue)]!, stringValue)
diff --git a/submodules/TelegramUI/Resources/PresentationStrings.mapping b/submodules/TelegramUI/Resources/PresentationStrings.mapping
index c48a93109f..eb8d162e64 100644
Binary files a/submodules/TelegramUI/Resources/PresentationStrings.mapping and b/submodules/TelegramUI/Resources/PresentationStrings.mapping differ
diff --git a/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryController.swift b/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryController.swift
index db77030f94..bf5948de32 100644
--- a/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryController.swift
+++ b/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryController.swift
@@ -58,6 +58,8 @@ final class AuthorizationSequencePhoneEntryController: ViewController {
self.openUrl = openUrl
self.back = back
+ loadServerCountryCodes(network: account.network)
+
super.init(navigationBarPresentationData: NavigationBarPresentationData(theme: AuthorizationSequenceController.navigationBarTheme(presentationData.theme), strings: NavigationBarStrings(presentationStrings: presentationData.strings)))
self.supportedOrientations = ViewControllerSupportedOrientations(regularSize: .all, compactSize: .portrait)
diff --git a/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryControllerNode.swift b/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryControllerNode.swift
index 8444c74660..0f514b7657 100644
--- a/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryControllerNode.swift
+++ b/submodules/TelegramUI/Sources/AuthorizationSequencePhoneEntryControllerNode.swift
@@ -121,26 +121,32 @@ private final class PhoneAndCountryNode: ASDisplayNode {
self.phoneInputNode.countryCodeField.textField.disableAutomaticKeyboardHandling = [.forward]
self.phoneInputNode.numberField.textField.disableAutomaticKeyboardHandling = [.forward]
-
self.countryButton.contentEdgeInsets = UIEdgeInsets(top: 0.0, left: 15.0, bottom: 10.0, right: 0.0)
self.countryButton.contentHorizontalAlignment = .left
- self.phoneInputNode.numberField.textField.attributedPlaceholder = NSAttributedString(string: strings.Login_PhonePlaceholder, font: Font.regular(20.0), textColor: theme.list.itemPlaceholderTextColor)
+// self.phoneInputNode.numberField.textField.attributedPlaceholder = NSAttributedString(string: strings.Login_PhonePlaceholder, font: Font.regular(20.0), textColor: theme.list.itemPlaceholderTextColor)
self.countryButton.addTarget(self, action: #selector(self.countryPressed), forControlEvents: .touchUpInside)
self.phoneInputNode.countryCodeUpdated = { [weak self] code, name in
+ let font = Font.with(size: 20.0, design: .monospace, traits: [])
if let strongSelf = self {
if let code = Int(code), let name = name, let countryName = countryCodeAndIdToName[CountryCodeAndId(code: code, id: name)] {
let flagString = emojiFlagForISOCountryCode(name as NSString)
let localizedName: String = AuthorizationSequenceCountrySelectionController.lookupCountryNameById(name, strings: strongSelf.strings) ?? countryName
strongSelf.countryButton.setTitle("\(flagString) \(localizedName)", with: Font.regular(20.0), with: theme.list.itemPrimaryTextColor, for: [])
+
+ strongSelf.phoneInputNode.mask = AuthorizationSequenceCountrySelectionController.lookupPatternByCode(code).flatMap { NSAttributedString(string: $0, font: font, textColor: theme.list.itemPlaceholderTextColor) }
} else if let code = Int(code), let (countryId, countryName) = countryCodeToIdAndName[code] {
let flagString = emojiFlagForISOCountryCode(countryId as NSString)
let localizedName: String = AuthorizationSequenceCountrySelectionController.lookupCountryNameById(countryId, strings: strongSelf.strings) ?? countryName
strongSelf.countryButton.setTitle("\(flagString) \(localizedName)", with: Font.regular(20.0), with: theme.list.itemPrimaryTextColor, for: [])
+
+ strongSelf.phoneInputNode.mask = AuthorizationSequenceCountrySelectionController.lookupPatternByCode(code).flatMap { NSAttributedString(string: $0, font: font, textColor: theme.list.itemPlaceholderTextColor) }
} else {
strongSelf.countryButton.setTitle(strings.Login_SelectCountry_Title, with: Font.regular(20.0), with: theme.list.itemPlaceholderTextColor, for: [])
+
+ strongSelf.phoneInputNode.mask = nil
}
}
}
@@ -165,12 +171,14 @@ private final class PhoneAndCountryNode: ASDisplayNode {
let countryCodeFrame = CGRect(origin: CGPoint(x: 18.0, y: size.height - 57.0), size: CGSize(width: 60.0, height: 57.0))
let numberFrame = CGRect(origin: CGPoint(x: 96.0, y: size.height - 57.0), size: CGSize(width: size.width - 96.0 - 8.0, height: 57.0))
+ let placeholderFrame = numberFrame.offsetBy(dx: -1.0, dy: 16.0)
let phoneInputFrame = countryCodeFrame.union(numberFrame)
self.phoneInputNode.frame = phoneInputFrame
self.phoneInputNode.countryCodeField.frame = countryCodeFrame.offsetBy(dx: -phoneInputFrame.minX, dy: -phoneInputFrame.minY)
self.phoneInputNode.numberField.frame = numberFrame.offsetBy(dx: -phoneInputFrame.minX, dy: -phoneInputFrame.minY)
+ self.phoneInputNode.placeholderNode.frame = placeholderFrame.offsetBy(dx: -phoneInputFrame.minX, dy: -phoneInputFrame.minY)
}
}
@@ -204,6 +212,8 @@ private final class ContactSyncNode: ASDisplayNode {
}
}
+
+
final class AuthorizationSequencePhoneEntryControllerNode: ASDisplayNode {
private let sharedContext: SharedAccountContext
private var account: UnauthorizedAccount
diff --git a/submodules/TelegramUI/Sources/ChatButtonKeyboardInputNode.swift b/submodules/TelegramUI/Sources/ChatButtonKeyboardInputNode.swift
index dfd63fe8b1..0d1ec9db8c 100644
--- a/submodules/TelegramUI/Sources/ChatButtonKeyboardInputNode.swift
+++ b/submodules/TelegramUI/Sources/ChatButtonKeyboardInputNode.swift
@@ -176,11 +176,11 @@ final class ChatButtonKeyboardInputNode: ChatInputNode {
self.controllerInteraction.shareAccountContact()
case .openWebApp:
if let message = self.message {
- self.controllerInteraction.requestMessageActionCallback(message.id, nil, true)
+ self.controllerInteraction.requestMessageActionCallback(message.id, nil, true, false)
}
- case let .callback(data):
+ case let .callback(requiresPassword, data):
if let message = self.message {
- self.controllerInteraction.requestMessageActionCallback(message.id, data, false)
+ self.controllerInteraction.requestMessageActionCallback(message.id, data, false, requiresPassword)
}
case let .switchInline(samePeer, query):
if let message = message {
diff --git a/submodules/TelegramUI/Sources/ChatController.swift b/submodules/TelegramUI/Sources/ChatController.swift
index 323db8b19e..24b975e867 100644
--- a/submodules/TelegramUI/Sources/ChatController.swift
+++ b/submodules/TelegramUI/Sources/ChatController.swift
@@ -793,7 +793,7 @@ public final class ChatControllerImpl: TelegramBaseController, ChatController, G
strongSelf.enqueueChatContextResult(collection, result, hideVia: true, closeMediaInput: true)
return true
- }, requestMessageActionCallback: { [weak self] messageId, data, isGame in
+ }, requestMessageActionCallback: { [weak self] messageId, data, isGame, requiresPassword in
if let strongSelf = self {
guard !strongSelf.presentationInterfaceState.isScheduledMessages else {
strongSelf.present(textAlertController(context: strongSelf.context, title: nil, text: strongSelf.presentationData.strings.ScheduledMessages_BotActionUnavailable, actions: [TextAlertAction(type: .defaultAction, title: strongSelf.presentationData.strings.Common_OK, action: {})]), in: .window(.root))
@@ -819,52 +819,73 @@ public final class ChatControllerImpl: TelegramBaseController, ChatController, G
}
})
- strongSelf.messageActionCallbackDisposable.set(((requestMessageActionCallback(account: strongSelf.context.account, messageId: messageId, isGame: isGame, data: data)
- |> afterDisposed {
- Queue.mainQueue().async {
- if let strongSelf = self {
- strongSelf.updateChatPresentationInterfaceState(animated: true, interactive: true, {
- return $0.updatedTitlePanelContext {
- if let index = $0.firstIndex(where: {
- switch $0 {
- case .requestInProgress:
- return true
- default:
- return false
- }
- }) {
- var updatedContexts = $0
- updatedContexts.remove(at: index)
- return updatedContexts
- }
- return $0
- }
+ let proceedWithResult: (MessageActionCallbackResult) -> Void = { [weak self] result in
+ guard let strongSelf = self else {
+ return
+ }
+
+ switch result {
+ case .none:
+ break
+ case let .alert(text):
+ strongSelf.present(textAlertController(context: strongSelf.context, title: nil, text: text, actions: [TextAlertAction(type: .defaultAction, title: strongSelf.presentationData.strings.Common_OK, action: {})]), in: .window(.root))
+ case let .toast(text):
+ let message: Signal = .single(text)
+ let noMessage: Signal = .single(nil)
+ let delayedNoMessage: Signal = noMessage |> delay(1.0, queue: Queue.mainQueue())
+ strongSelf.botCallbackAlertMessage.set(message |> then(delayedNoMessage))
+ case let .url(url):
+ if isGame {
+ strongSelf.chatDisplayNode.dismissInput()
+ strongSelf.effectiveNavigationController?.pushViewController(GameController(context: strongSelf.context, url: url, message: message))
+ } else {
+ strongSelf.openUrl(url, concealed: false)
+ }
+ }
+ }
+
+ let account = strongSelf.context.account
+ if requiresPassword {
+ strongSelf.messageActionCallbackDisposable.set((requestMessageActionCallbackPasswordCheck(account: account, messageId: messageId, isGame: isGame, data: data)
+ |> deliverOnMainQueue).start(error: { error in
+ let controller = ownershipTransferController(context: context, initialError: error, present: { c, a in
+ strongSelf.present(c, in: .window(.root), with: a)
+ }, commit: { password in
+ return requestMessageActionCallback(account: account, messageId: messageId, isGame: isGame, password: password, data: data)
+ }, completion: { result in
+ proceedWithResult(result)
})
+ strongSelf.present(controller, in: .window(.root))
+ }))
+ } else {
+ strongSelf.messageActionCallbackDisposable.set(((requestMessageActionCallback(account: account, messageId: messageId, isGame: isGame, password: nil, data: data)
+ |> afterDisposed {
+ Queue.mainQueue().async {
+ if let strongSelf = self {
+ strongSelf.updateChatPresentationInterfaceState(animated: true, interactive: true, {
+ return $0.updatedTitlePanelContext {
+ if let index = $0.firstIndex(where: {
+ switch $0 {
+ case .requestInProgress:
+ return true
+ default:
+ return false
+ }
+ }) {
+ var updatedContexts = $0
+ updatedContexts.remove(at: index)
+ return updatedContexts
+ }
+ return $0
+ }
+ })
+ }
}
- }
- })
- |> deliverOnMainQueue).start(next: { result in
- if let strongSelf = self {
- switch result {
- case .none:
- break
- case let .alert(text):
- strongSelf.present(textAlertController(context: strongSelf.context, title: nil, text: text, actions: [TextAlertAction(type: .defaultAction, title: strongSelf.presentationData.strings.Common_OK, action: {})]), in: .window(.root))
- case let .toast(text):
- let message: Signal = .single(text)
- let noMessage: Signal = .single(nil)
- let delayedNoMessage: Signal = noMessage |> delay(1.0, queue: Queue.mainQueue())
- strongSelf.botCallbackAlertMessage.set(message |> then(delayedNoMessage))
- case let .url(url):
- if isGame {
- strongSelf.chatDisplayNode.dismissInput()
- strongSelf.effectiveNavigationController?.pushViewController(GameController(context: strongSelf.context, url: url, message: message))
- } else {
- strongSelf.openUrl(url, concealed: false)
- }
- }
- }
- }))
+ })
+ |> deliverOnMainQueue).start(next: { result in
+ proceedWithResult(result)
+ }))
+ }
}
}
}, requestMessageActionUrlAuth: { [weak self] defaultUrl, messageId, buttonId in
diff --git a/submodules/TelegramUI/Sources/ChatControllerInteraction.swift b/submodules/TelegramUI/Sources/ChatControllerInteraction.swift
index 1885abd5ba..1aaaad688d 100644
--- a/submodules/TelegramUI/Sources/ChatControllerInteraction.swift
+++ b/submodules/TelegramUI/Sources/ChatControllerInteraction.swift
@@ -71,7 +71,7 @@ public final class ChatControllerInteraction {
let sendSticker: (FileMediaReference, Bool, ASDisplayNode, CGRect) -> Bool
let sendGif: (FileMediaReference, ASDisplayNode, CGRect) -> Bool
let sendBotContextResultAsGif: (ChatContextResultCollection, ChatContextResult, ASDisplayNode, CGRect) -> Bool
- let requestMessageActionCallback: (MessageId, MemoryBuffer?, Bool) -> Void
+ let requestMessageActionCallback: (MessageId, MemoryBuffer?, Bool, Bool) -> Void
let requestMessageActionUrlAuth: (String, MessageId, Int32) -> Void
let activateSwitchInline: (PeerId?, String) -> Void
let openUrl: (String, Bool, Bool?, Message?) -> Void
@@ -138,7 +138,7 @@ public final class ChatControllerInteraction {
var searchTextHighightState: (String, [MessageIndex])?
var seenOneTimeAnimatedMedia = Set()
- init(openMessage: @escaping (Message, ChatControllerInteractionOpenMessageMode) -> Bool, openPeer: @escaping (PeerId?, ChatControllerInteractionNavigateToPeer, Message?) -> Void, openPeerMention: @escaping (String) -> Void, openMessageContextMenu: @escaping (Message, Bool, ASDisplayNode, CGRect, UIGestureRecognizer?) -> Void, openMessageContextActions: @escaping (Message, ASDisplayNode, CGRect, ContextGesture?) -> Void, navigateToMessage: @escaping (MessageId, MessageId) -> Void, tapMessage: ((Message) -> Void)?, clickThroughMessage: @escaping () -> Void, toggleMessagesSelection: @escaping ([MessageId], Bool) -> Void, sendCurrentMessage: @escaping (Bool) -> Void, sendMessage: @escaping (String) -> Void, sendSticker: @escaping (FileMediaReference, Bool, ASDisplayNode, CGRect) -> Bool, sendGif: @escaping (FileMediaReference, ASDisplayNode, CGRect) -> Bool, sendBotContextResultAsGif: @escaping (ChatContextResultCollection, ChatContextResult, ASDisplayNode, CGRect) -> Bool, requestMessageActionCallback: @escaping (MessageId, MemoryBuffer?, Bool) -> Void, requestMessageActionUrlAuth: @escaping (String, MessageId, Int32) -> Void, activateSwitchInline: @escaping (PeerId?, String) -> Void, openUrl: @escaping (String, Bool, Bool?, Message?) -> Void, shareCurrentLocation: @escaping () -> Void, shareAccountContact: @escaping () -> Void, sendBotCommand: @escaping (MessageId?, String) -> Void, openInstantPage: @escaping (Message, ChatMessageItemAssociatedData?) -> Void, openWallpaper: @escaping (Message) -> Void, openTheme: @escaping (Message) -> Void, openHashtag: @escaping (String?, String) -> Void, updateInputState: @escaping ((ChatTextInputState) -> ChatTextInputState) -> Void, updateInputMode: @escaping ((ChatInputMode) -> ChatInputMode) -> Void, openMessageShareMenu: @escaping (MessageId) -> Void, presentController: @escaping (ViewController, Any?) -> Void, navigationController: @escaping () -> NavigationController?, chatControllerNode: @escaping () -> ASDisplayNode?, reactionContainerNode: @escaping () -> ReactionSelectionParentNode?, presentGlobalOverlayController: @escaping (ViewController, Any?) -> Void, callPeer: @escaping (PeerId, Bool) -> Void, longTap: @escaping (ChatControllerInteractionLongTapAction, Message?) -> Void, openCheckoutOrReceipt: @escaping (MessageId) -> Void, openSearch: @escaping () -> Void, setupReply: @escaping (MessageId) -> Void, canSetupReply: @escaping (Message) -> ChatControllerInteractionSwipeAction, navigateToFirstDateMessage: @escaping(Int32) ->Void, requestRedeliveryOfFailedMessages: @escaping (MessageId) -> Void, addContact: @escaping (String) -> Void, rateCall: @escaping (Message, CallId) -> Void, requestSelectMessagePollOptions: @escaping (MessageId, [Data]) -> Void, requestOpenMessagePollResults: @escaping (MessageId, MediaId) -> Void, openAppStorePage: @escaping () -> Void, displayMessageTooltip: @escaping (MessageId, String, ASDisplayNode?, CGRect?) -> Void, seekToTimecode: @escaping (Message, Double, Bool) -> Void, scheduleCurrentMessage: @escaping () -> Void, sendScheduledMessagesNow: @escaping ([MessageId]) -> Void, editScheduledMessagesTime: @escaping ([MessageId]) -> Void, performTextSelectionAction: @escaping (UInt32, NSAttributedString, TextSelectionAction) -> Void, updateMessageLike: @escaping (MessageId, Bool) -> Void, openMessageReactions: @escaping (MessageId) -> Void, displaySwipeToReplyHint: @escaping () -> Void, dismissReplyMarkupMessage: @escaping (Message) -> Void, openMessagePollResults: @escaping (MessageId, Data) -> Void, openPollCreation: @escaping (Bool?) -> Void, displayPollSolution: @escaping (TelegramMediaPollResults.Solution, ASDisplayNode) -> Void, displayPsa: @escaping (String, ASDisplayNode) -> Void, displayDiceTooltip: @escaping (TelegramMediaDice) -> Void, animateDiceSuccess: @escaping () -> Void, greetingStickerNode: @escaping () -> (ASDisplayNode, ASDisplayNode, ASDisplayNode, () -> Void)?, openPeerContextMenu: @escaping (Peer, ASDisplayNode, CGRect, ContextGesture?) -> Void, requestMessageUpdate: @escaping (MessageId) -> Void, cancelInteractiveKeyboardGestures: @escaping () -> Void, automaticMediaDownloadSettings: MediaAutoDownloadSettings, pollActionState: ChatInterfacePollActionState, stickerSettings: ChatInterfaceStickerSettings) {
+ init(openMessage: @escaping (Message, ChatControllerInteractionOpenMessageMode) -> Bool, openPeer: @escaping (PeerId?, ChatControllerInteractionNavigateToPeer, Message?) -> Void, openPeerMention: @escaping (String) -> Void, openMessageContextMenu: @escaping (Message, Bool, ASDisplayNode, CGRect, UIGestureRecognizer?) -> Void, openMessageContextActions: @escaping (Message, ASDisplayNode, CGRect, ContextGesture?) -> Void, navigateToMessage: @escaping (MessageId, MessageId) -> Void, tapMessage: ((Message) -> Void)?, clickThroughMessage: @escaping () -> Void, toggleMessagesSelection: @escaping ([MessageId], Bool) -> Void, sendCurrentMessage: @escaping (Bool) -> Void, sendMessage: @escaping (String) -> Void, sendSticker: @escaping (FileMediaReference, Bool, ASDisplayNode, CGRect) -> Bool, sendGif: @escaping (FileMediaReference, ASDisplayNode, CGRect) -> Bool, sendBotContextResultAsGif: @escaping (ChatContextResultCollection, ChatContextResult, ASDisplayNode, CGRect) -> Bool, requestMessageActionCallback: @escaping (MessageId, MemoryBuffer?, Bool, Bool) -> Void, requestMessageActionUrlAuth: @escaping (String, MessageId, Int32) -> Void, activateSwitchInline: @escaping (PeerId?, String) -> Void, openUrl: @escaping (String, Bool, Bool?, Message?) -> Void, shareCurrentLocation: @escaping () -> Void, shareAccountContact: @escaping () -> Void, sendBotCommand: @escaping (MessageId?, String) -> Void, openInstantPage: @escaping (Message, ChatMessageItemAssociatedData?) -> Void, openWallpaper: @escaping (Message) -> Void, openTheme: @escaping (Message) -> Void, openHashtag: @escaping (String?, String) -> Void, updateInputState: @escaping ((ChatTextInputState) -> ChatTextInputState) -> Void, updateInputMode: @escaping ((ChatInputMode) -> ChatInputMode) -> Void, openMessageShareMenu: @escaping (MessageId) -> Void, presentController: @escaping (ViewController, Any?) -> Void, navigationController: @escaping () -> NavigationController?, chatControllerNode: @escaping () -> ASDisplayNode?, reactionContainerNode: @escaping () -> ReactionSelectionParentNode?, presentGlobalOverlayController: @escaping (ViewController, Any?) -> Void, callPeer: @escaping (PeerId, Bool) -> Void, longTap: @escaping (ChatControllerInteractionLongTapAction, Message?) -> Void, openCheckoutOrReceipt: @escaping (MessageId) -> Void, openSearch: @escaping () -> Void, setupReply: @escaping (MessageId) -> Void, canSetupReply: @escaping (Message) -> ChatControllerInteractionSwipeAction, navigateToFirstDateMessage: @escaping(Int32) ->Void, requestRedeliveryOfFailedMessages: @escaping (MessageId) -> Void, addContact: @escaping (String) -> Void, rateCall: @escaping (Message, CallId) -> Void, requestSelectMessagePollOptions: @escaping (MessageId, [Data]) -> Void, requestOpenMessagePollResults: @escaping (MessageId, MediaId) -> Void, openAppStorePage: @escaping () -> Void, displayMessageTooltip: @escaping (MessageId, String, ASDisplayNode?, CGRect?) -> Void, seekToTimecode: @escaping (Message, Double, Bool) -> Void, scheduleCurrentMessage: @escaping () -> Void, sendScheduledMessagesNow: @escaping ([MessageId]) -> Void, editScheduledMessagesTime: @escaping ([MessageId]) -> Void, performTextSelectionAction: @escaping (UInt32, NSAttributedString, TextSelectionAction) -> Void, updateMessageLike: @escaping (MessageId, Bool) -> Void, openMessageReactions: @escaping (MessageId) -> Void, displaySwipeToReplyHint: @escaping () -> Void, dismissReplyMarkupMessage: @escaping (Message) -> Void, openMessagePollResults: @escaping (MessageId, Data) -> Void, openPollCreation: @escaping (Bool?) -> Void, displayPollSolution: @escaping (TelegramMediaPollResults.Solution, ASDisplayNode) -> Void, displayPsa: @escaping (String, ASDisplayNode) -> Void, displayDiceTooltip: @escaping (TelegramMediaDice) -> Void, animateDiceSuccess: @escaping () -> Void, greetingStickerNode: @escaping () -> (ASDisplayNode, ASDisplayNode, ASDisplayNode, () -> Void)?, openPeerContextMenu: @escaping (Peer, ASDisplayNode, CGRect, ContextGesture?) -> Void, requestMessageUpdate: @escaping (MessageId) -> Void, cancelInteractiveKeyboardGestures: @escaping () -> Void, automaticMediaDownloadSettings: MediaAutoDownloadSettings, pollActionState: ChatInterfacePollActionState, stickerSettings: ChatInterfaceStickerSettings) {
self.openMessage = openMessage
self.openPeer = openPeer
self.openPeerMention = openPeerMention
@@ -215,7 +215,7 @@ public final class ChatControllerInteraction {
static var `default`: ChatControllerInteraction {
return ChatControllerInteraction(openMessage: { _, _ in
- return false }, openPeer: { _, _, _ in }, openPeerMention: { _ in }, openMessageContextMenu: { _, _, _, _, _ in }, openMessageContextActions: { _, _, _, _ in }, navigateToMessage: { _, _ in }, tapMessage: nil, clickThroughMessage: { }, toggleMessagesSelection: { _, _ in }, sendCurrentMessage: { _ in }, sendMessage: { _ in }, sendSticker: { _, _, _, _ in return false }, sendGif: { _, _, _ in return false }, sendBotContextResultAsGif: { _, _, _, _ in return false }, requestMessageActionCallback: { _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { _, _, _, _ in }, shareCurrentLocation: {}, shareAccountContact: {}, sendBotCommand: { _, _ in }, openInstantPage: { _, _ in }, openWallpaper: { _ in }, openTheme: { _ in }, openHashtag: { _, _ in }, updateInputState: { _ in }, updateInputMode: { _ in }, openMessageShareMenu: { _ in
+ return false }, openPeer: { _, _, _ in }, openPeerMention: { _ in }, openMessageContextMenu: { _, _, _, _, _ in }, openMessageContextActions: { _, _, _, _ in }, navigateToMessage: { _, _ in }, tapMessage: nil, clickThroughMessage: { }, toggleMessagesSelection: { _, _ in }, sendCurrentMessage: { _ in }, sendMessage: { _ in }, sendSticker: { _, _, _, _ in return false }, sendGif: { _, _, _ in return false }, sendBotContextResultAsGif: { _, _, _, _ in return false }, requestMessageActionCallback: { _, _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { _, _, _, _ in }, shareCurrentLocation: {}, shareAccountContact: {}, sendBotCommand: { _, _ in }, openInstantPage: { _, _ in }, openWallpaper: { _ in }, openTheme: { _ in }, openHashtag: { _, _ in }, updateInputState: { _ in }, updateInputMode: { _ in }, openMessageShareMenu: { _ in
}, presentController: { _, _ in }, navigationController: {
return nil
}, chatControllerNode: {
diff --git a/submodules/TelegramUI/Sources/ChatMessageAnimatedStickerItemNode.swift b/submodules/TelegramUI/Sources/ChatMessageAnimatedStickerItemNode.swift
index d248495c13..04e3869f03 100644
--- a/submodules/TelegramUI/Sources/ChatMessageAnimatedStickerItemNode.swift
+++ b/submodules/TelegramUI/Sources/ChatMessageAnimatedStickerItemNode.swift
@@ -68,7 +68,7 @@ class ChatMessageAnimatedStickerItemNode: ChatMessageItemView {
private var highlightedState: Bool = false
- private var heartbeatHaptic: HeartbeatHaptic?
+ private var haptic: EmojiHaptic?
private var currentSwipeToReplyTranslation: CGFloat = 0.0
@@ -217,7 +217,7 @@ class ChatMessageAnimatedStickerItemNode: ChatMessageItemView {
didSet {
if self.visibilityStatus != oldValue {
self.updateVisibility()
- self.heartbeatHaptic?.enabled = self.visibilityStatus
+ self.haptic?.enabled = self.visibilityStatus
}
}
}
@@ -228,10 +228,10 @@ class ChatMessageAnimatedStickerItemNode: ChatMessageItemView {
}
if let telegramDice = self.telegramDice {
- if telegramDice.emoji == "🎲" {
- let animationNode = SlotMachineAnimationNode(context: item.context)
- self.animationNode = animationNode
- } else {
+// if telegramDice.emoji == "🎲" {
+// let animationNode = SlotMachineAnimationNode(context: item.context)
+// self.animationNode = animationNode
+// } else {
let animationNode = ManagedDiceAnimationNode(context: item.context, emoji: telegramDice.emoji.strippedEmoji)
if !item.message.effectivelyIncoming(item.context.account.peerId) {
animationNode.success = { [weak self] in
@@ -241,7 +241,7 @@ class ChatMessageAnimatedStickerItemNode: ChatMessageItemView {
}
}
self.animationNode = animationNode
- }
+// }
} else {
let animationNode: AnimatedStickerNode
if let (node, parentNode, listNode, greetingCompletion) = item.controllerInteraction.greetingStickerNode(), let greetingStickerNode = node as? AnimatedStickerNode {
@@ -1110,24 +1110,29 @@ class ChatMessageAnimatedStickerItemNode: ChatMessageItemView {
}
let beatingHearts: [UInt32] = [0x2764, 0x1F90E, 0x1F9E1, 0x1F49A, 0x1F49C, 0x1F49B, 0x1F5A4, 0x1F90D]
-
- if let text = self.item?.message.text, let firstScalar = text.unicodeScalars.first, beatingHearts.contains(firstScalar.value) {
+ let peach = 0x1F351
+
+ if let text = self.item?.message.text, let firstScalar = text.unicodeScalars.first, beatingHearts.contains(firstScalar.value) || firstScalar.value == peach {
return .optionalAction({
let _ = startTime.start(next: { [weak self] time in
guard let strongSelf = self else {
return
}
- let heartbeatHaptic: HeartbeatHaptic
- if let current = strongSelf.heartbeatHaptic {
- heartbeatHaptic = current
+ var haptic: EmojiHaptic
+ if let current = strongSelf.haptic {
+ haptic = current
} else {
- heartbeatHaptic = HeartbeatHaptic()
- heartbeatHaptic.enabled = true
- strongSelf.heartbeatHaptic = heartbeatHaptic
+ if beatingHearts.contains(firstScalar.value) {
+ haptic = HeartbeatHaptic()
+ } else {
+ haptic = PeachHaptic()
+ }
+ haptic.enabled = true
+ strongSelf.haptic = haptic
}
- if !heartbeatHaptic.active {
- heartbeatHaptic.start(time: time)
+ if !haptic.active {
+ haptic.start(time: time)
}
})
})
diff --git a/submodules/TelegramUI/Sources/ChatMessageBubbleItemNode.swift b/submodules/TelegramUI/Sources/ChatMessageBubbleItemNode.swift
index 6b153f1771..df66db593a 100644
--- a/submodules/TelegramUI/Sources/ChatMessageBubbleItemNode.swift
+++ b/submodules/TelegramUI/Sources/ChatMessageBubbleItemNode.swift
@@ -907,6 +907,10 @@ class ChatMessageBubbleItemNode: ChatMessageItemView, ChatMessagePrevewItemNode
}
}
+ if item.presentationData.isPreview {
+ needShareButton = false
+ }
+
var tmpWidth: CGFloat
if allowFullWidth {
tmpWidth = baseWidth
@@ -1843,6 +1847,7 @@ class ChatMessageBubbleItemNode: ChatMessageItemView, ChatMessagePrevewItemNode
strongSelf.contextSourceNode.contentNode.addSubnode(nameNode)
}
nameNode.frame = CGRect(origin: CGPoint(x: contentOrigin.x + layoutConstants.text.bubbleInsets.left, y: layoutConstants.bubble.contentInsets.top + nameNodeOriginY), size: nameNodeSizeApply.0)
+ nameNode.displaysAsynchronously = !item.presentationData.isPreview
if let credibilityIconImage = currentCredibilityIconImage {
let credibilityIconNode: ASImageNode
diff --git a/submodules/TelegramUI/Sources/ChatMessageDateAndStatusNode.swift b/submodules/TelegramUI/Sources/ChatMessageDateAndStatusNode.swift
index 3ed9230c12..2de1494996 100644
--- a/submodules/TelegramUI/Sources/ChatMessageDateAndStatusNode.swift
+++ b/submodules/TelegramUI/Sources/ChatMessageDateAndStatusNode.swift
@@ -508,6 +508,7 @@ class ChatMessageDateAndStatusNode: ASDisplayNode {
impressionIcon.removeFromSupernode()
strongSelf.impressionIcon = nil
}
+ strongSelf.impressionIcon?.displaysAsynchronously = !presentationData.isPreview
strongSelf.dateNode.frame = CGRect(origin: CGPoint(x: leftInset + backgroundInsets.left + impressionWidth, y: backgroundInsets.top + 1.0 + offset), size: date.size)
diff --git a/submodules/TelegramUI/Sources/ChatMessageGameBubbleContentNode.swift b/submodules/TelegramUI/Sources/ChatMessageGameBubbleContentNode.swift
index de894e9555..43c68319f1 100644
--- a/submodules/TelegramUI/Sources/ChatMessageGameBubbleContentNode.swift
+++ b/submodules/TelegramUI/Sources/ChatMessageGameBubbleContentNode.swift
@@ -26,7 +26,7 @@ final class ChatMessageGameBubbleContentNode: ChatMessageBubbleContentNode {
self.addSubnode(self.contentNode)
self.contentNode.openMedia = { [weak self] _ in
if let strongSelf = self, let item = strongSelf.item {
- item.controllerInteraction.requestMessageActionCallback(item.message.id, nil, true)
+ item.controllerInteraction.requestMessageActionCallback(item.message.id, nil, true, false)
}
}
}
diff --git a/submodules/TelegramUI/Sources/ChatMessageItemView.swift b/submodules/TelegramUI/Sources/ChatMessageItemView.swift
index e4bab4067d..f114d2af30 100644
--- a/submodules/TelegramUI/Sources/ChatMessageItemView.swift
+++ b/submodules/TelegramUI/Sources/ChatMessageItemView.swift
@@ -782,9 +782,9 @@ public class ChatMessageItemView: ListViewItemNode {
case .requestPhone:
item.controllerInteraction.shareAccountContact()
case .openWebApp:
- item.controllerInteraction.requestMessageActionCallback(item.message.id, nil, true)
- case let .callback(data):
- item.controllerInteraction.requestMessageActionCallback(item.message.id, data, false)
+ item.controllerInteraction.requestMessageActionCallback(item.message.id, nil, true, false)
+ case let .callback(requiresPassword, data):
+ item.controllerInteraction.requestMessageActionCallback(item.message.id, data, false, requiresPassword)
case let .switchInline(samePeer, query):
var botPeer: Peer?
diff --git a/submodules/TelegramUI/Sources/ChatRecentActionsControllerNode.swift b/submodules/TelegramUI/Sources/ChatRecentActionsControllerNode.swift
index 2211b4da21..242cc801c2 100644
--- a/submodules/TelegramUI/Sources/ChatRecentActionsControllerNode.swift
+++ b/submodules/TelegramUI/Sources/ChatRecentActionsControllerNode.swift
@@ -216,7 +216,7 @@ final class ChatRecentActionsControllerNode: ViewControllerTracingNode {
}, openMessageContextMenu: { [weak self] message, selectAll, node, frame, _ in
self?.openMessageContextMenu(message: message, selectAll: selectAll, node: node, frame: frame)
}, openMessageContextActions: { _, _, _, _ in
- }, navigateToMessage: { _, _ in }, tapMessage: nil, clickThroughMessage: { }, toggleMessagesSelection: { _, _ in }, sendCurrentMessage: { _ in }, sendMessage: { _ in }, sendSticker: { _, _, _, _ in return false }, sendGif: { _, _, _ in return false }, sendBotContextResultAsGif: { _, _, _, _ in return false }, requestMessageActionCallback: { _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { [weak self] url, _, _, _ in
+ }, navigateToMessage: { _, _ in }, tapMessage: nil, clickThroughMessage: { }, toggleMessagesSelection: { _, _ in }, sendCurrentMessage: { _ in }, sendMessage: { _ in }, sendSticker: { _, _, _, _ in return false }, sendGif: { _, _, _ in return false }, sendBotContextResultAsGif: { _, _, _, _ in return false }, requestMessageActionCallback: { _, _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { [weak self] url, _, _, _ in
self?.openUrl(url)
}, shareCurrentLocation: {}, shareAccountContact: {}, sendBotCommand: { _, _ in }, openInstantPage: { [weak self] message, associatedData in
if let strongSelf = self, let navigationController = strongSelf.getNavigationController() {
diff --git a/submodules/TelegramUI/Sources/DrawingStickersScreen.swift b/submodules/TelegramUI/Sources/DrawingStickersScreen.swift
index 2763398844..e3c585e781 100644
--- a/submodules/TelegramUI/Sources/DrawingStickersScreen.swift
+++ b/submodules/TelegramUI/Sources/DrawingStickersScreen.swift
@@ -108,7 +108,7 @@ private final class DrawingStickersScreenNode: ViewControllerTracingNode {
var selectStickerImpl: ((FileMediaReference, ASDisplayNode, CGRect) -> Bool)?
self.controllerInteraction = ChatControllerInteraction(openMessage: { _, _ in
- return false }, openPeer: { _, _, _ in }, openPeerMention: { _ in }, openMessageContextMenu: { _, _, _, _, _ in }, openMessageContextActions: { _, _, _, _ in }, navigateToMessage: { _, _ in }, tapMessage: nil, clickThroughMessage: { }, toggleMessagesSelection: { _, _ in }, sendCurrentMessage: { _ in }, sendMessage: { _ in }, sendSticker: { fileReference, _, node, rect in return selectStickerImpl?(fileReference, node, rect) ?? false }, sendGif: { _, _, _ in return false }, sendBotContextResultAsGif: { _, _, _, _ in return false }, requestMessageActionCallback: { _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { _, _, _, _ in }, shareCurrentLocation: {}, shareAccountContact: {}, sendBotCommand: { _, _ in }, openInstantPage: { _, _ in }, openWallpaper: { _ in }, openTheme: { _ in }, openHashtag: { _, _ in }, updateInputState: { _ in }, updateInputMode: { _ in }, openMessageShareMenu: { _ in
+ return false }, openPeer: { _, _, _ in }, openPeerMention: { _ in }, openMessageContextMenu: { _, _, _, _, _ in }, openMessageContextActions: { _, _, _, _ in }, navigateToMessage: { _, _ in }, tapMessage: nil, clickThroughMessage: { }, toggleMessagesSelection: { _, _ in }, sendCurrentMessage: { _ in }, sendMessage: { _ in }, sendSticker: { fileReference, _, node, rect in return selectStickerImpl?(fileReference, node, rect) ?? false }, sendGif: { _, _, _ in return false }, sendBotContextResultAsGif: { _, _, _, _ in return false }, requestMessageActionCallback: { _, _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { _, _, _, _ in }, shareCurrentLocation: {}, shareAccountContact: {}, sendBotCommand: { _, _ in }, openInstantPage: { _, _ in }, openWallpaper: { _ in }, openTheme: { _ in }, openHashtag: { _, _ in }, updateInputState: { _ in }, updateInputMode: { _ in }, openMessageShareMenu: { _ in
}, presentController: { _, _ in }, navigationController: {
return nil
}, chatControllerNode: {
diff --git a/submodules/TelegramUI/Sources/HeartbeatHaptic.swift b/submodules/TelegramUI/Sources/HeartbeatHaptic.swift
index 5c636cbea0..e70cc92788 100644
--- a/submodules/TelegramUI/Sources/HeartbeatHaptic.swift
+++ b/submodules/TelegramUI/Sources/HeartbeatHaptic.swift
@@ -2,11 +2,18 @@ import Foundation
import Display
import SwiftSignalKit
-final class HeartbeatHaptic {
+protocol EmojiHaptic {
+ var enabled: Bool { get set }
+ var active: Bool { get }
+
+ func start(time: Double)
+}
+
+final class HeartbeatHaptic: EmojiHaptic {
private var hapticFeedback = HapticFeedback()
private var timer: SwiftSignalKit.Timer?
private var time: Double = 0.0
- var enabled = false {
+ var enabled: Bool = false {
didSet {
if !self.enabled {
self.reset()
diff --git a/submodules/TelegramUI/Sources/OverlayPlayerControllerNode.swift b/submodules/TelegramUI/Sources/OverlayPlayerControllerNode.swift
index b635f7ac1b..b81ff47c8c 100644
--- a/submodules/TelegramUI/Sources/OverlayPlayerControllerNode.swift
+++ b/submodules/TelegramUI/Sources/OverlayPlayerControllerNode.swift
@@ -76,7 +76,7 @@ final class OverlayAudioPlayerControllerNode: ViewControllerTracingNode, UIGestu
return false
}, sendBotContextResultAsGif: { _, _, _, _ in
return false
- }, requestMessageActionCallback: { _, _, _ in
+ }, requestMessageActionCallback: { _, _, _, _ in
}, requestMessageActionUrlAuth: { _, _, _ in
}, activateSwitchInline: { _, _ in
}, openUrl: { _, _, _, _ in
diff --git a/submodules/TelegramUI/Sources/OwnershipTransferController.swift b/submodules/TelegramUI/Sources/OwnershipTransferController.swift
new file mode 100644
index 0000000000..b2028a051a
--- /dev/null
+++ b/submodules/TelegramUI/Sources/OwnershipTransferController.swift
@@ -0,0 +1,128 @@
+import Foundation
+import UIKit
+import AsyncDisplayKit
+import Display
+import SwiftSignalKit
+import Postbox
+import TelegramCore
+import SyncCore
+import TelegramPresentationData
+import ActivityIndicator
+import TextFormat
+import AccountContext
+import AlertUI
+import PresentationDataUtils
+import PasswordSetupUI
+import Markdown
+import PeerInfoUI
+
+private func commitOwnershipTransferController(context: AccountContext, present: @escaping (ViewController, Any?) -> Void, commit: @escaping (String) -> Signal, completion: @escaping (MessageActionCallbackResult) -> Void) -> ViewController {
+ let presentationData = context.sharedContext.currentPresentationData.with { $0 }
+
+ var dismissImpl: (() -> Void)?
+ var proceedImpl: (() -> Void)?
+
+ var pushControllerImpl: ((ViewController) -> Void)?
+
+ let disposable = MetaDisposable()
+
+ let contentNode = ChannelOwnershipTransferAlertContentNode(theme: AlertControllerTheme(presentationData: presentationData), ptheme: presentationData.theme, strings: presentationData.strings, actions: [TextAlertAction(type: .genericAction, title: presentationData.strings.Common_Cancel, action: {
+ dismissImpl?()
+ }), TextAlertAction(type: .defaultAction, title: presentationData.strings.OwnershipTransfer_Transfer, action: {
+ proceedImpl?()
+ })])
+
+ contentNode.complete = {
+ proceedImpl?()
+ }
+
+ let controller = AlertController(theme: AlertControllerTheme(presentationData: presentationData), contentNode: contentNode)
+ let presentationDataDisposable = context.sharedContext.presentationData.start(next: { [weak controller, weak contentNode] presentationData in
+ controller?.theme = AlertControllerTheme(presentationData: presentationData)
+ contentNode?.theme = presentationData.theme
+ })
+ controller.dismissed = {
+ presentationDataDisposable.dispose()
+ disposable.dispose()
+ }
+ dismissImpl = { [weak controller, weak contentNode] in
+ contentNode?.dismissInput()
+ controller?.dismissAnimated()
+ }
+ proceedImpl = { [weak contentNode] in
+ guard let contentNode = contentNode else {
+ return
+ }
+ contentNode.updateIsChecking(true)
+
+ disposable.set((commit(contentNode.password) |> deliverOnMainQueue).start(next: { result in
+ dismissImpl?()
+ }, error: { [weak contentNode] error in
+ var errorTextAndActions: (String, [TextAlertAction])?
+ switch error {
+ case .invalidPassword:
+ contentNode?.animateError()
+ case .limitExceeded:
+ errorTextAndActions = (presentationData.strings.TwoStepAuth_FloodError, [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})])
+ case .userBlocked, .restricted:
+ errorTextAndActions = (presentationData.strings.Group_OwnershipTransfer_ErrorPrivacyRestricted, [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})])
+ default:
+ errorTextAndActions = (presentationData.strings.Login_UnknownError, [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})])
+ }
+ contentNode?.updateIsChecking(false)
+
+ if let (text, actions) = errorTextAndActions {
+ dismissImpl?()
+ present(textAlertController(context: context, title: nil, text: text, actions: actions), nil)
+ }
+ }))
+ }
+
+ pushControllerImpl = { [weak controller] c in
+ controller?.push(c)
+ }
+
+ return controller
+}
+
+
+func ownershipTransferController(context: AccountContext, initialError: MessageActionCallbackError, present: @escaping (ViewController, Any?) -> Void, commit: @escaping (String) -> Signal, completion: @escaping (MessageActionCallbackResult) -> Void) -> ViewController {
+ let presentationData = context.sharedContext.currentPresentationData.with { $0 }
+ let theme = AlertControllerTheme(presentationData: presentationData)
+
+ var title: NSAttributedString? = NSAttributedString(string: presentationData.strings.OwnershipTransfer_SecurityCheck, font: Font.medium(presentationData.listsFontSize.itemListBaseFontSize), textColor: theme.primaryColor, paragraphAlignment: .center)
+
+ var text = presentationData.strings.OwnershipTransfer_SecurityRequirements
+ var actions: [TextAlertAction] = []
+
+ switch initialError {
+ case .requestPassword:
+ return commitOwnershipTransferController(context: context, present: present, commit: commit, completion: completion)
+ case .twoStepAuthTooFresh, .authSessionTooFresh:
+ text = text + presentationData.strings.OwnershipTransfer_ComeBackLater
+ actions = [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]
+ case .twoStepAuthMissing:
+ actions = [TextAlertAction(type: .genericAction, title: presentationData.strings.OwnershipTransfer_SetupTwoStepAuth, action: {
+ let controller = SetupTwoStepVerificationController(context: context, initialState: .automatic, stateUpdated: { update, shouldDismiss, controller in
+ if shouldDismiss {
+ controller.dismiss()
+ }
+ })
+ present(controller, ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
+ }), TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_Cancel, action: {})]
+ case .userBlocked, .restricted:
+ title = nil
+ text = presentationData.strings.Group_OwnershipTransfer_ErrorPrivacyRestricted
+ actions = [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]
+ default:
+ title = nil
+ text = presentationData.strings.Login_UnknownError
+ actions = [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]
+ }
+
+ let body = MarkdownAttributeSet(font: Font.regular(13.0), textColor: theme.primaryColor)
+ let bold = MarkdownAttributeSet(font: Font.semibold(13.0), textColor: theme.primaryColor)
+ let attributedText = parseMarkdownIntoAttributedString(text, attributes: MarkdownAttributes(body: body, bold: bold, link: body, linkAttribute: { _ in return nil }), textAlignment: .center)
+
+ return richTextAlertController(context: context, title: title, text: attributedText, actions: actions)
+}
diff --git a/submodules/TelegramUI/Sources/PeachHaptic.swift b/submodules/TelegramUI/Sources/PeachHaptic.swift
new file mode 100644
index 0000000000..e92ffeb0af
--- /dev/null
+++ b/submodules/TelegramUI/Sources/PeachHaptic.swift
@@ -0,0 +1,73 @@
+import Foundation
+import Display
+import SwiftSignalKit
+
+private let impactTime: Double = 0.4
+
+final class PeachHaptic: EmojiHaptic {
+ private var hapticFeedback = HapticFeedback()
+ private var timer: SwiftSignalKit.Timer?
+ private var time: Double = 0.0
+ var enabled: Bool = false {
+ didSet {
+ if !self.enabled {
+ self.reset()
+ }
+ }
+ }
+
+ var active: Bool {
+ return self.timer != nil
+ }
+
+ private func reset() {
+ if let timer = self.timer {
+ self.time = 0.0
+ timer.invalidate()
+ self.timer = nil
+ }
+ }
+
+ private func beat(time: Double) {
+ let epsilon = 0.1
+ if fabs(impactTime - time) < epsilon {
+ self.hapticFeedback.impact(.heavy)
+ }
+ }
+
+ func start(time: Double) {
+ self.hapticFeedback.prepareImpact()
+
+ if time > impactTime {
+ return
+ }
+
+ let startTime: Double = 0.0
+
+ let block = { [weak self] in
+ guard let strongSelf = self, strongSelf.enabled else {
+ return
+ }
+
+ strongSelf.time = startTime
+ strongSelf.beat(time: startTime)
+ strongSelf.timer = SwiftSignalKit.Timer(timeout: 0.2, repeat: true, completion: { [weak self] in
+ guard let strongSelf = self, strongSelf.enabled else {
+ return
+ }
+ strongSelf.time += 0.2
+ strongSelf.beat(time: strongSelf.time)
+
+ if strongSelf.time > impactTime {
+ strongSelf.reset()
+ strongSelf.time = 0.0
+ strongSelf.timer?.invalidate()
+ strongSelf.timer = nil
+ }
+ }, queue: Queue.mainQueue())
+ strongSelf.timer?.start()
+ }
+
+ block()
+ }
+}
diff --git a/submodules/TelegramUI/Sources/PeerInfo/PeerInfoScreen.swift b/submodules/TelegramUI/Sources/PeerInfo/PeerInfoScreen.swift
index 34a2d2a76e..6cba1f2a1f 100644
--- a/submodules/TelegramUI/Sources/PeerInfo/PeerInfoScreen.swift
+++ b/submodules/TelegramUI/Sources/PeerInfo/PeerInfoScreen.swift
@@ -1825,7 +1825,7 @@ private final class PeerInfoScreenNode: ViewControllerTracingNode, UIScrollViewD
return false
}, sendBotContextResultAsGif: { _, _, _, _ in
return false
- }, requestMessageActionCallback: { _, _, _ in
+ }, requestMessageActionCallback: { _, _, _, _ in
}, requestMessageActionUrlAuth: { _, _, _ in
}, activateSwitchInline: { _, _ in
}, openUrl: { [weak self] url, concealed, external, _ in
diff --git a/submodules/TelegramUI/Sources/PeerMediaCollectionController.swift b/submodules/TelegramUI/Sources/PeerMediaCollectionController.swift
index 7f9fdcb0dd..08f6108245 100644
--- a/submodules/TelegramUI/Sources/PeerMediaCollectionController.swift
+++ b/submodules/TelegramUI/Sources/PeerMediaCollectionController.swift
@@ -327,7 +327,7 @@ public class PeerMediaCollectionController: TelegramBaseController {
return false
}, sendBotContextResultAsGif: { _, _, _, _ in
return false
- }, requestMessageActionCallback: { _, _, _ in
+ }, requestMessageActionCallback: { _, _, _, _ in
}, requestMessageActionUrlAuth: { _, _, _ in
}, activateSwitchInline: { _, _ in
}, openUrl: { [weak self] url, _, external, _ in
diff --git a/submodules/TelegramUI/Sources/SharedAccountContext.swift b/submodules/TelegramUI/Sources/SharedAccountContext.swift
index a4c3640344..e16044228f 100644
--- a/submodules/TelegramUI/Sources/SharedAccountContext.swift
+++ b/submodules/TelegramUI/Sources/SharedAccountContext.swift
@@ -1158,7 +1158,7 @@ public final class SharedAccountContextImpl: SharedAccountContext {
clickThroughMessage?()
}, toggleMessagesSelection: { _, _ in }, sendCurrentMessage: { _ in }, sendMessage: { _ in }, sendSticker: { _, _, _, _ in return false }, sendGif: { _, _, _ in return false }, sendBotContextResultAsGif: { _, _, _, _ in
return false
- }, requestMessageActionCallback: { _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { _, _, _, _ in }, shareCurrentLocation: {}, shareAccountContact: {}, sendBotCommand: { _, _ in }, openInstantPage: { _, _ in }, openWallpaper: { _ in }, openTheme: { _ in }, openHashtag: { _, _ in }, updateInputState: { _ in }, updateInputMode: { _ in }, openMessageShareMenu: { _ in
+ }, requestMessageActionCallback: { _, _, _, _ in }, requestMessageActionUrlAuth: { _, _, _ in }, activateSwitchInline: { _, _ in }, openUrl: { _, _, _, _ in }, shareCurrentLocation: {}, shareAccountContact: {}, sendBotCommand: { _, _ in }, openInstantPage: { _, _ in }, openWallpaper: { _ in }, openTheme: { _ in }, openHashtag: { _, _ in }, updateInputState: { _ in }, updateInputMode: { _ in }, openMessageShareMenu: { _ in
}, presentController: { _, _ in }, navigationController: {
return nil
}, chatControllerNode: {
diff --git a/submodules/TelegramUI/Sources/TelegramRootController.swift b/submodules/TelegramUI/Sources/TelegramRootController.swift
index 99e3ae0cfd..ffc7cf94f2 100644
--- a/submodules/TelegramUI/Sources/TelegramRootController.swift
+++ b/submodules/TelegramUI/Sources/TelegramRootController.swift
@@ -127,6 +127,25 @@ public final class TelegramRootController: NavigationController {
self.accountSettingsController = accountSettingsController
self.rootTabController = tabBarController
self.pushViewController(tabBarController, animated: false)
+
+// Queue.mainQueue().after(2.0) {
+// let messageId = MessageId(peerId: PeerId(namespace: 2, id: 1488156064), namespace: 0, id: 528)
+// let _ = ((self.context.account.postbox.transaction { transaction in
+// return transaction.getMessage(messageId)
+// }) |> deliverOnMainQueue).start(next: { [weak self] message in
+// guard let strongSelf = self, let message = message else {
+// return
+// }
+//
+// let layout = ContainerViewLayout(size: CGSize(width: 414.0, height: 896.0), metrics: LayoutMetrics(widthClass: .compact, heightClass: .compact), deviceMetrics: .iPhoneX, intrinsicInsets: UIEdgeInsets(), safeInsets: UIEdgeInsets(), statusBarHeight: 0.0, inputHeight: nil, inputHeightIsInteractivellyChanging: false, inVoiceOver: false)
+// let renderer = MessageStoryRenderer(context: strongSelf.context, message: message)
+// let image = renderer.update(layout: layout)
+//
+// let node = renderer.containerNode
+// node.frame = CGRect(origin: CGPoint(), size: layout.size)
+// strongSelf.displayNode.addSubnode(node)
+// })
+// }
}
public func updateRootControllers(showCallsTab: Bool) {
@@ -174,3 +193,134 @@ public final class TelegramRootController: NavigationController {
presentedLegacyShortcutCamera(context: self.context, saveCapturedMedia: false, saveEditedPhotos: false, mediaGrouping: true, parentController: controller)
}
}
+
+class MessageStoryRenderer {
+ private let context: AccountContext
+ private let presentationData: PresentationData
+ private let message: Message
+
+ let containerNode: ASDisplayNode
+ private let instantChatBackgroundNode: WallpaperBackgroundNode
+ private let messagesContainerNode: ASDisplayNode
+ private var dateHeaderNode: ListViewItemHeaderNode?
+ private var messageNodes: [ListViewItemNode]?
+ private let addressNode: ImmediateTextNode
+
+ init(context: AccountContext, message: Message) {
+ self.context = context
+ self.presentationData = context.sharedContext.currentPresentationData.with { $0 }
+ self.message = message
+
+ self.containerNode = ASDisplayNode()
+
+ self.instantChatBackgroundNode = WallpaperBackgroundNode()
+ self.instantChatBackgroundNode.displaysAsynchronously = false
+ self.instantChatBackgroundNode.image = chatControllerBackgroundImage(theme: presentationData.theme, wallpaper: .builtin(WallpaperSettings()), mediaBox: context.sharedContext.accountManager.mediaBox, knockoutMode: context.sharedContext.immediateExperimentalUISettings.knockoutWallpaper)
+
+ self.messagesContainerNode = ASDisplayNode()
+ self.messagesContainerNode.clipsToBounds = true
+ self.messagesContainerNode.transform = CATransform3DMakeScale(1.0, -1.0, 1.0)
+
+ let peer = message.peers[message.id.peerId]!
+ self.addressNode = ImmediateTextNode()
+ self.addressNode.displaysAsynchronously = false
+ self.addressNode.attributedText = NSAttributedString(string: "t.me/\(peer.addressName ?? "")", font: Font.medium(14.0), textColor: UIColor(rgb: 0xa8b7c4))
+// self.addressNode.textShadowColor = .black
+
+ self.containerNode.addSubnode(self.instantChatBackgroundNode)
+ self.containerNode.addSubnode(self.messagesContainerNode)
+ self.containerNode.addSubnode(self.addressNode)
+ }
+
+// func update(layout: ContainerViewLayout, completion: (UIImage?) -> Void) {
+// self.updateMessagesLayout(layout: layout)
+//
+// Queue.mainQueue().after(0.01) {
+// UIGraphicsBeginImageContextWithOptions(layout.size, false, 3.0)
+// self.containerNode.view.drawHierarchy(in: CGRect(origin: CGPoint(), size: layout.size), afterScreenUpdates: true)
+// let img = UIGraphicsGetImageFromCurrentImageContext()
+// UIGraphicsEndImageContext()
+// completion(img)
+// }
+// }
+
+ private func updateMessagesLayout(layout: ContainerViewLayout) {
+ let size = layout.size
+ self.containerNode.frame = CGRect(origin: CGPoint(), size: layout.size)
+ self.instantChatBackgroundNode.frame = CGRect(origin: CGPoint(), size: layout.size)
+ self.instantChatBackgroundNode.updateLayout(size: size, transition: .immediate)
+ self.messagesContainerNode.frame = CGRect(origin: CGPoint(), size: layout.size)
+
+ let addressLayout = self.addressNode.updateLayout(size)
+
+ let theme = self.presentationData.theme.withUpdated(preview: true)
+ let headerItem = self.context.sharedContext.makeChatMessageDateHeaderItem(context: self.context, timestamp: self.message.timestamp, theme: theme, strings: self.presentationData.strings, wallpaper: self.presentationData.chatWallpaper, fontSize: self.presentationData.chatFontSize, chatBubbleCorners: self.presentationData.chatBubbleCorners, dateTimeFormat: self.presentationData.dateTimeFormat, nameOrder: self.presentationData.nameDisplayOrder)
+
+ var items: [ListViewItem] = []
+ let sampleMessages: [Message] = [self.message]
+
+ items = sampleMessages.reversed().map { message in
+ self.context.sharedContext.makeChatMessagePreviewItem(context: self.context, message: message, theme: theme, strings: self.presentationData.strings, wallpaper: self.presentationData.theme.chat.defaultWallpaper, fontSize: self.presentationData.chatFontSize, chatBubbleCorners: self.presentationData.chatBubbleCorners, dateTimeFormat: self.presentationData.dateTimeFormat, nameOrder: self.presentationData.nameDisplayOrder, forcedResourceStatus: nil, tapMessage: nil, clickThroughMessage: nil)
+ }
+
+ let inset: CGFloat = 16.0
+ let width = layout.size.width - inset * 2.0
+ let params = ListViewItemLayoutParams(width: width, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right, availableHeight: layout.size.height)
+ if let messageNodes = self.messageNodes {
+ for i in 0 ..< items.count {
+ let itemNode = messageNodes[i]
+ items[i].updateNode(async: { $0() }, node: {
+ return itemNode
+ }, params: params, previousItem: i == 0 ? nil : items[i - 1], nextItem: i == (items.count - 1) ? nil : items[i + 1], animation: .None, completion: { (layout, apply) in
+ let nodeFrame = CGRect(origin: CGPoint(x: 0.0, y: floor((size.height - layout.size.height) / 2.0)), size: CGSize(width: width, height: layout.size.height))
+
+ itemNode.contentSize = layout.contentSize
+ itemNode.insets = layout.insets
+ itemNode.frame = nodeFrame
+ itemNode.isUserInteractionEnabled = false
+
+ apply(ListViewItemApply(isOnScreen: true))
+ })
+ }
+ } else {
+ var messageNodes: [ListViewItemNode] = []
+ for i in 0 ..< items.count {
+ var itemNode: ListViewItemNode?
+ items[i].nodeConfiguredForParams(async: { $0() }, params: params, synchronousLoads: true, previousItem: i == 0 ? nil : items[i - 1], nextItem: i == (items.count - 1) ? nil : items[i + 1], completion: { node, apply in
+ itemNode = node
+ apply().1(ListViewItemApply(isOnScreen: true))
+ })
+ itemNode!.subnodeTransform = CATransform3DMakeScale(-1.0, 1.0, 1.0)
+ itemNode!.isUserInteractionEnabled = false
+ messageNodes.append(itemNode!)
+ self.messagesContainerNode.addSubnode(itemNode!)
+ }
+ self.messageNodes = messageNodes
+ }
+
+ var bottomOffset: CGFloat = 0.0
+ if let messageNodes = self.messageNodes {
+ for itemNode in messageNodes {
+ itemNode.frame = CGRect(origin: CGPoint(x: inset, y: floor((size.height - itemNode.frame.height) / 2.0)), size: itemNode.frame.size)
+ bottomOffset += itemNode.frame.maxY
+ itemNode.updateFrame(itemNode.frame, within: layout.size)
+ }
+ }
+
+ self.addressNode.frame = CGRect(origin: CGPoint(x: inset + 16.0, y: bottomOffset + 3.0), size: CGSize(width: addressLayout.width, height: addressLayout.height + 3.0))
+
+ let dateHeaderNode: ListViewItemHeaderNode
+ if let currentDateHeaderNode = self.dateHeaderNode {
+ dateHeaderNode = currentDateHeaderNode
+ headerItem.updateNode(dateHeaderNode, previous: nil, next: headerItem)
+ } else {
+ dateHeaderNode = headerItem.node()
+ dateHeaderNode.subnodeTransform = CATransform3DMakeScale(-1.0, 1.0, 1.0)
+ self.messagesContainerNode.addSubnode(dateHeaderNode)
+ self.dateHeaderNode = dateHeaderNode
+ }
+
+ dateHeaderNode.frame = CGRect(origin: CGPoint(x: 0.0, y: bottomOffset), size: CGSize(width: layout.size.width, height: headerItem.height))
+ dateHeaderNode.updateLayout(size: self.containerNode.frame.size, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right)
+ }
+}
diff --git a/submodules/TgVoipWebrtc/tgcalls b/submodules/TgVoipWebrtc/tgcalls
index a7d9b717fd..3195a121ef 160000
--- a/submodules/TgVoipWebrtc/tgcalls
+++ b/submodules/TgVoipWebrtc/tgcalls
@@ -1 +1 @@
-Subproject commit a7d9b717fdf7e8e441b47692dc5771684b2d7970
+Subproject commit 3195a121ef3897d888ae55be1d0665a416560023
diff --git a/third-party/webrtc/webrtc-ios b/third-party/webrtc/webrtc-ios
index cf2c8a8364..e4d49e73cd 160000
--- a/third-party/webrtc/webrtc-ios
+++ b/third-party/webrtc/webrtc-ios
@@ -1 +1 @@
-Subproject commit cf2c8a8364b4cfda7ea9eb448671033351851130
+Subproject commit e4d49e73cd8206518e7b3dd75d54af0f0ef5b810