mirror of
https://github.com/Swiftgram/Telegram-iOS.git
synced 2025-06-16 05:55:20 +00:00
Animated emoji autocompletion
This commit is contained in:
parent
eaf0b74f1b
commit
89ecb672c7
@ -469,7 +469,7 @@ public enum ChatPresentationInputQueryResult: Equatable {
|
||||
case hashtags([String])
|
||||
case mentions([EnginePeer])
|
||||
case commands([PeerCommand])
|
||||
case emojis([(String, String)], NSRange)
|
||||
case emojis([(String, TelegramMediaFile?, String)], NSRange)
|
||||
case contextRequestResult(EnginePeer?, ChatContextResultCollection?)
|
||||
|
||||
public static func ==(lhs: ChatPresentationInputQueryResult, rhs: ChatPresentationInputQueryResult) -> Bool {
|
||||
@ -513,7 +513,13 @@ public enum ChatPresentationInputQueryResult: Equatable {
|
||||
return false
|
||||
}
|
||||
for i in 0 ..< lhsValue.count {
|
||||
if lhsValue[i] != rhsValue[i] {
|
||||
if lhsValue[i].0 != rhsValue[i].0 {
|
||||
return false
|
||||
}
|
||||
if lhsValue[i].1?.fileId != rhsValue[i].1?.fileId {
|
||||
return false
|
||||
}
|
||||
if lhsValue[i].2 != rhsValue[i].2 {
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
@ -412,7 +412,7 @@ public class AttachmentTextInputPanelNode: ASDisplayNode, TGCaptionPanelView, AS
|
||||
return UIView()
|
||||
}
|
||||
|
||||
return EmojiTextAttachmentView(context: context, emoji: emoji, file: emoji.file, cache: strongSelf.animationCache, renderer: strongSelf.animationRenderer, placeholderColor: presentationInterfaceState.theme.chat.inputPanel.inputTextColor.withAlphaComponent(0.12))
|
||||
return EmojiTextAttachmentView(context: context, emoji: emoji, file: emoji.file, cache: strongSelf.animationCache, renderer: strongSelf.animationRenderer, placeholderColor: presentationInterfaceState.theme.chat.inputPanel.inputTextColor.withAlphaComponent(0.12), pointSize: CGSize(width: 24.0, height: 24.0))
|
||||
}
|
||||
|
||||
self.updateSendButtonEnabled(isCaption || isAttachment, animated: false)
|
||||
|
@ -249,8 +249,8 @@ public final class InlineStickerItemLayer: MultiAnimationRenderTarget {
|
||||
public final class EmojiTextAttachmentView: UIView {
|
||||
private let contentLayer: InlineStickerItemLayer
|
||||
|
||||
public init(context: AccountContext, emoji: ChatTextInputTextCustomEmojiAttribute, file: TelegramMediaFile?, cache: AnimationCache, renderer: MultiAnimationRenderer, placeholderColor: UIColor) {
|
||||
self.contentLayer = InlineStickerItemLayer(context: context, attemptSynchronousLoad: true, emoji: emoji, file: file, cache: cache, renderer: renderer, placeholderColor: placeholderColor, pointSize: CGSize(width: 24.0, height: 24.0))
|
||||
public init(context: AccountContext, emoji: ChatTextInputTextCustomEmojiAttribute, file: TelegramMediaFile?, cache: AnimationCache, renderer: MultiAnimationRenderer, placeholderColor: UIColor, pointSize: CGSize) {
|
||||
self.contentLayer = InlineStickerItemLayer(context: context, attemptSynchronousLoad: true, emoji: emoji, file: file, cache: cache, renderer: renderer, placeholderColor: placeholderColor, pointSize: pointSize)
|
||||
|
||||
super.init(frame: CGRect())
|
||||
|
||||
|
@ -350,7 +350,7 @@ public final class EmojiPagerContentComponent: Component {
|
||||
var premiumButtonInset: CGFloat
|
||||
var premiumButtonHeight: CGFloat
|
||||
|
||||
init(width: CGFloat, containerInsets: UIEdgeInsets, itemGroups: [ItemGroupDescription], itemLayoutType: ItemLayoutType, expandedPremiumGroups: Set<AnyHashable>) {
|
||||
init(width: CGFloat, containerInsets: UIEdgeInsets, itemGroups: [ItemGroupDescription], itemLayoutType: ItemLayoutType) {
|
||||
self.width = width
|
||||
self.containerInsets = containerInsets
|
||||
|
||||
@ -392,7 +392,7 @@ public final class EmojiPagerContentComponent: Component {
|
||||
|
||||
let numRowsInGroup = (itemGroup.itemCount + (self.itemsPerRow - 1)) / self.itemsPerRow
|
||||
var groupContentSize = CGSize(width: width, height: itemTopOffset + CGFloat(numRowsInGroup) * self.visibleItemSize + CGFloat(max(0, numRowsInGroup - 1)) * self.verticalSpacing)
|
||||
if itemGroup.isPremium && expandedPremiumGroups.contains(itemGroup.groupId) {
|
||||
if itemGroup.isPremium {
|
||||
groupContentSize.height += self.premiumButtonInset + self.premiumButtonHeight
|
||||
}
|
||||
self.itemGroupLayouts.append(ItemGroupLayout(
|
||||
@ -765,7 +765,6 @@ public final class EmojiPagerContentComponent: Component {
|
||||
private var visibleGroupHeaders: [AnyHashable: GroupHeaderLayer] = [:]
|
||||
private var visibleGroupBorders: [AnyHashable: GroupBorderLayer] = [:]
|
||||
private var visibleGroupPremiumButtons: [AnyHashable: ComponentView<Empty>] = [:]
|
||||
private var expandedPremiumGroups: Set<AnyHashable> = Set()
|
||||
private var ignoreScrolling: Bool = false
|
||||
private var keepTopPanelVisibleUntilScrollingInput: Bool = false
|
||||
|
||||
@ -1034,7 +1033,8 @@ public final class EmojiPagerContentComponent: Component {
|
||||
let locationInScrollView = recognizer.location(in: self.scrollView)
|
||||
outer: for (id, groupHeader) in self.visibleGroupHeaders {
|
||||
if groupHeader.frame.insetBy(dx: -10.0, dy: -6.0).contains(locationInScrollView) {
|
||||
for group in component.itemGroups {
|
||||
let _ = id
|
||||
/*for group in component.itemGroups {
|
||||
if group.groupId == id {
|
||||
if group.isPremium && !self.expandedPremiumGroups.contains(id) {
|
||||
if self.expandedPremiumGroups.contains(id) {
|
||||
@ -1059,7 +1059,7 @@ public final class EmojiPagerContentComponent: Component {
|
||||
break outer
|
||||
}
|
||||
}
|
||||
}
|
||||
}*/
|
||||
}
|
||||
}
|
||||
|
||||
@ -1288,7 +1288,7 @@ public final class EmojiPagerContentComponent: Component {
|
||||
}
|
||||
groupBorderTransition.setFrame(layer: groupBorderLayer, frame: groupBorderFrame)
|
||||
|
||||
if self.expandedPremiumGroups.contains(itemGroup.groupId) {
|
||||
if itemGroup.isPremium {
|
||||
validGroupPremiumButtonIds.insert(itemGroup.groupId)
|
||||
|
||||
let groupPremiumButton: ComponentView<Empty>
|
||||
@ -1562,7 +1562,7 @@ public final class EmojiPagerContentComponent: Component {
|
||||
|
||||
var itemTransition = transition
|
||||
|
||||
let itemLayout = ItemLayout(width: availableSize.width, containerInsets: UIEdgeInsets(top: pagerEnvironment.containerInsets.top + 9.0, left: pagerEnvironment.containerInsets.left + 12.0, bottom: 9.0 + pagerEnvironment.containerInsets.bottom, right: pagerEnvironment.containerInsets.right + 12.0), itemGroups: itemGroups, itemLayoutType: component.itemLayoutType, expandedPremiumGroups: expandedPremiumGroups)
|
||||
let itemLayout = ItemLayout(width: availableSize.width, containerInsets: UIEdgeInsets(top: pagerEnvironment.containerInsets.top + 9.0, left: pagerEnvironment.containerInsets.left + 12.0, bottom: 9.0 + pagerEnvironment.containerInsets.bottom, right: pagerEnvironment.containerInsets.right + 12.0), itemGroups: itemGroups, itemLayoutType: component.itemLayoutType)
|
||||
if let previousItemLayout = self.itemLayout {
|
||||
if previousItemLayout.width != itemLayout.width {
|
||||
itemTransition = .immediate
|
||||
|
@ -1331,7 +1331,7 @@ class ChatControllerNode: ASDisplayNode, UIScrollViewDelegate {
|
||||
let (duration, curve) = listViewAnimationDurationAndCurve(transition: transition)
|
||||
|
||||
var immediatelyLayoutInputContextPanelAndAnimateAppearance = false
|
||||
if let inputContextPanelNode = inputContextPanelForChatPresentationIntefaceState(self.chatPresentationInterfaceState, context: self.context, currentPanel: self.inputContextPanelNode, controllerInteraction: self.controllerInteraction, interfaceInteraction: self.interfaceInteraction) {
|
||||
if let inputContextPanelNode = inputContextPanelForChatPresentationIntefaceState(self.chatPresentationInterfaceState, context: self.context, currentPanel: self.inputContextPanelNode, controllerInteraction: self.controllerInteraction, interfaceInteraction: self.interfaceInteraction, chatPresentationContext: self.controllerInteraction.presentationContext) {
|
||||
if inputContextPanelNode !== self.inputContextPanelNode {
|
||||
dismissedInputContextPanelNode = self.inputContextPanelNode
|
||||
self.inputContextPanelNode = inputContextPanelNode
|
||||
@ -1345,7 +1345,7 @@ class ChatControllerNode: ASDisplayNode, UIScrollViewDelegate {
|
||||
}
|
||||
|
||||
var immediatelyLayoutOverlayContextPanelAndAnimateAppearance = false
|
||||
if let overlayContextPanelNode = chatOverlayContextPanelForChatPresentationIntefaceState(self.chatPresentationInterfaceState, context: self.context, currentPanel: self.overlayContextPanelNode, interfaceInteraction: self.interfaceInteraction) {
|
||||
if let overlayContextPanelNode = chatOverlayContextPanelForChatPresentationIntefaceState(self.chatPresentationInterfaceState, context: self.context, currentPanel: self.overlayContextPanelNode, interfaceInteraction: self.interfaceInteraction, chatPresentationContext: self.controllerInteraction.presentationContext) {
|
||||
if overlayContextPanelNode !== self.overlayContextPanelNode {
|
||||
dismissedOverlayContextPanelNode = self.overlayContextPanelNode
|
||||
self.overlayContextPanelNode = overlayContextPanelNode
|
||||
|
@ -20,7 +20,7 @@ class ChatInputContextPanelNode: ASDisplayNode {
|
||||
var theme: PresentationTheme
|
||||
var fontSize: PresentationFontSize
|
||||
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.context = context
|
||||
self.theme = theme
|
||||
self.fontSize = fontSize
|
||||
|
@ -25,7 +25,7 @@ private func inputQueryResultPriority(_ result: ChatPresentationInputQueryResult
|
||||
}
|
||||
}
|
||||
|
||||
func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfaceState: ChatPresentationInterfaceState, context: AccountContext, currentPanel: ChatInputContextPanelNode?, controllerInteraction: ChatControllerInteraction?, interfaceInteraction: ChatPanelInterfaceInteraction?) -> ChatInputContextPanelNode? {
|
||||
func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfaceState: ChatPresentationInterfaceState, context: AccountContext, currentPanel: ChatInputContextPanelNode?, controllerInteraction: ChatControllerInteraction, interfaceInteraction: ChatPanelInterfaceInteraction?, chatPresentationContext: ChatPresentationContext) -> ChatInputContextPanelNode? {
|
||||
guard let _ = chatPresentationInterfaceState.renderedPeer?.peer else {
|
||||
return nil
|
||||
}
|
||||
@ -34,7 +34,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
if let currentPanel = currentPanel as? CommandMenuChatInputContextPanelNode {
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = CommandMenuChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, peerId: renderedPeer.peerId)
|
||||
let panel = CommandMenuChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, peerId: renderedPeer.peerId, chatPresentationContext: chatPresentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
return panel
|
||||
}
|
||||
@ -68,7 +68,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
if let currentPanel = currentPanel as? DisabledContextResultsChatInputContextPanelNode {
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = DisabledContextResultsChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize)
|
||||
let panel = DisabledContextResultsChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, chatPresentationContext: controllerInteraction.presentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
return panel
|
||||
}
|
||||
@ -86,7 +86,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
currentPanel.updateResults(results: results.map({ $0.file }), query: query)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = InlineReactionSearchPanel(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, peerId: chatPresentationInterfaceState.renderedPeer?.peerId)
|
||||
let panel = InlineReactionSearchPanel(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, peerId: chatPresentationInterfaceState.renderedPeer?.peerId, chatPresentationContext: chatPresentationContext)
|
||||
panel.controllerInteraction = controllerInteraction
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(results: results.map({ $0.file }), query: query)
|
||||
@ -99,7 +99,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
currentPanel.updateResults(results)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = HashtagChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize)
|
||||
let panel = HashtagChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, chatPresentationContext: controllerInteraction.presentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(results)
|
||||
return panel
|
||||
@ -111,7 +111,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
currentPanel.updateResults(results)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = EmojisChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize)
|
||||
let panel = EmojisChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, chatPresentationContext: chatPresentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(results)
|
||||
return panel
|
||||
@ -123,7 +123,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
currentPanel.updateResults(peers)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = MentionChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, mode: .input)
|
||||
let panel = MentionChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, mode: .input, chatPresentationContext: chatPresentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(peers)
|
||||
return panel
|
||||
@ -137,7 +137,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
currentPanel.updateResults(commands)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = CommandChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize)
|
||||
let panel = CommandChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, chatPresentationContext: controllerInteraction.presentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(commands)
|
||||
return panel
|
||||
@ -153,7 +153,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
currentPanel.updateResults(results)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = VerticalListContextResultsChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize)
|
||||
let panel = VerticalListContextResultsChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, chatPresentationContext: controllerInteraction.presentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(results)
|
||||
return panel
|
||||
@ -163,7 +163,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
currentPanel.updateResults(results)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = HorizontalListContextResultsChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize)
|
||||
let panel = HorizontalListContextResultsChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, chatPresentationContext: controllerInteraction.presentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(results)
|
||||
return panel
|
||||
@ -177,7 +177,7 @@ func inputContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfa
|
||||
return nil
|
||||
}
|
||||
|
||||
func chatOverlayContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfaceState: ChatPresentationInterfaceState, context: AccountContext, currentPanel: ChatInputContextPanelNode?, interfaceInteraction: ChatPanelInterfaceInteraction?) -> ChatInputContextPanelNode? {
|
||||
func chatOverlayContextPanelForChatPresentationIntefaceState(_ chatPresentationInterfaceState: ChatPresentationInterfaceState, context: AccountContext, currentPanel: ChatInputContextPanelNode?, interfaceInteraction: ChatPanelInterfaceInteraction?, chatPresentationContext: ChatPresentationContext) -> ChatInputContextPanelNode? {
|
||||
guard let searchQuerySuggestionResult = chatPresentationInterfaceState.searchQuerySuggestionResult, let _ = chatPresentationInterfaceState.renderedPeer?.peer else {
|
||||
return nil
|
||||
}
|
||||
@ -189,7 +189,7 @@ func chatOverlayContextPanelForChatPresentationIntefaceState(_ chatPresentationI
|
||||
currentPanel.updateResults(peers)
|
||||
return currentPanel
|
||||
} else {
|
||||
let panel = MentionChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, mode: .search)
|
||||
let panel = MentionChatInputContextPanelNode(context: context, theme: chatPresentationInterfaceState.theme, strings: chatPresentationInterfaceState.strings, fontSize: chatPresentationInterfaceState.fontSize, mode: .search, chatPresentationContext: chatPresentationContext)
|
||||
panel.interfaceInteraction = interfaceInteraction
|
||||
panel.updateResults(peers)
|
||||
return panel
|
||||
|
@ -341,21 +341,61 @@ private func updatedContextQueryResultStateForQuery(context: AccountContext, pee
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
let hasPremium = context.engine.data.subscribe(TelegramEngine.EngineData.Item.Peer.Peer(id: context.account.peerId))
|
||||
|> map { peer -> Bool in
|
||||
guard case let .user(user) = peer else {
|
||||
return false
|
||||
}
|
||||
return user.isPremium
|
||||
}
|
||||
|> distinctUntilChanged
|
||||
|
||||
return signal
|
||||
|> map { keywords -> [(String, String)] in
|
||||
var result: [(String, String)] = []
|
||||
for keyword in keywords {
|
||||
for emoticon in keyword.emoticons {
|
||||
result.append((emoticon, keyword.keyword))
|
||||
}
|
||||
}
|
||||
return result
|
||||
}
|
||||
|> map { result -> (ChatPresentationInputQueryResult?) -> ChatPresentationInputQueryResult? in
|
||||
return { _ in return .emojis(result, range) }
|
||||
}
|
||||
|> castError(ChatContextQueryError.self)
|
||||
|> mapToSignal { keywords -> Signal<(ChatPresentationInputQueryResult?) -> ChatPresentationInputQueryResult?, ChatContextQueryError> in
|
||||
return combineLatest(
|
||||
context.account.postbox.itemCollectionsView(orderedItemListCollectionIds: [], namespaces: [Namespaces.ItemCollection.CloudEmojiPacks], aroundIndex: nil, count: 10000000),
|
||||
hasPremium
|
||||
)
|
||||
|> map { view, hasPremium -> [(String, TelegramMediaFile?, String)] in
|
||||
var result: [(String, TelegramMediaFile?, String)] = []
|
||||
|
||||
var allEmoticons: [String: String] = [:]
|
||||
for keyword in keywords {
|
||||
for emoticon in keyword.emoticons {
|
||||
allEmoticons[emoticon] = keyword.keyword
|
||||
}
|
||||
}
|
||||
|
||||
for entry in view.entries {
|
||||
guard let item = entry.item as? StickerPackItem else {
|
||||
continue
|
||||
}
|
||||
for attribute in item.file.attributes {
|
||||
switch attribute {
|
||||
case let .CustomEmoji(_, alt, _):
|
||||
if !alt.isEmpty, let keyword = allEmoticons[alt] {
|
||||
result.append((alt, item.file, keyword))
|
||||
}
|
||||
default:
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for keyword in keywords {
|
||||
for emoticon in keyword.emoticons {
|
||||
result.append((emoticon, nil, keyword.keyword))
|
||||
}
|
||||
}
|
||||
return result
|
||||
}
|
||||
|> map { result -> (ChatPresentationInputQueryResult?) -> ChatPresentationInputQueryResult? in
|
||||
return { _ in return .emojis(result, range) }
|
||||
}
|
||||
|> castError(ChatContextQueryError.self)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -802,7 +802,7 @@ class ChatTextInputPanelNode: ChatInputPanelNode, ASEditableTextNodeDelegate {
|
||||
return UIView()
|
||||
}
|
||||
|
||||
return EmojiTextAttachmentView(context: context, emoji: emoji, file: emoji.file, cache: presentationContext.animationCache, renderer: presentationContext.animationRenderer, placeholderColor: presentationInterfaceState.theme.chat.inputPanel.inputTextColor.withAlphaComponent(0.12))
|
||||
return EmojiTextAttachmentView(context: context, emoji: emoji, file: emoji.file, cache: presentationContext.animationCache, renderer: presentationContext.animationRenderer, placeholderColor: presentationInterfaceState.theme.chat.inputPanel.inputTextColor.withAlphaComponent(0.12), pointSize: CGSize(width: 24.0, height: 24.0))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -63,7 +63,7 @@ final class CommandChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
private var enqueuedTransitions: [(CommandChatInputContextPanelTransition, Bool)] = []
|
||||
private var validLayout: (CGSize, CGFloat, CGFloat, CGFloat)?
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.listView = ListView()
|
||||
self.listView.isOpaque = false
|
||||
self.listView.stackFromBottom = true
|
||||
@ -74,7 +74,7 @@ final class CommandChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
return strings.VoiceOver_ScrollStatus(row, count).string
|
||||
}
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
@ -66,7 +66,7 @@ final class CommandMenuChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
|
||||
private let disposable = MetaDisposable()
|
||||
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, peerId: PeerId) {
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, peerId: PeerId, chatPresentationContext: ChatPresentationContext) {
|
||||
self.listView = ListView()
|
||||
self.listView.clipsToBounds = false
|
||||
self.listView.isOpaque = false
|
||||
@ -77,7 +77,7 @@ final class CommandMenuChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
return strings.VoiceOver_ScrollStatus(row, count).string
|
||||
}
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
@ -16,14 +16,14 @@ final class DisabledContextResultsChatInputContextPanelNode: ChatInputContextPan
|
||||
|
||||
private var validLayout: (CGSize, CGFloat, CGFloat, CGFloat)?
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.containerNode = ASDisplayNode()
|
||||
self.separatorNode = ASDisplayNode()
|
||||
self.textNode = ImmediateTextNode()
|
||||
self.textNode.maximumNumberOfLines = 0
|
||||
self.textNode.textAlignment = .center
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
@ -10,9 +10,13 @@ import MergeLists
|
||||
import AccountContext
|
||||
import Emoji
|
||||
import ChatPresentationInterfaceState
|
||||
import AnimationCache
|
||||
import MultiAnimationRenderer
|
||||
import TextFormat
|
||||
|
||||
private struct EmojisChatInputContextPanelEntryStableId: Hashable, Equatable {
|
||||
let symbol: String
|
||||
private enum EmojisChatInputContextPanelEntryStableId: Hashable, Equatable {
|
||||
case symbol(String)
|
||||
case media(MediaId)
|
||||
}
|
||||
|
||||
private func backgroundCenterImage(_ theme: PresentationTheme) -> UIImage? {
|
||||
@ -55,25 +59,30 @@ private struct EmojisChatInputContextPanelEntry: Comparable, Identifiable {
|
||||
let theme: PresentationTheme
|
||||
let symbol: String
|
||||
let text: String
|
||||
let file: TelegramMediaFile?
|
||||
|
||||
var stableId: EmojisChatInputContextPanelEntryStableId {
|
||||
return EmojisChatInputContextPanelEntryStableId(symbol: self.symbol)
|
||||
if let file = self.file {
|
||||
return .media(file.fileId)
|
||||
} else {
|
||||
return .symbol(self.symbol)
|
||||
}
|
||||
}
|
||||
|
||||
func withUpdatedTheme(_ theme: PresentationTheme) -> EmojisChatInputContextPanelEntry {
|
||||
return EmojisChatInputContextPanelEntry(index: self.index, theme: theme, symbol: self.symbol, text: self.text)
|
||||
return EmojisChatInputContextPanelEntry(index: self.index, theme: theme, symbol: self.symbol, text: self.text, file: self.file)
|
||||
}
|
||||
|
||||
static func ==(lhs: EmojisChatInputContextPanelEntry, rhs: EmojisChatInputContextPanelEntry) -> Bool {
|
||||
return lhs.index == rhs.index && lhs.symbol == rhs.symbol && lhs.text == rhs.text && lhs.theme === rhs.theme
|
||||
return lhs.index == rhs.index && lhs.symbol == rhs.symbol && lhs.text == rhs.text && lhs.theme === rhs.theme && lhs.file?.fileId == rhs.file?.fileId
|
||||
}
|
||||
|
||||
static func <(lhs: EmojisChatInputContextPanelEntry, rhs: EmojisChatInputContextPanelEntry) -> Bool {
|
||||
return lhs.index < rhs.index
|
||||
}
|
||||
|
||||
func item(account: Account, emojiSelected: @escaping (String) -> Void) -> ListViewItem {
|
||||
return EmojisChatInputPanelItem(theme: self.theme, symbol: self.symbol, text: self.text, emojiSelected: emojiSelected)
|
||||
func item(context: AccountContext, animationCache: AnimationCache, animationRenderer: MultiAnimationRenderer, emojiSelected: @escaping (String, TelegramMediaFile?) -> Void) -> ListViewItem {
|
||||
return EmojisChatInputPanelItem(context: context, theme: self.theme, symbol: self.symbol, text: self.text, file: self.file, animationCache: animationCache, animationRenderer: animationRenderer, emojiSelected: emojiSelected)
|
||||
}
|
||||
}
|
||||
|
||||
@ -83,12 +92,12 @@ private struct EmojisChatInputContextPanelTransition {
|
||||
let updates: [ListViewUpdateItem]
|
||||
}
|
||||
|
||||
private func preparedTransition(from fromEntries: [EmojisChatInputContextPanelEntry], to toEntries: [EmojisChatInputContextPanelEntry], account: Account, emojiSelected: @escaping (String) -> Void) -> EmojisChatInputContextPanelTransition {
|
||||
private func preparedTransition(from fromEntries: [EmojisChatInputContextPanelEntry], to toEntries: [EmojisChatInputContextPanelEntry], context: AccountContext, animationCache: AnimationCache, animationRenderer: MultiAnimationRenderer, emojiSelected: @escaping (String, TelegramMediaFile?) -> Void) -> EmojisChatInputContextPanelTransition {
|
||||
let (deleteIndices, indicesAndItems, updateIndices) = mergeListsStableWithUpdates(leftList: fromEntries, rightList: toEntries)
|
||||
|
||||
let deletions = deleteIndices.map { ListViewDeleteItem(index: $0, directionHint: nil) }
|
||||
let insertions = indicesAndItems.map { ListViewInsertItem(index: $0.0, previousIndex: $0.2, item: $0.1.item(account: account, emojiSelected: emojiSelected), directionHint: nil) }
|
||||
let updates = updateIndices.map { ListViewUpdateItem(index: $0.0, previousIndex: $0.2, item: $0.1.item(account: account, emojiSelected: emojiSelected), directionHint: nil) }
|
||||
let insertions = indicesAndItems.map { ListViewInsertItem(index: $0.0, previousIndex: $0.2, item: $0.1.item(context: context, animationCache: animationCache, animationRenderer: animationRenderer, emojiSelected: emojiSelected), directionHint: nil) }
|
||||
let updates = updateIndices.map { ListViewUpdateItem(index: $0.0, previousIndex: $0.2, item: $0.1.item(context: context, animationCache: animationCache, animationRenderer: animationRenderer, emojiSelected: emojiSelected), directionHint: nil) }
|
||||
|
||||
return EmojisChatInputContextPanelTransition(deletions: deletions, insertions: insertions, updates: updates)
|
||||
}
|
||||
@ -106,7 +115,13 @@ final class EmojisChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
private var validLayout: (CGSize, CGFloat, CGFloat, CGFloat)?
|
||||
private var presentationInterfaceState: ChatPresentationInterfaceState?
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
private let animationCache: AnimationCache
|
||||
private let animationRenderer: MultiAnimationRenderer
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.animationCache = chatPresentationContext.animationCache
|
||||
self.animationRenderer = chatPresentationContext.animationRenderer
|
||||
|
||||
self.backgroundNode = ASImageNode()
|
||||
self.backgroundNode.displayWithoutProcessing = true
|
||||
self.backgroundNode.displaysAsynchronously = false
|
||||
@ -134,7 +149,7 @@ final class EmojisChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
return strings.VoiceOver_ScrollStatus(row, count).string
|
||||
}
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.placement = .overTextInput
|
||||
self.isOpaque = false
|
||||
@ -147,12 +162,12 @@ final class EmojisChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
self.clippingNode.addSubnode(self.listView)
|
||||
}
|
||||
|
||||
func updateResults(_ results: [(String, String)]) {
|
||||
func updateResults(_ results: [(String, TelegramMediaFile?, String)]) {
|
||||
var entries: [EmojisChatInputContextPanelEntry] = []
|
||||
var index = 0
|
||||
var stableIds = Set<EmojisChatInputContextPanelEntryStableId>()
|
||||
for (symbol, text) in results {
|
||||
let entry = EmojisChatInputContextPanelEntry(index: index, theme: self.theme, symbol: symbol.normalizedEmoji, text: text)
|
||||
for (symbol, file, text) in results {
|
||||
let entry = EmojisChatInputContextPanelEntry(index: index, theme: self.theme, symbol: symbol.normalizedEmoji, text: text, file: file)
|
||||
if stableIds.contains(entry.stableId) {
|
||||
continue
|
||||
}
|
||||
@ -165,33 +180,54 @@ final class EmojisChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
|
||||
private func prepareTransition(from: [EmojisChatInputContextPanelEntry]? , to: [EmojisChatInputContextPanelEntry]) {
|
||||
let firstTime = self.currentEntries == nil
|
||||
let transition = preparedTransition(from: from ?? [], to: to, account: self.context.account, emojiSelected: { [weak self] text in
|
||||
if let strongSelf = self, let interfaceInteraction = strongSelf.interfaceInteraction {
|
||||
interfaceInteraction.updateTextInputStateAndMode { textInputState, inputMode in
|
||||
var hashtagQueryRange: NSRange?
|
||||
inner: for (range, type, _) in textInputStateContextQueryRangeAndType(textInputState) {
|
||||
if type == [.emojiSearch] {
|
||||
var range = range
|
||||
range.location -= 1
|
||||
range.length += 1
|
||||
hashtagQueryRange = range
|
||||
break inner
|
||||
let transition = preparedTransition(from: from ?? [], to: to, context: self.context, animationCache: self.animationCache, animationRenderer: self.animationRenderer, emojiSelected: { [weak self] text, file in
|
||||
guard let strongSelf = self, let interfaceInteraction = strongSelf.interfaceInteraction else {
|
||||
return
|
||||
}
|
||||
|
||||
var text = text
|
||||
|
||||
interfaceInteraction.updateTextInputStateAndMode { textInputState, inputMode in
|
||||
var hashtagQueryRange: NSRange?
|
||||
inner: for (range, type, _) in textInputStateContextQueryRangeAndType(textInputState) {
|
||||
if type == [.emojiSearch] {
|
||||
var range = range
|
||||
range.location -= 1
|
||||
range.length += 1
|
||||
hashtagQueryRange = range
|
||||
break inner
|
||||
}
|
||||
}
|
||||
|
||||
if let range = hashtagQueryRange {
|
||||
let inputText = NSMutableAttributedString(attributedString: textInputState.inputText)
|
||||
|
||||
var emojiAttribute: ChatTextInputTextCustomEmojiAttribute?
|
||||
if let file = file {
|
||||
loop: for attribute in file.attributes {
|
||||
switch attribute {
|
||||
case let .CustomEmoji(_, displayText, packReference):
|
||||
text = displayText
|
||||
emojiAttribute = ChatTextInputTextCustomEmojiAttribute(stickerPack: packReference, fileId: file.fileId.id, file: file)
|
||||
break loop
|
||||
default:
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if let range = hashtagQueryRange {
|
||||
let inputText = NSMutableAttributedString(attributedString: textInputState.inputText)
|
||||
|
||||
let replacementText = text
|
||||
|
||||
inputText.replaceCharacters(in: range, with: replacementText)
|
||||
|
||||
let selectionPosition = range.lowerBound + (replacementText as NSString).length
|
||||
|
||||
return (ChatTextInputState(inputText: inputText, selectionRange: selectionPosition ..< selectionPosition), inputMode)
|
||||
var replacementText = NSAttributedString(string: text)
|
||||
if let emojiAttribute = emojiAttribute {
|
||||
replacementText = NSAttributedString(string: text, attributes: [ChatTextInputAttributes.customEmoji: emojiAttribute])
|
||||
}
|
||||
return (textInputState, inputMode)
|
||||
|
||||
inputText.replaceCharacters(in: range, with: replacementText)
|
||||
|
||||
let selectionPosition = range.lowerBound + (replacementText.string as NSString).length
|
||||
|
||||
return (ChatTextInputState(inputText: inputText, selectionRange: selectionPosition ..< selectionPosition), inputMode)
|
||||
}
|
||||
return (textInputState, inputMode)
|
||||
}
|
||||
})
|
||||
self.currentEntries = to
|
||||
|
@ -6,19 +6,32 @@ import TelegramCore
|
||||
import SwiftSignalKit
|
||||
import Postbox
|
||||
import TelegramPresentationData
|
||||
import AnimationCache
|
||||
import MultiAnimationRenderer
|
||||
import EmojiTextAttachmentView
|
||||
import AccountContext
|
||||
import TextFormat
|
||||
|
||||
final class EmojisChatInputPanelItem: ListViewItem {
|
||||
fileprivate let context: AccountContext
|
||||
fileprivate let theme: PresentationTheme
|
||||
fileprivate let symbol: String
|
||||
fileprivate let text: String
|
||||
private let emojiSelected: (String) -> Void
|
||||
fileprivate let file: TelegramMediaFile?
|
||||
fileprivate let animationCache: AnimationCache
|
||||
fileprivate let animationRenderer: MultiAnimationRenderer
|
||||
private let emojiSelected: (String, TelegramMediaFile?) -> Void
|
||||
|
||||
let selectable: Bool = true
|
||||
|
||||
public init(theme: PresentationTheme, symbol: String, text: String, emojiSelected: @escaping (String) -> Void) {
|
||||
public init(context: AccountContext, theme: PresentationTheme, symbol: String, text: String, file: TelegramMediaFile?, animationCache: AnimationCache, animationRenderer: MultiAnimationRenderer, emojiSelected: @escaping (String, TelegramMediaFile?) -> Void) {
|
||||
self.context = context
|
||||
self.theme = theme
|
||||
self.symbol = symbol
|
||||
self.text = text
|
||||
self.file = file
|
||||
self.animationCache = animationCache
|
||||
self.animationRenderer = animationRenderer
|
||||
self.emojiSelected = emojiSelected
|
||||
}
|
||||
|
||||
@ -70,7 +83,7 @@ final class EmojisChatInputPanelItem: ListViewItem {
|
||||
}
|
||||
|
||||
func selected(listView: ListView) {
|
||||
self.emojiSelected(self.symbol)
|
||||
self.emojiSelected(self.symbol, self.file)
|
||||
}
|
||||
}
|
||||
|
||||
@ -79,6 +92,7 @@ private let textFont = Font.regular(32.0)
|
||||
final class EmojisChatInputPanelItemNode: ListViewItemNode {
|
||||
static let itemSize = CGSize(width: 45.0, height: 45.0)
|
||||
private let symbolNode: TextNode
|
||||
private var emojiView: EmojiTextAttachmentView?
|
||||
|
||||
init() {
|
||||
self.symbolNode = TextNode()
|
||||
@ -111,6 +125,45 @@ final class EmojisChatInputPanelItemNode: ListViewItemNode {
|
||||
if let strongSelf = self {
|
||||
let _ = symbolApply()
|
||||
strongSelf.symbolNode.frame = CGRect(origin: CGPoint(x: floorToScreenPixels((EmojisChatInputPanelItemNode.itemSize.width - symbolLayout.size.width) / 2.0), y: 0.0), size: symbolLayout.size)
|
||||
|
||||
if let file = item.file {
|
||||
strongSelf.symbolNode.isHidden = true
|
||||
|
||||
let emojiView: EmojiTextAttachmentView
|
||||
if let current = strongSelf.emojiView {
|
||||
emojiView = current
|
||||
} else {
|
||||
emojiView = EmojiTextAttachmentView(
|
||||
context: item.context,
|
||||
emoji: ChatTextInputTextCustomEmojiAttribute(
|
||||
stickerPack: nil,
|
||||
fileId: file.fileId.id,
|
||||
file: file
|
||||
),
|
||||
file: file,
|
||||
cache: item.animationCache,
|
||||
renderer: item.animationRenderer,
|
||||
placeholderColor: item.theme.list.mediaPlaceholderColor,
|
||||
pointSize: CGSize(width: 40.0, height: 40.0)
|
||||
)
|
||||
emojiView.layer.transform = CATransform3DMakeRotation(CGFloat.pi / 2.0, 0.0, 0.0, 1.0)
|
||||
strongSelf.emojiView = emojiView
|
||||
strongSelf.view.addSubview(emojiView)
|
||||
|
||||
let emojiSize = CGSize(width: 40.0, height: 40.0)
|
||||
let emojiFrame = CGRect(origin: CGPoint(x: floorToScreenPixels((EmojisChatInputPanelItemNode.itemSize.width - emojiSize.width) / 2.0) + 1.0, y: floorToScreenPixels((EmojisChatInputPanelItemNode.itemSize.height - emojiSize.height) / 2.0)), size: emojiSize)
|
||||
|
||||
emojiView.center = emojiFrame.center
|
||||
emojiView.bounds = CGRect(origin: CGPoint(), size: emojiFrame.size)
|
||||
}
|
||||
} else {
|
||||
strongSelf.symbolNode.isHidden = false
|
||||
|
||||
if let emojiView = strongSelf.emojiView {
|
||||
strongSelf.emojiView = nil
|
||||
emojiView.removeFromSuperview()
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
@ -69,7 +69,7 @@ final class HashtagChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
private var enqueuedTransitions: [(HashtagChatInputContextPanelTransition, Bool)] = []
|
||||
private var validLayout: (CGSize, CGFloat, CGFloat, CGFloat)?
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.listView = ListView()
|
||||
self.listView.isOpaque = false
|
||||
self.listView.stackFromBottom = true
|
||||
@ -80,7 +80,7 @@ final class HashtagChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
return strings.VoiceOver_ScrollStatus(row, count).string
|
||||
}
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
@ -91,7 +91,7 @@ final class HorizontalListContextResultsChatInputContextPanelNode: ChatInputCont
|
||||
private var enqueuedTransitions: [(HorizontalListContextResultsChatInputContextPanelTransition, Bool)] = []
|
||||
private var hasValidLayout = false
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.strings = strings
|
||||
|
||||
self.separatorNode = ASDisplayNode()
|
||||
@ -108,7 +108,7 @@ final class HorizontalListContextResultsChatInputContextPanelNode: ChatInputCont
|
||||
return strings.VoiceOver_ScrollStatus(row, count).string
|
||||
}
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
@ -117,7 +117,7 @@ final class HorizontalStickersChatContextPanelNode: ChatInputContextPanelNode {
|
||||
|
||||
private var stickerPreviewController: StickerPreviewController?
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.strings = strings
|
||||
|
||||
self.backgroundNode = ASImageNode()
|
||||
@ -144,7 +144,7 @@ final class HorizontalStickersChatContextPanelNode: ChatInputContextPanelNode {
|
||||
|
||||
self.stickersInteraction = HorizontalStickersChatContextPanelInteraction()
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.placement = .overTextInput
|
||||
self.isOpaque = false
|
||||
|
@ -492,7 +492,7 @@ final class InlineReactionSearchPanel: ChatInputContextPanelNode {
|
||||
|
||||
private var choosingStickerDisposable: Disposable?
|
||||
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, peerId: PeerId?) {
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, peerId: PeerId?, chatPresentationContext: ChatPresentationContext) {
|
||||
self.containerNode = ASDisplayNode()
|
||||
|
||||
self.backgroundNode = ASDisplayNode()
|
||||
@ -535,7 +535,7 @@ final class InlineReactionSearchPanel: ChatInputContextPanelNode {
|
||||
|
||||
self.stickersNode = InlineReactionSearchStickersNode(context: context, theme: theme, strings: strings, peerId: peerId)
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.placement = .overPanels
|
||||
self.isOpaque = false
|
||||
|
@ -67,7 +67,7 @@ final class MentionChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
private var enqueuedTransitions: [(CommandChatInputContextPanelTransition, Bool)] = []
|
||||
private var validLayout: (CGSize, CGFloat, CGFloat, CGFloat)?
|
||||
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, mode: MentionChatInputContextPanelMode) {
|
||||
init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, mode: MentionChatInputContextPanelMode, chatPresentationContext: ChatPresentationContext) {
|
||||
self.mode = mode
|
||||
|
||||
self.listView = ListView()
|
||||
@ -80,7 +80,7 @@ final class MentionChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
return strings.VoiceOver_ScrollStatus(row, count).string
|
||||
}
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
@ -84,7 +84,7 @@ final class StickersChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
|
||||
private var stickerPreviewController: StickerPreviewController?
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.strings = strings
|
||||
|
||||
self.listView = ListView()
|
||||
@ -99,7 +99,7 @@ final class StickersChatInputContextPanelNode: ChatInputContextPanelNode {
|
||||
|
||||
self.stickersInteraction = StickersChatInputContextPanelInteraction()
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
@ -133,7 +133,7 @@ final class VerticalListContextResultsChatInputContextPanelNode: ChatInputContex
|
||||
private let loadMoreDisposable = MetaDisposable()
|
||||
private var isLoadingMore: Bool = false
|
||||
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize) {
|
||||
override init(context: AccountContext, theme: PresentationTheme, strings: PresentationStrings, fontSize: PresentationFontSize, chatPresentationContext: ChatPresentationContext) {
|
||||
self.listView = ListView()
|
||||
self.listView.isOpaque = false
|
||||
self.listView.stackFromBottom = true
|
||||
@ -145,7 +145,7 @@ final class VerticalListContextResultsChatInputContextPanelNode: ChatInputContex
|
||||
return strings.VoiceOver_ScrollStatus(row, count).string
|
||||
}
|
||||
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize)
|
||||
super.init(context: context, theme: theme, strings: strings, fontSize: fontSize, chatPresentationContext: chatPresentationContext)
|
||||
|
||||
self.isOpaque = false
|
||||
self.clipsToBounds = true
|
||||
|
Loading…
x
Reference in New Issue
Block a user