mirror of
https://github.com/Swiftgram/Telegram-iOS.git
synced 2025-06-16 05:55:20 +00:00
Various fixes
This commit is contained in:
parent
5069754694
commit
6f08efd8ae
@ -8241,3 +8241,6 @@ Sorry for the inconvenience.";
|
||||
"Attachment.DiscardPasteboardAlertText" = "Discard pasted items?";
|
||||
|
||||
"Undo.DeletedTopic" = "Topic Deleted";
|
||||
|
||||
"EmojiSearch.SearchTopicIconsPlaceholder" = "Search Topic Icons";
|
||||
"EmojiSearch.SearchTopicIconsEmptyResult" = "No emoji found";
|
||||
|
@ -524,9 +524,9 @@ public class ChatListControllerImpl: TelegramBaseController, ChatListController
|
||||
default:
|
||||
let actionTitle: String
|
||||
if channel.flags.contains(.requestToJoin) {
|
||||
actionTitle = strongSelf.presentationData.strings.Channel_JoinChannel
|
||||
} else {
|
||||
actionTitle = strongSelf.presentationData.strings.Group_ApplyToJoin
|
||||
} else {
|
||||
actionTitle = strongSelf.presentationData.strings.Channel_JoinChannel
|
||||
}
|
||||
strongSelf.setToolbar(Toolbar(leftAction: nil, rightAction: nil, middleAction: ToolbarAction(title: actionTitle, isEnabled: true)), transition: .animated(duration: 0.4, curve: .spring))
|
||||
}
|
||||
@ -1871,10 +1871,18 @@ public class ChatListControllerImpl: TelegramBaseController, ChatListController
|
||||
}
|
||||
self.tabContainerNode.presentPremiumTip = { [weak self] in
|
||||
if let strongSelf = self {
|
||||
let context = strongSelf.context
|
||||
strongSelf.present(UndoOverlayController(presentationData: strongSelf.presentationData, content: .universal(animation: "anim_reorder", scale: 0.05, colors: [:], title: nil, text: strongSelf.presentationData.strings.ChatListFolderSettings_SubscribeToMoveAll, customUndoText: strongSelf.presentationData.strings.ChatListFolderSettings_SubscribeToMoveAllAction), elevatedLayout: false, position: .top, animateInAsReplacement: false, action: { action in
|
||||
if case .undo = action {
|
||||
strongSelf.push(PremiumIntroScreen(context: context, source: .folders))
|
||||
let context = strongSelf.context
|
||||
var replaceImpl: ((ViewController) -> Void)?
|
||||
let controller = PremiumDemoScreen(context: context, subject: .advancedChatManagement, action: {
|
||||
let controller = PremiumIntroScreen(context: context, source: .folders)
|
||||
replaceImpl?(controller)
|
||||
})
|
||||
replaceImpl = { [weak controller] c in
|
||||
controller?.replace(with: c)
|
||||
}
|
||||
strongSelf.push(controller)
|
||||
}
|
||||
return false }), in: .current)
|
||||
}
|
||||
@ -2980,6 +2988,15 @@ public class ChatListControllerImpl: TelegramBaseController, ChatListController
|
||||
displaySearchFilters = false
|
||||
}
|
||||
|
||||
if !tabsIsEmpty, let snapshotView = strongSelf.tabContainerNode.view.snapshotView(afterScreenUpdates: false) {
|
||||
snapshotView.frame = strongSelf.tabContainerNode.frame
|
||||
strongSelf.tabContainerNode.view.superview?.addSubview(snapshotView)
|
||||
|
||||
snapshotView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, removeOnCompletion: false, completion: { [weak snapshotView] _ in
|
||||
snapshotView?.removeFromSuperview()
|
||||
})
|
||||
}
|
||||
|
||||
if let searchContentNode = strongSelf.searchContentNode {
|
||||
if let filterContainerNodeAndActivate = strongSelf.chatListDisplayNode.activateSearch(placeholderNode: searchContentNode.placeholderNode, displaySearchFilters: displaySearchFilters, hasDownloads: strongSelf.hasDownloads, initialFilter: filter, navigationController: strongSelf.navigationController as? NavigationController) {
|
||||
let (filterContainerNode, activate) = filterContainerNodeAndActivate
|
||||
@ -2996,13 +3013,9 @@ public class ChatListControllerImpl: TelegramBaseController, ChatListController
|
||||
searchContentNode.search(filter: filter, query: query)
|
||||
}
|
||||
|
||||
if !tabsIsEmpty {
|
||||
Queue.mainQueue().after(0.01) {
|
||||
filterContainerNode.layer.animatePosition(from: CGPoint(x: 0.0, y: 38.0), to: CGPoint(), duration: 0.4, timingFunction: kCAMediaTimingFunctionSpring, additive: true)
|
||||
filterContainerNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2)
|
||||
|
||||
strongSelf.tabContainerNode.layer.animatePosition(from: CGPoint(), to: CGPoint(x: 0.0, y: -64.0), duration: 0.4, timingFunction: kCAMediaTimingFunctionSpring, additive: true)
|
||||
}
|
||||
Queue.mainQueue().justDispatch {
|
||||
filterContainerNode.layer.animatePosition(from: CGPoint(x: 0.0, y: 30.0), to: CGPoint(), duration: 0.4, timingFunction: kCAMediaTimingFunctionSpring, additive: true)
|
||||
filterContainerNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.3)
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -3033,15 +3046,6 @@ public class ChatListControllerImpl: TelegramBaseController, ChatListController
|
||||
if !self.displayNavigationBar {
|
||||
var completion: (() -> Void)?
|
||||
|
||||
var filterContainerNode: ASDisplayNode?
|
||||
if animated, let searchContentNode = self.chatListDisplayNode.searchDisplayController?.contentNode as? ChatListSearchContainerNode {
|
||||
filterContainerNode = searchContentNode.filterContainerNode
|
||||
}
|
||||
|
||||
if let searchContentNode = self.searchContentNode {
|
||||
completion = self.chatListDisplayNode.deactivateSearch(placeholderNode: searchContentNode.placeholderNode, animated: animated)
|
||||
}
|
||||
|
||||
let tabsIsEmpty: Bool
|
||||
if let (resolvedItems, displayTabsAtBottom, _) = self.tabContainerData {
|
||||
tabsIsEmpty = resolvedItems.count <= 1 || displayTabsAtBottom
|
||||
@ -3049,6 +3053,33 @@ public class ChatListControllerImpl: TelegramBaseController, ChatListController
|
||||
tabsIsEmpty = true
|
||||
}
|
||||
|
||||
|
||||
var filterContainerNode: ASDisplayNode?
|
||||
if animated, let searchContentNode = self.chatListDisplayNode.searchDisplayController?.contentNode as? ChatListSearchContainerNode {
|
||||
filterContainerNode = searchContentNode.filterContainerNode
|
||||
|
||||
if let filterContainerNode = filterContainerNode, let snapshotView = filterContainerNode.view.snapshotView(afterScreenUpdates: false) {
|
||||
snapshotView.frame = filterContainerNode.frame
|
||||
filterContainerNode.view.superview?.addSubview(snapshotView)
|
||||
|
||||
snapshotView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.3, removeOnCompletion: false, completion: { [weak snapshotView] _ in
|
||||
snapshotView?.removeFromSuperview()
|
||||
})
|
||||
|
||||
if !tabsIsEmpty {
|
||||
Queue.mainQueue().after(0.01) {
|
||||
self.tabContainerNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.3)
|
||||
self.tabContainerNode.layer.animatePosition(from: CGPoint(x: 0.0, y: -74.0), to: .zero, duration: 0.4, timingFunction: kCAMediaTimingFunctionSpring, additive: true)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if let searchContentNode = self.searchContentNode {
|
||||
completion = self.chatListDisplayNode.deactivateSearch(placeholderNode: searchContentNode.placeholderNode, animated: animated)
|
||||
}
|
||||
|
||||
|
||||
self.navigationBar?.setSecondaryContentNode(tabsIsEmpty ? nil : self.tabContainerNode, animated: false)
|
||||
if let parentController = self.parent as? TabBarController {
|
||||
parentController.navigationBar?.setSecondaryContentNode(tabsIsEmpty ? nil : self.tabContainerNode, animated: animated)
|
||||
@ -3061,14 +3092,6 @@ public class ChatListControllerImpl: TelegramBaseController, ChatListController
|
||||
|
||||
(self.parent as? TabBarController)?.updateIsTabBarHidden(false, transition: .animated(duration: 0.4, curve: .spring))
|
||||
|
||||
if let filterContainerNode = filterContainerNode {
|
||||
filterContainerNode.layer.animatePosition(from: CGPoint(), to: CGPoint(x: 0.0, y: -44.0), duration: 0.4, timingFunction: kCAMediaTimingFunctionSpring, removeOnCompletion: false, additive: true)
|
||||
|
||||
if !tabsIsEmpty {
|
||||
self.tabContainerNode.layer.animatePosition(from: CGPoint(x: 0.0, y: -64.0), to: CGPoint(), duration: 0.4, timingFunction: kCAMediaTimingFunctionSpring, additive: true)
|
||||
}
|
||||
}
|
||||
|
||||
self.isSearchActive = false
|
||||
if let navigationController = self.navigationController as? NavigationController {
|
||||
for controller in navigationController.globalOverlayControllers {
|
||||
|
@ -473,7 +473,7 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
private(set) var transitionFraction: CGFloat = 0.0
|
||||
private var transitionFractionOffset: CGFloat = 0.0
|
||||
private var disableItemNodeOperationsWhileAnimating: Bool = false
|
||||
private var validLayout: (layout: ContainerViewLayout, navigationBarHeight: CGFloat, visualNavigationHeight: CGFloat, cleanNavigationBarHeight: CGFloat, isReorderingFilters: Bool, isEditing: Bool)?
|
||||
private var validLayout: (layout: ContainerViewLayout, navigationBarHeight: CGFloat, visualNavigationHeight: CGFloat, cleanNavigationBarHeight: CGFloat, insets: UIEdgeInsets, isReorderingFilters: Bool, isEditing: Bool)?
|
||||
|
||||
private var enableAdjacentFilterLoading: Bool = false
|
||||
|
||||
@ -714,7 +714,7 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
self.onFilterSwitch?()
|
||||
|
||||
self.transitionFractionOffset = 0.0
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = self.validLayout, let itemNode = self.itemNodes[self.selectedId] {
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = self.validLayout, let itemNode = self.itemNodes[self.selectedId] {
|
||||
for (id, itemNode) in self.itemNodes {
|
||||
if id != selectedId {
|
||||
itemNode.emptyNode?.restartAnimation()
|
||||
@ -727,13 +727,13 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
for (_, itemNode) in self.itemNodes {
|
||||
itemNode.layer.removeAllAnimations()
|
||||
}
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
self.currentItemFilterUpdated?(self.currentItemFilter, self.transitionFraction, .immediate, true)
|
||||
}
|
||||
}
|
||||
}
|
||||
case .changed:
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = self.validLayout, let selectedIndex = self.availableFilters.firstIndex(where: { $0.id == self.selectedId }) {
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = self.validLayout, let selectedIndex = self.availableFilters.firstIndex(where: { $0.id == self.selectedId }) {
|
||||
let translation = recognizer.translation(in: self.view)
|
||||
var transitionFraction = translation.x / layout.size.width
|
||||
|
||||
@ -770,11 +770,11 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
}
|
||||
}
|
||||
}
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
self.currentItemFilterUpdated?(self.currentItemFilter, self.transitionFraction, .immediate, false)
|
||||
}
|
||||
case .cancelled, .ended:
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = self.validLayout, let selectedIndex = self.availableFilters.firstIndex(where: { $0.id == self.selectedId }) {
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = self.validLayout, let selectedIndex = self.availableFilters.firstIndex(where: { $0.id == self.selectedId }) {
|
||||
let translation = recognizer.translation(in: self.view)
|
||||
let velocity = recognizer.velocity(in: self.view)
|
||||
var directionIsToRight: Bool?
|
||||
@ -813,12 +813,12 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
self.transitionFraction = 0.0
|
||||
let transition: ContainedViewLayoutTransition = .animated(duration: 0.45, curve: .spring)
|
||||
self.disableItemNodeOperationsWhileAnimating = true
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: transition)
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: transition)
|
||||
self.currentItemFilterUpdated?(self.currentItemFilter, self.transitionFraction, transition, false)
|
||||
DispatchQueue.main.async {
|
||||
self.disableItemNodeOperationsWhileAnimating = false
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = self.validLayout {
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = self.validLayout {
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -884,8 +884,8 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
}
|
||||
strongSelf.availableFilters = availableFilters
|
||||
strongSelf.filtersLimit = limit
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = strongSelf.validLayout {
|
||||
strongSelf.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
if let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = strongSelf.validLayout {
|
||||
strongSelf.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
}
|
||||
}
|
||||
if !availableFilters.contains(where: { $0.id == self.selectedId }) {
|
||||
@ -902,8 +902,8 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
if value != self.enableAdjacentFilterLoading {
|
||||
self.enableAdjacentFilterLoading = value
|
||||
|
||||
if self.enableAdjacentFilterLoading, let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = self.validLayout {
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
if self.enableAdjacentFilterLoading, let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = self.validLayout {
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -912,7 +912,7 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
self.onFilterSwitch?()
|
||||
if id != self.selectedId, let index = self.availableFilters.firstIndex(where: { $0.id == id }) {
|
||||
if let itemNode = self.itemNodes[id] {
|
||||
guard let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = self.validLayout else {
|
||||
guard let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = self.validLayout else {
|
||||
return
|
||||
}
|
||||
self.selectedId = id
|
||||
@ -921,7 +921,7 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
}
|
||||
self.applyItemNodeAsCurrent(id: id, itemNode: itemNode)
|
||||
let transition: ContainedViewLayoutTransition = .animated(duration: 0.35, curve: .spring)
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: transition)
|
||||
self.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: transition)
|
||||
self.currentItemFilterUpdated?(self.currentItemFilter, self.transitionFraction, transition, false)
|
||||
itemNode.emptyNode?.restartAnimation()
|
||||
completion?()
|
||||
@ -951,7 +951,7 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
|
||||
strongSelf.pendingItemNode = nil
|
||||
|
||||
guard let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing) = strongSelf.validLayout else {
|
||||
guard let (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing) = strongSelf.validLayout else {
|
||||
strongSelf.itemNodes[id] = itemNode
|
||||
strongSelf.addSubnode(itemNode)
|
||||
|
||||
@ -999,13 +999,7 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
itemNode.frame = itemFrame
|
||||
|
||||
transition.animatePositionAdditive(node: itemNode, offset: CGPoint(x: -offset, y: 0.0))
|
||||
|
||||
var insets = layout.insets(options: [.input])
|
||||
insets.top += navigationBarHeight
|
||||
|
||||
insets.left += layout.safeInsets.left
|
||||
insets.right += layout.safeInsets.right
|
||||
|
||||
|
||||
itemNode.updateLayout(size: layout.size, insets: insets, visualNavigationHeight: visualNavigationHeight, transition: .immediate)
|
||||
|
||||
strongSelf.selectedId = id
|
||||
@ -1014,7 +1008,7 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
}
|
||||
strongSelf.applyItemNodeAsCurrent(id: id, itemNode: itemNode)
|
||||
|
||||
strongSelf.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
strongSelf.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: isReorderingFilters, isEditing: isEditing, transition: .immediate)
|
||||
|
||||
strongSelf.currentItemFilterUpdated?(strongSelf.currentItemFilter, strongSelf.transitionFraction, transition, false)
|
||||
}
|
||||
@ -1025,25 +1019,11 @@ final class ChatListContainerNode: ASDisplayNode, UIGestureRecognizerDelegate {
|
||||
}
|
||||
}
|
||||
|
||||
func update(layout: ContainerViewLayout, navigationBarHeight: CGFloat, visualNavigationHeight: CGFloat, cleanNavigationBarHeight: CGFloat, isReorderingFilters: Bool, isEditing: Bool, transition: ContainedViewLayoutTransition) {
|
||||
self.validLayout = (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, isReorderingFilters, isEditing)
|
||||
func update(layout: ContainerViewLayout, navigationBarHeight: CGFloat, visualNavigationHeight: CGFloat, cleanNavigationBarHeight: CGFloat, insets: UIEdgeInsets, isReorderingFilters: Bool, isEditing: Bool, transition: ContainedViewLayoutTransition) {
|
||||
self.validLayout = (layout, navigationBarHeight, visualNavigationHeight, cleanNavigationBarHeight, insets, isReorderingFilters, isEditing)
|
||||
|
||||
self._validLayoutReady.set(.single(true))
|
||||
|
||||
var insets = layout.insets(options: [.input])
|
||||
insets.top += navigationBarHeight
|
||||
|
||||
insets.left += layout.safeInsets.left
|
||||
insets.right += layout.safeInsets.right
|
||||
|
||||
if isEditing {
|
||||
if !layout.safeInsets.left.isZero {
|
||||
insets.bottom += 34.0
|
||||
} else {
|
||||
insets.bottom += 49.0
|
||||
}
|
||||
}
|
||||
|
||||
transition.updateAlpha(node: self, alpha: isReorderingFilters ? 0.5 : 1.0)
|
||||
self.isUserInteractionEnabled = !isReorderingFilters
|
||||
|
||||
@ -1264,20 +1244,26 @@ final class ChatListControllerNode: ASDisplayNode {
|
||||
if layout.metrics.widthClass == .regular {
|
||||
options.insert(.input)
|
||||
}
|
||||
|
||||
var heightInset: CGFloat = 0.0
|
||||
if case .forum = self.location {
|
||||
heightInset = 4.0
|
||||
}
|
||||
|
||||
let bottomInset: CGFloat = layout.insets(options: options).bottom
|
||||
if !layout.safeInsets.left.isZero {
|
||||
tabBarHeight = 34.0 + bottomInset
|
||||
insets.bottom += 34.0
|
||||
} else {
|
||||
tabBarHeight = 49.0 + bottomInset
|
||||
insets.bottom += 49.0
|
||||
tabBarHeight = 49.0 - heightInset + bottomInset
|
||||
insets.bottom += 49.0 - heightInset
|
||||
}
|
||||
|
||||
let tabBarFrame = CGRect(origin: CGPoint(x: 0.0, y: layout.size.height - tabBarHeight), size: CGSize(width: layout.size.width, height: tabBarHeight))
|
||||
let toolbarFrame = CGRect(origin: CGPoint(x: 0.0, y: layout.size.height - tabBarHeight), size: CGSize(width: layout.size.width, height: tabBarHeight))
|
||||
|
||||
if let toolbarNode = self.toolbarNode {
|
||||
transition.updateFrame(node: toolbarNode, frame: tabBarFrame)
|
||||
toolbarNode.updateLayout(size: tabBarFrame.size, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right, additionalSideInsets: layout.additionalInsets, bottomInset: bottomInset, toolbar: toolbar, transition: transition)
|
||||
transition.updateFrame(node: toolbarNode, frame: toolbarFrame)
|
||||
toolbarNode.updateLayout(size: toolbarFrame.size, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right, additionalSideInsets: layout.additionalInsets, bottomInset: bottomInset, toolbar: toolbar, transition: transition)
|
||||
} else {
|
||||
let toolbarNode = ToolbarNode(theme: ToolbarTheme(rootControllerTheme: self.presentationData.theme), displaySeparator: true, left: { [weak self] in
|
||||
self?.toolbarActionSelected?(.left)
|
||||
@ -1286,8 +1272,8 @@ final class ChatListControllerNode: ASDisplayNode {
|
||||
}, middle: { [weak self] in
|
||||
self?.toolbarActionSelected?(.middle)
|
||||
})
|
||||
toolbarNode.frame = tabBarFrame
|
||||
toolbarNode.updateLayout(size: tabBarFrame.size, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right, additionalSideInsets: layout.additionalInsets, bottomInset: bottomInset, toolbar: toolbar, transition: .immediate)
|
||||
toolbarNode.frame = toolbarFrame
|
||||
toolbarNode.updateLayout(size: toolbarFrame.size, leftInset: layout.safeInsets.left, rightInset: layout.safeInsets.right, additionalSideInsets: layout.additionalInsets, bottomInset: bottomInset, toolbar: toolbar, transition: .immediate)
|
||||
self.addSubnode(toolbarNode)
|
||||
self.toolbarNode = toolbarNode
|
||||
if transition.isAnimated {
|
||||
@ -1306,7 +1292,7 @@ final class ChatListControllerNode: ASDisplayNode {
|
||||
self.controller?.presentationContext.containerLayoutUpdated(childrenLayout, transition: transition)
|
||||
|
||||
transition.updateFrame(node: self.containerNode, frame: CGRect(origin: CGPoint(), size: layout.size))
|
||||
self.containerNode.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, isReorderingFilters: self.isReorderingFilters, isEditing: self.isEditing, transition: transition)
|
||||
self.containerNode.update(layout: layout, navigationBarHeight: navigationBarHeight, visualNavigationHeight: visualNavigationHeight, cleanNavigationBarHeight: cleanNavigationBarHeight, insets: insets, isReorderingFilters: self.isReorderingFilters, isEditing: self.isEditing, transition: transition)
|
||||
|
||||
transition.updateFrame(node: self.inlineTabContainerNode, frame: CGRect(origin: CGPoint(x: 0.0, y: layout.size.height - layout.intrinsicInsets.bottom - 8.0 - 40.0), size: CGSize(width: layout.size.width, height: 40.0)))
|
||||
|
||||
|
@ -2211,7 +2211,7 @@ class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
|
||||
let avatarIconContent: EmojiStatusComponent.Content
|
||||
if let fileId = threadInfo.info.icon, fileId != 0 {
|
||||
avatarIconContent = .animation(content: .customEmoji(fileId: fileId), size: CGSize(width: 48.0, height: 48.0), placeholderColor: item.presentationData.theme.list.mediaPlaceholderColor, themeColor: item.presentationData.theme.list.itemAccentColor, loopMode: .forever)
|
||||
avatarIconContent = .animation(content: .customEmoji(fileId: fileId), size: CGSize(width: 48.0, height: 48.0), placeholderColor: item.presentationData.theme.list.mediaPlaceholderColor, themeColor: item.presentationData.theme.list.itemAccentColor, loopMode: .count(2))
|
||||
} else {
|
||||
avatarIconContent = .topic(title: String(threadInfo.info.title.prefix(1)), color: threadInfo.info.iconColor, size: CGSize(width: 32.0, height: 32.0))
|
||||
}
|
||||
|
@ -407,7 +407,7 @@ private class SearchBarTextField: UITextField, UIScrollViewDelegate {
|
||||
}
|
||||
}
|
||||
|
||||
private var tokensWidth: CGFloat = 0.0
|
||||
fileprivate var tokensWidth: CGFloat = 0.0
|
||||
|
||||
private let measurePrefixLabel: ImmediateTextNode
|
||||
let prefixLabel: ImmediateTextNode
|
||||
@ -569,19 +569,24 @@ private class SearchBarTextField: UITextField, UIScrollViewDelegate {
|
||||
textOffset += 2.0
|
||||
}
|
||||
|
||||
var placeholderOffset: CGFloat = 0.0
|
||||
var placeholderXOffset: CGFloat = 0.0
|
||||
if self.tokensWidth > 0.0, self.scrollView?.superview != nil {
|
||||
placeholderXOffset = self.tokensWidth + 8.0
|
||||
}
|
||||
|
||||
var placeholderYOffset: CGFloat = 0.0
|
||||
if #available(iOS 14.0, *) {
|
||||
placeholderOffset = 1.0
|
||||
placeholderYOffset = 1.0
|
||||
} else {
|
||||
}
|
||||
|
||||
let textRect = self.textRect(forBounds: bounds)
|
||||
let labelSize = self.placeholderLabel.updateLayout(textRect.size)
|
||||
self.placeholderLabel.frame = CGRect(origin: CGPoint(x: textRect.minX, y: textRect.minY + textOffset + placeholderOffset), size: labelSize)
|
||||
|
||||
self.placeholderLabel.frame = CGRect(origin: CGPoint(x: textRect.minX + placeholderXOffset, y: textRect.minY + textOffset + placeholderYOffset), size: labelSize)
|
||||
|
||||
let prefixSize = self.prefixLabel.updateLayout(CGSize(width: floor(bounds.size.width * 0.7), height: bounds.size.height))
|
||||
let prefixBounds = bounds.insetBy(dx: 4.0, dy: 4.0)
|
||||
self.prefixLabel.frame = CGRect(origin: CGPoint(x: prefixBounds.minX, y: prefixBounds.minY + textOffset + placeholderOffset), size: prefixSize)
|
||||
self.prefixLabel.frame = CGRect(origin: CGPoint(x: prefixBounds.minX, y: prefixBounds.minY + textOffset + placeholderYOffset), size: prefixSize)
|
||||
}
|
||||
|
||||
override func deleteBackward() {
|
||||
@ -1027,7 +1032,12 @@ public class SearchBarNode: ASDisplayNode, UITextFieldDelegate {
|
||||
self.textBackgroundNode.layer.animateFrame(from: initialTextBackgroundFrame, to: self.textBackgroundNode.frame, duration: duration, timingFunction: timingFunction)
|
||||
|
||||
let textFieldFrame = self.textField.frame
|
||||
let initialLabelNodeFrame = CGRect(origin: node.labelNode.frame.offsetBy(dx: initialTextBackgroundFrame.origin.x - 7.0, dy: initialTextBackgroundFrame.origin.y - 8.0).origin, size: textFieldFrame.size)
|
||||
var tokensWidth = self.textField.tokensWidth
|
||||
if tokensWidth > 0.0 {
|
||||
tokensWidth += 8.0
|
||||
}
|
||||
|
||||
let initialLabelNodeFrame = CGRect(origin: node.labelNode.frame.offsetBy(dx: initialTextBackgroundFrame.origin.x - 7.0 - tokensWidth, dy: initialTextBackgroundFrame.origin.y - 8.0).origin, size: textFieldFrame.size)
|
||||
self.textField.layer.animateFrame(from: initialLabelNodeFrame, to: self.textField.frame, duration: duration, timingFunction: timingFunction)
|
||||
|
||||
let iconFrame = self.iconNode.frame
|
||||
@ -1056,13 +1066,54 @@ public class SearchBarNode: ASDisplayNode, UITextFieldDelegate {
|
||||
let timingFunction = kCAMediaTimingFunctionSpring
|
||||
|
||||
node.isHidden = true
|
||||
self.clearButton.isHidden = true
|
||||
|
||||
if !self.clearButton.isHidden {
|
||||
let xOffset = targetTextBackgroundFrame.width - self.textBackgroundNode.frame.width
|
||||
if !xOffset.isZero {
|
||||
self.clearButton.layer.animatePosition(from: .zero, to: CGPoint(x: xOffset, y: 0.0), duration: duration, timingFunction: timingFunction, additive: true)
|
||||
}
|
||||
self.clearButton.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, completion: { _ in
|
||||
self.clearButton.isHidden = true
|
||||
})
|
||||
}
|
||||
|
||||
self.activityIndicator?.isHidden = true
|
||||
self.iconNode.isHidden = false
|
||||
|
||||
var tokensWidth = self.textField.tokensWidth
|
||||
if tokensWidth > 0.0 {
|
||||
tokensWidth += 8.0
|
||||
}
|
||||
|
||||
let textFieldFrame = self.textField.frame
|
||||
let targetLabelNodeFrame = CGRect(origin: CGPoint(x: node.labelNode.frame.minX + targetTextBackgroundFrame.origin.x - 7.0 - tokensWidth, y: targetTextBackgroundFrame.minY + floorToScreenPixels((targetTextBackgroundFrame.size.height - textFieldFrame.size.height) / 2.0) - UIScreenPixel), size: textFieldFrame.size)
|
||||
|
||||
self.textField.layer.animateFrame(from: textFieldFrame, to: targetLabelNodeFrame, duration: duration, timingFunction: timingFunction, removeOnCompletion: false)
|
||||
|
||||
if !self.textField.tokenNodes.isEmpty {
|
||||
for node in self.textField.tokenNodes.values {
|
||||
node.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, removeOnCompletion: false)
|
||||
}
|
||||
}
|
||||
|
||||
var hasText = false
|
||||
if !(self.textField.text ?? "").isEmpty, let snapshotView = self.textField.snapshotView(afterScreenUpdates: false) {
|
||||
hasText = true
|
||||
snapshotView.frame = self.textField.frame
|
||||
self.textField.superview?.addSubview(snapshotView)
|
||||
snapshotView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, removeOnCompletion: false, completion: { _ in
|
||||
snapshotView.removeFromSuperview()
|
||||
})
|
||||
|
||||
snapshotView.layer.animatePosition(from: .zero, to: CGPoint(x: targetLabelNodeFrame.minX - textFieldFrame.minX, y: 0.0), duration: duration, timingFunction: timingFunction, removeOnCompletion: false, additive: true)
|
||||
|
||||
self.textField.placeholderLabel.alpha = 0.0
|
||||
}
|
||||
|
||||
self.textField.prefixString = nil
|
||||
self.textField.text = ""
|
||||
self.textField.layoutSubviews()
|
||||
|
||||
|
||||
var backgroundCompleted = false
|
||||
var separatorCompleted = false
|
||||
var textBackgroundCompleted = false
|
||||
@ -1123,34 +1174,18 @@ public class SearchBarNode: ASDisplayNode, UITextFieldDelegate {
|
||||
transitionBackgroundNode.backgroundColor = node.backgroundNode.backgroundColor
|
||||
transitionBackgroundNode.cornerRadius = node.backgroundNode.cornerRadius
|
||||
self.insertSubnode(transitionBackgroundNode, aboveSubnode: self.textBackgroundNode)
|
||||
//transitionBackgroundNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: duration / 2.0, removeOnCompletion: false)
|
||||
transitionBackgroundNode.layer.animateFrame(from: self.textBackgroundNode.frame, to: targetTextBackgroundFrame, duration: duration, timingFunction: timingFunction, removeOnCompletion: false)
|
||||
|
||||
let textFieldFrame = self.textField.frame
|
||||
let targetLabelNodeFrame = CGRect(origin: CGPoint(x: node.labelNode.frame.minX + targetTextBackgroundFrame.origin.x - 7.0, y: targetTextBackgroundFrame.minY + floorToScreenPixels((targetTextBackgroundFrame.size.height - textFieldFrame.size.height) / 2.0) - UIScreenPixel), size: textFieldFrame.size)
|
||||
self.textField.layer.animateFrame(from: self.textField.frame, to: targetLabelNodeFrame, duration: duration, timingFunction: timingFunction, removeOnCompletion: false)
|
||||
if #available(iOSApplicationExtension 10.0, iOS 10.0, *) {
|
||||
if let snapshot = node.labelNode.layer.snapshotContentTree() {
|
||||
snapshot.frame = CGRect(origin: self.textField.placeholderLabel.frame.origin.offsetBy(dx: 0.0, dy: UIScreenPixel), size: node.labelNode.frame.size)
|
||||
self.textField.layer.addSublayer(snapshot)
|
||||
snapshot.animateAlpha(from: 0.0, to: 1.0, duration: duration * 2.0 / 3.0, timingFunction: CAMediaTimingFunctionName.linear.rawValue)
|
||||
transitionBackgroundNode.layer.animateFrame(from: self.textBackgroundNode.frame, to: targetTextBackgroundFrame, duration: duration, timingFunction: timingFunction, removeOnCompletion: false)
|
||||
|
||||
if let snapshot = node.labelNode.layer.snapshotContentTree() {
|
||||
snapshot.frame = CGRect(origin: self.textField.placeholderLabel.frame.origin.offsetBy(dx: 0.0, dy: UIScreenPixel), size: node.labelNode.frame.size)
|
||||
self.textField.layer.addSublayer(snapshot)
|
||||
snapshot.animateAlpha(from: 0.0, to: 1.0, duration: duration * 2.0 / 3.0, timingFunction: CAMediaTimingFunctionName.linear.rawValue)
|
||||
if !hasText {
|
||||
self.textField.placeholderLabel.layer.animateAlpha(from: 1.0, to: 0.0, duration: duration, timingFunction: CAMediaTimingFunctionName.linear.rawValue, removeOnCompletion: false)
|
||||
}
|
||||
} else if let cachedLayout = node.labelNode.cachedLayout {
|
||||
let labelNode = TextNode()
|
||||
labelNode.isOpaque = false
|
||||
labelNode.isUserInteractionEnabled = false
|
||||
let labelLayout = TextNode.asyncLayout(labelNode)
|
||||
let (labelLayoutResult, labelApply) = labelLayout(TextNodeLayoutArguments(attributedString: self.placeholderString, backgroundColor: .clear, maximumNumberOfLines: 1, truncationType: .end, constrainedSize: cachedLayout.size, alignment: .natural, cutout: nil, insets: UIEdgeInsets()))
|
||||
let _ = labelApply()
|
||||
|
||||
self.textField.addSubnode(labelNode)
|
||||
labelNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: duration * 2.0 / 3.0, timingFunction: CAMediaTimingFunctionName.linear.rawValue)
|
||||
labelNode.frame = CGRect(origin: self.textField.placeholderLabel.frame.origin.offsetBy(dx: 0.0, dy: UIScreenPixel), size: labelLayoutResult.size)
|
||||
self.textField.placeholderLabel.layer.animateAlpha(from: 1.0, to: 0.0, duration: duration, timingFunction: CAMediaTimingFunctionName.linear.rawValue, removeOnCompletion: false, completion: { _ in
|
||||
labelNode.removeFromSupernode()
|
||||
})
|
||||
}
|
||||
|
||||
let iconFrame = self.iconNode.frame
|
||||
let targetIconFrame = CGRect(origin: node.iconNode.frame.offsetBy(dx: targetTextBackgroundFrame.origin.x, dy: targetTextBackgroundFrame.origin.y).origin, size: iconFrame.size)
|
||||
self.iconNode.image = node.iconNode.image
|
||||
@ -1216,13 +1251,6 @@ public class SearchBarNode: ASDisplayNode, UITextFieldDelegate {
|
||||
}
|
||||
|
||||
private func updateIsEmpty(animated: Bool = false) {
|
||||
let textIsEmpty = (self.textField.text?.isEmpty ?? true)
|
||||
let isEmpty = textIsEmpty && self.tokens.isEmpty
|
||||
|
||||
let transition: ContainedViewLayoutTransition = animated ? .animated(duration: 0.3, curve: .spring) : .immediate
|
||||
let placeholderTransition = !isEmpty ? .immediate : transition
|
||||
placeholderTransition.updateAlpha(node: self.textField.placeholderLabel, alpha: isEmpty ? 1.0 : 0.0)
|
||||
|
||||
var tokensEmpty = true
|
||||
for token in self.tokens {
|
||||
if !token.permanent {
|
||||
@ -1230,6 +1258,13 @@ public class SearchBarNode: ASDisplayNode, UITextFieldDelegate {
|
||||
}
|
||||
}
|
||||
|
||||
let textIsEmpty = (self.textField.text?.isEmpty ?? true)
|
||||
let isEmpty = textIsEmpty && tokensEmpty
|
||||
|
||||
let transition: ContainedViewLayoutTransition = animated ? .animated(duration: 0.3, curve: .spring) : .immediate
|
||||
let placeholderTransition = !isEmpty ? .immediate : transition
|
||||
placeholderTransition.updateAlpha(node: self.textField.placeholderLabel, alpha: isEmpty ? 1.0 : 0.0)
|
||||
|
||||
let clearIsHidden = (textIsEmpty && tokensEmpty) && self.prefixString == nil
|
||||
transition.updateAlpha(node: self.clearButton.imageNode, alpha: clearIsHidden ? 0.0 : 1.0)
|
||||
transition.updateTransformScale(node: self.clearButton, scale: clearIsHidden ? 0.2 : 1.0)
|
||||
|
@ -200,7 +200,7 @@ public final class SearchDisplayController {
|
||||
|
||||
if !self.contentNode.hasDim {
|
||||
self.backgroundNode.alpha = 1.0
|
||||
self.backgroundNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.25, timingFunction: CAMediaTimingFunctionName.easeOut.rawValue)
|
||||
self.backgroundNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2, timingFunction: CAMediaTimingFunctionName.linear.rawValue)
|
||||
|
||||
self.backgroundNode.layer.animateScale(from: 0.85, to: 1.0, duration: 0.5, timingFunction: kCAMediaTimingFunctionSpring)
|
||||
}
|
||||
@ -259,7 +259,7 @@ public final class SearchDisplayController {
|
||||
}
|
||||
|
||||
public func deactivate(placeholder: SearchBarPlaceholderNode?, animated: Bool = true) {
|
||||
self.searchBar.deactivate()
|
||||
self.searchBar.deactivate(clear: false)
|
||||
|
||||
let searchBar = self.searchBar
|
||||
if let placeholder = placeholder {
|
||||
|
@ -718,7 +718,7 @@ public final class ChatTitleView: UIView, NavigationBarTitleView {
|
||||
if self.titleRightIconNode.supernode == nil {
|
||||
self.titleTextNode.addSubnode(self.titleRightIconNode)
|
||||
}
|
||||
rightIconWidth = image.size.width + 3.0
|
||||
rightIconWidth = max(24.0, image.size.width) + 3.0
|
||||
} else if self.titleRightIconNode.supernode != nil {
|
||||
self.titleRightIconNode.removeFromSupernode()
|
||||
}
|
||||
|
@ -63,9 +63,9 @@ public func generateTopicIcon(title: String, backgroundColors: [UIColor], stroke
|
||||
let attributedString = NSAttributedString(string: title, attributes: [NSAttributedString.Key.font: Font.with(size: fontSize, design: .round, weight: .bold), NSAttributedString.Key.foregroundColor: UIColor.white])
|
||||
|
||||
let line = CTLineCreateWithAttributedString(attributedString)
|
||||
let lineBounds = CTLineGetBoundsWithOptions(line, .useGlyphPathBounds)
|
||||
let lineBounds = CTLineGetBoundsWithOptions(line, [.useOpticalBounds])
|
||||
|
||||
let lineOffset = CGPoint(x: title == "B" ? 1.0 : 0.0, y: floorToScreenPixels(realSize.height * 0.05))
|
||||
let lineOffset = CGPoint(x: 1.0 - UIScreenPixel, y: floorToScreenPixels(realSize.height * 0.05))
|
||||
let lineOrigin = CGPoint(x: floorToScreenPixels(-lineBounds.origin.x + (realSize.width - lineBounds.size.width) / 2.0) + lineOffset.x, y: floorToScreenPixels(-lineBounds.origin.y + (realSize.height - lineBounds.size.height) / 2.0) + lineOffset.y)
|
||||
|
||||
context.translateBy(x: realSize.width / 2.0, y: realSize.height / 2.0)
|
||||
|
@ -6916,6 +6916,8 @@ public final class EmojiPagerContentComponent: Component {
|
||||
displaySearchWithPlaceholder = strings.EmojiSearch_SearchReactionsPlaceholder
|
||||
} else if isStatusSelection {
|
||||
displaySearchWithPlaceholder = strings.EmojiSearch_SearchStatusesPlaceholder
|
||||
} else if isTopicIconSelection {
|
||||
displaySearchWithPlaceholder = strings.EmojiSearch_SearchTopicIconsPlaceholder
|
||||
}
|
||||
|
||||
return EmojiPagerContentComponent(
|
||||
@ -7014,8 +7016,7 @@ func generateTopicIcon(backgroundColors: [UIColor], strokeColors: [UIColor], tit
|
||||
let line = CTLineCreateWithAttributedString(attributedString)
|
||||
let lineBounds = CTLineGetBoundsWithOptions(line, .useGlyphPathBounds)
|
||||
|
||||
let lineOffset = CGPoint(x: title == "B" ? 1.0 : 0.0, y: 0.0)
|
||||
let lineOrigin = CGPoint(x: floorToScreenPixels(-lineBounds.origin.x + (size.width - lineBounds.size.width) / 2.0) + lineOffset.x, y: floorToScreenPixels(-lineBounds.origin.y + (size.height - lineBounds.size.height) / 2.0) + 1.0)
|
||||
let lineOrigin = CGPoint(x: floorToScreenPixels(-lineBounds.origin.x + (size.width - lineBounds.size.width) / 2.0), y: floorToScreenPixels(-lineBounds.origin.y + (size.height - lineBounds.size.height) / 2.0) + 1.0)
|
||||
|
||||
context.translateBy(x: size.width / 2.0, y: size.height / 2.0)
|
||||
context.scaleBy(x: 1.0, y: -1.0)
|
||||
|
@ -85,7 +85,11 @@ private func actionForPeer(peer: Peer, interfaceState: ChatPresentationInterface
|
||||
if channel.flags.contains(.requestToJoin) {
|
||||
return .applyToJoin
|
||||
} else {
|
||||
return .joinGroup
|
||||
if channel.flags.contains(.isForum) {
|
||||
return .join
|
||||
} else {
|
||||
return .joinGroup
|
||||
}
|
||||
}
|
||||
} else {
|
||||
return .join
|
||||
|
@ -4924,7 +4924,7 @@ public final class ChatControllerImpl: TelegramBaseController, ChatController, G
|
||||
|
||||
let avatarContent: EmojiStatusComponent.Content
|
||||
if let fileId = threadInfo.icon {
|
||||
avatarContent = .animation(content: .customEmoji(fileId: fileId), size: CGSize(width: 48.0, height: 48.0), placeholderColor: strongSelf.presentationData.theme.list.mediaPlaceholderColor, themeColor: strongSelf.presentationData.theme.list.itemAccentColor, loopMode: .count(2))
|
||||
avatarContent = .animation(content: .customEmoji(fileId: fileId), size: CGSize(width: 48.0, height: 48.0), placeholderColor: strongSelf.presentationData.theme.list.mediaPlaceholderColor, themeColor: strongSelf.presentationData.theme.list.itemAccentColor, loopMode: .count(1))
|
||||
} else {
|
||||
avatarContent = .topic(title: String(threadInfo.title.prefix(1)), color: threadInfo.iconColor, size: CGSize(width: 32.0, height: 32.0))
|
||||
}
|
||||
|
@ -896,7 +896,7 @@ private enum ChatEmptyNodeContentType: Equatable {
|
||||
case cloud
|
||||
case peerNearby
|
||||
case greeting
|
||||
case topic(Int64?)
|
||||
case topic
|
||||
}
|
||||
|
||||
final class ChatEmptyNode: ASDisplayNode {
|
||||
@ -973,7 +973,7 @@ final class ChatEmptyNode: ASDisplayNode {
|
||||
let contentType: ChatEmptyNodeContentType
|
||||
if case .replyThread = interfaceState.chatLocation {
|
||||
if case .topic = emptyType {
|
||||
contentType = .topic(nil)
|
||||
contentType = .topic
|
||||
} else {
|
||||
contentType = .regular
|
||||
}
|
||||
|
@ -2765,7 +2765,7 @@ public final class ChatHistoryListNode: ListView, ChatHistoryNode {
|
||||
} else if action.action == .historyCleared {
|
||||
emptyType = .clearedHistory
|
||||
break
|
||||
} else if case .topicCreated = action.action {
|
||||
} else if case .topicCreated = action.action, firstEntry.message.author?.id == strongSelf.context.account.peerId {
|
||||
emptyType = .topic
|
||||
break
|
||||
}
|
||||
|
@ -152,13 +152,13 @@ func inputPanelForChatPresentationIntefaceState(_ chatPresentationInterfaceState
|
||||
isMember = true
|
||||
case .left:
|
||||
if case .replyThread = chatPresentationInterfaceState.chatLocation {
|
||||
if !channel.flags.contains(.joinToSend) {
|
||||
if !channel.flags.contains(.joinToSend) && !channel.flags.contains(.isForum) {
|
||||
isMember = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if channel.flags.contains(.isForum) {
|
||||
if channel.flags.contains(.isForum) && isMember {
|
||||
if let threadData = chatPresentationInterfaceState.threadData {
|
||||
if threadData.isClosed {
|
||||
var canManage = false
|
||||
|
@ -1396,17 +1396,9 @@ class ChatMessageBubbleItemNode: ChatMessageItemView, ChatMessagePreviewItemNode
|
||||
}
|
||||
authorRank = attributes.rank
|
||||
}
|
||||
|
||||
var enableAutoRank = false
|
||||
if let authorRank = authorRank, case .admin = authorRank {
|
||||
enableAutoRank = true
|
||||
} else if authorRank == nil {
|
||||
enableAutoRank = true
|
||||
}
|
||||
if enableAutoRank {
|
||||
if let topicAuthorId = item.associatedData.topicAuthorId, topicAuthorId == message.author?.id {
|
||||
authorRank = .custom(item.presentationData.strings.Chat_Message_TopicAuthorBadge)
|
||||
}
|
||||
|
||||
if authorRank == nil, let topicAuthorId = item.associatedData.topicAuthorId, topicAuthorId == message.author?.id {
|
||||
authorRank = .custom(item.presentationData.strings.Chat_Message_TopicAuthorBadge)
|
||||
}
|
||||
case .group:
|
||||
break
|
||||
|
Loading…
x
Reference in New Issue
Block a user