mirror of
https://github.com/Swiftgram/Telegram-iOS.git
synced 2025-12-24 07:05:35 +00:00
Various improvements
This commit is contained in:
@@ -1234,6 +1234,9 @@ public class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
var credibilityIconComponent: EmojiStatusComponent?
|
||||
let mutedIconNode: ASImageNode
|
||||
var itemTagList: ComponentView<Empty>?
|
||||
var actionButtonTitleNode: TextNode?
|
||||
var actionButtonBackgroundView: UIImageView?
|
||||
var actionButtonNode: HighlightableButtonNode?
|
||||
|
||||
private var hierarchyTrackingLayer: HierarchyTrackingLayer?
|
||||
private var cachedDataDisposable = MetaDisposable()
|
||||
@@ -1890,6 +1893,7 @@ public class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
let onlineLayout = self.onlineNode.asyncLayout()
|
||||
let selectableControlLayout = ItemListSelectableControlNode.asyncLayout(self.selectableControlNode)
|
||||
let reorderControlLayout = ItemListEditableReorderControlNode.asyncLayout(self.reorderControlNode)
|
||||
let makeActionButtonTitleNodeLayout = TextNode.asyncLayout(self.actionButtonTitleNode)
|
||||
|
||||
let currentItem = self.layoutParams?.0
|
||||
let currentChatListText = self.cachedChatListText
|
||||
@@ -3061,6 +3065,12 @@ public class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
|
||||
let (mentionBadgeLayout, mentionBadgeApply) = mentionBadgeLayout(CGSize(width: rawContentWidth, height: CGFloat.greatestFiniteMagnitude), badgeDiameter, badgeFont, currentMentionBadgeImage, mentionBadgeContent)
|
||||
|
||||
var actionButtonTitleNodeLayoutAndApply: (TextNodeLayout, () -> TextNode)?
|
||||
if case .none = badgeContent, case .none = mentionBadgeContent, case let .chat(itemPeer) = contentPeer, case let .user(user) = itemPeer.chatMainPeer, let botInfo = user.botInfo, botInfo.flags.contains(.hasWebApp) {
|
||||
//TODO:localize
|
||||
actionButtonTitleNodeLayoutAndApply = makeActionButtonTitleNodeLayout(TextNodeLayoutArguments(attributedString: NSAttributedString(string: "OPEN", font: Font.semibold(15.0), textColor: theme.unreadBadgeActiveTextColor), backgroundColor: nil, maximumNumberOfLines: 1, truncationType: .end, constrainedSize: CGSize(width: rawContentWidth, height: CGFloat.greatestFiniteMagnitude), alignment: .natural, cutout: nil, insets: UIEdgeInsets()))
|
||||
}
|
||||
|
||||
var badgeSize: CGFloat = 0.0
|
||||
if !badgeLayout.width.isZero {
|
||||
badgeSize += badgeLayout.width + 5.0
|
||||
@@ -3081,6 +3091,14 @@ public class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
}
|
||||
badgeSize += currentPinnedIconImage.size.width
|
||||
}
|
||||
if let (actionButtonTitleNodeLayout, _) = actionButtonTitleNodeLayoutAndApply {
|
||||
if !badgeSize.isZero {
|
||||
badgeSize += 4.0
|
||||
} else {
|
||||
badgeSize += 5.0
|
||||
}
|
||||
badgeSize += actionButtonTitleNodeLayout.size.width + 12.0 * 2.0
|
||||
}
|
||||
badgeSize = max(badgeSize, reorderInset)
|
||||
|
||||
if !itemTags.isEmpty {
|
||||
@@ -3816,23 +3834,19 @@ public class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
strongSelf.statusNode.fontSize = item.presentationData.fontSize.itemListBaseFontSize
|
||||
let _ = strongSelf.statusNode.transitionToState(statusState, animated: animateContent)
|
||||
|
||||
var nextBadgeX: CGFloat = contentRect.maxX
|
||||
if let _ = currentBadgeBackgroundImage {
|
||||
let badgeFrame = CGRect(x: contentRect.maxX - badgeLayout.width, y: contentRect.maxY - badgeLayout.height - 2.0, width: badgeLayout.width, height: badgeLayout.height)
|
||||
let badgeFrame = CGRect(x: nextBadgeX - badgeLayout.width, y: contentRect.maxY - badgeLayout.height - 2.0, width: badgeLayout.width, height: badgeLayout.height)
|
||||
|
||||
transition.updateFrame(node: strongSelf.badgeNode, frame: badgeFrame)
|
||||
nextBadgeX -= badgeLayout.width + 6.0
|
||||
}
|
||||
|
||||
if currentMentionBadgeImage != nil || currentBadgeBackgroundImage != nil {
|
||||
let mentionBadgeOffset: CGFloat
|
||||
if badgeLayout.width.isZero {
|
||||
mentionBadgeOffset = contentRect.maxX - mentionBadgeLayout.width
|
||||
} else {
|
||||
mentionBadgeOffset = contentRect.maxX - badgeLayout.width - 6.0 - mentionBadgeLayout.width
|
||||
}
|
||||
|
||||
let badgeFrame = CGRect(x: mentionBadgeOffset, y: contentRect.maxY - mentionBadgeLayout.height - 2.0, width: mentionBadgeLayout.width, height: mentionBadgeLayout.height)
|
||||
let badgeFrame = CGRect(x: nextBadgeX - mentionBadgeLayout.width, y: contentRect.maxY - mentionBadgeLayout.height - 2.0, width: mentionBadgeLayout.width, height: mentionBadgeLayout.height)
|
||||
|
||||
transition.updateFrame(node: strongSelf.mentionBadgeNode, frame: badgeFrame)
|
||||
nextBadgeX -= mentionBadgeLayout.width + 6.0
|
||||
}
|
||||
|
||||
if let currentPinnedIconImage = currentPinnedIconImage {
|
||||
@@ -3840,14 +3854,71 @@ public class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
strongSelf.pinnedIconNode.isHidden = false
|
||||
|
||||
let pinnedIconSize = currentPinnedIconImage.size
|
||||
let pinnedIconFrame = CGRect(x: contentRect.maxX - pinnedIconSize.width, y: contentRect.maxY - pinnedIconSize.height - 2.0, width: pinnedIconSize.width, height: pinnedIconSize.height)
|
||||
let pinnedIconFrame = CGRect(x: nextBadgeX - pinnedIconSize.width, y: contentRect.maxY - pinnedIconSize.height - 2.0, width: pinnedIconSize.width, height: pinnedIconSize.height)
|
||||
|
||||
strongSelf.pinnedIconNode.frame = pinnedIconFrame
|
||||
nextBadgeX -= pinnedIconSize.width + 6.0
|
||||
} else {
|
||||
strongSelf.pinnedIconNode.image = nil
|
||||
strongSelf.pinnedIconNode.isHidden = true
|
||||
}
|
||||
|
||||
if let (actionButtonTitleNodeLayout, apply) = actionButtonTitleNodeLayoutAndApply {
|
||||
let actionButtonSize = CGSize(width: actionButtonTitleNodeLayout.size.width + 12.0 * 2.0, height: actionButtonTitleNodeLayout.size.height + 5.0 + 4.0)
|
||||
let actionButtonFrame = CGRect(x: nextBadgeX - actionButtonSize.width, y: contentRect.maxY - actionButtonSize.height, width: actionButtonSize.width, height: actionButtonSize.height)
|
||||
|
||||
let actionButtonNode: HighlightableButtonNode
|
||||
if let current = strongSelf.actionButtonNode {
|
||||
actionButtonNode = current
|
||||
} else {
|
||||
actionButtonNode = HighlightableButtonNode()
|
||||
strongSelf.actionButtonNode = actionButtonNode
|
||||
strongSelf.mainContentContainerNode.addSubnode(actionButtonNode)
|
||||
actionButtonNode.addTarget(strongSelf, action: #selector(strongSelf.actionButtonPressed), forControlEvents: .touchUpInside)
|
||||
}
|
||||
|
||||
let actionButtonBackgroundView: UIImageView
|
||||
if let current = strongSelf.actionButtonBackgroundView {
|
||||
actionButtonBackgroundView = current
|
||||
} else {
|
||||
actionButtonBackgroundView = UIImageView()
|
||||
strongSelf.actionButtonBackgroundView = actionButtonBackgroundView
|
||||
actionButtonNode.view.addSubview(actionButtonBackgroundView)
|
||||
|
||||
if actionButtonBackgroundView.image?.size.height != actionButtonSize.height {
|
||||
actionButtonBackgroundView.image = generateStretchableFilledCircleImage(diameter: actionButtonSize.height, color: .white)?.withRenderingMode(.alwaysTemplate)
|
||||
}
|
||||
}
|
||||
|
||||
actionButtonBackgroundView.tintColor = theme.unreadBadgeActiveBackgroundColor
|
||||
|
||||
let actionButtonTitleNode = apply()
|
||||
if strongSelf.actionButtonTitleNode !== actionButtonTitleNode {
|
||||
strongSelf.actionButtonTitleNode?.removeFromSupernode()
|
||||
strongSelf.actionButtonTitleNode = actionButtonTitleNode
|
||||
actionButtonNode.addSubnode(actionButtonTitleNode)
|
||||
}
|
||||
|
||||
actionButtonNode.frame = actionButtonFrame
|
||||
actionButtonBackgroundView.frame = CGRect(origin: CGPoint(), size: actionButtonFrame.size)
|
||||
actionButtonTitleNode.frame = CGRect(origin: CGPoint(x: floorToScreenPixels((actionButtonFrame.width - actionButtonTitleNodeLayout.size.width) * 0.5), y: 5.0), size: actionButtonTitleNodeLayout.size)
|
||||
|
||||
nextBadgeX -= actionButtonSize.width + 6.0
|
||||
} else {
|
||||
if let actionButtonTitleNode = strongSelf.actionButtonTitleNode {
|
||||
actionButtonTitleNode.removeFromSupernode()
|
||||
strongSelf.actionButtonTitleNode = nil
|
||||
}
|
||||
if let actionButtonBackgroundView = strongSelf.actionButtonBackgroundView {
|
||||
actionButtonBackgroundView.removeFromSuperview()
|
||||
strongSelf.actionButtonBackgroundView = nil
|
||||
}
|
||||
if let actionButtonNode = strongSelf.actionButtonNode {
|
||||
actionButtonNode.removeFromSupernode()
|
||||
strongSelf.actionButtonNode = nil
|
||||
}
|
||||
}
|
||||
|
||||
var titleOffset: CGFloat = 0.0
|
||||
if let currentSecretIconImage = currentSecretIconImage {
|
||||
let iconNode: ASImageNode
|
||||
@@ -4495,6 +4566,18 @@ public class ChatListItemNode: ItemListRevealOptionsItemNode {
|
||||
item.interaction.openForumThread(index.messageIndex.id.peerId, topicItem.id)
|
||||
}
|
||||
|
||||
@objc private func actionButtonPressed() {
|
||||
guard let item else {
|
||||
return
|
||||
}
|
||||
guard case let .peer(peerData) = item.content else {
|
||||
return
|
||||
}
|
||||
if case let .user(user) = peerData.peer.peer, let botInfo = user.botInfo, botInfo.flags.contains(.hasWebApp) {
|
||||
item.interaction.openWebApp(user)
|
||||
}
|
||||
}
|
||||
|
||||
override public func animateInsertion(_ currentTimestamp: Double, duration: Double, options: ListViewItemAnimationOptions) {
|
||||
self.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.25)
|
||||
}
|
||||
|
||||
@@ -112,6 +112,7 @@ public final class ChatListNodeInteraction {
|
||||
let openStarsTopup: (Int64?) -> Void
|
||||
let dismissNotice: (ChatListNotice) -> Void
|
||||
let editPeer: (ChatListItem) -> Void
|
||||
let openWebApp: (TelegramUser) -> Void
|
||||
|
||||
public var searchTextHighightState: String?
|
||||
var highlightedChatLocation: ChatListHighlightedLocation?
|
||||
@@ -167,7 +168,8 @@ public final class ChatListNodeInteraction {
|
||||
openStories: @escaping (ChatListNode.OpenStoriesSubject, ASDisplayNode?) -> Void,
|
||||
openStarsTopup: @escaping (Int64?) -> Void,
|
||||
dismissNotice: @escaping (ChatListNotice) -> Void,
|
||||
editPeer: @escaping (ChatListItem) -> Void
|
||||
editPeer: @escaping (ChatListItem) -> Void,
|
||||
openWebApp: @escaping (TelegramUser) -> Void
|
||||
) {
|
||||
self.activateSearch = activateSearch
|
||||
self.peerSelected = peerSelected
|
||||
@@ -211,6 +213,7 @@ public final class ChatListNodeInteraction {
|
||||
self.openStarsTopup = openStarsTopup
|
||||
self.dismissNotice = dismissNotice
|
||||
self.editPeer = editPeer
|
||||
self.openWebApp = openWebApp
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1220,6 +1223,7 @@ public final class ChatListNode: ListView {
|
||||
public var openBirthdaySetup: (() -> Void)?
|
||||
public var openPremiumManagement: (() -> Void)?
|
||||
public var openStarsTopup: ((Int64?) -> Void)?
|
||||
public var openWebApp: ((TelegramUser) -> Void)?
|
||||
|
||||
private var theme: PresentationTheme
|
||||
|
||||
@@ -1867,6 +1871,11 @@ public final class ChatListNode: ListView {
|
||||
break
|
||||
}
|
||||
}, editPeer: { _ in
|
||||
}, openWebApp: { [weak self] user in
|
||||
guard let self else {
|
||||
return
|
||||
}
|
||||
self.openWebApp?(user)
|
||||
})
|
||||
nodeInteraction.isInlineMode = isInlineMode
|
||||
|
||||
|
||||
Reference in New Issue
Block a user