mirror of
https://github.com/Swiftgram/Telegram-iOS.git
synced 2025-06-16 05:55:20 +00:00
Merge commit 'b7a9165d28d5c4224c524015a59d6e8305f6ed2c'
This commit is contained in:
commit
5b66668753
@ -226,10 +226,18 @@ public class AttachmentController: ViewController {
|
||||
self.mainButtonStateDisposable.set((mediaPickerContext.mainButtonState
|
||||
|> deliverOnMainQueue).start(next: { [weak self] mainButtonState in
|
||||
if let strongSelf = self {
|
||||
strongSelf.panel.updateMainButtonState(mainButtonState)
|
||||
if let layout = strongSelf.validLayout {
|
||||
strongSelf.containerLayoutUpdated(layout, transition: .animated(duration: 0.4, curve: .spring))
|
||||
let _ = (strongSelf.panel.animatingTransitionPromise.get()
|
||||
|> filter { value in
|
||||
return !value
|
||||
}
|
||||
|> take(1)).start(next: { [weak self] _ in
|
||||
if let strongSelf = self {
|
||||
strongSelf.panel.updateMainButtonState(mainButtonState)
|
||||
if let layout = strongSelf.validLayout {
|
||||
strongSelf.containerLayoutUpdated(layout, transition: .animated(duration: 0.4, curve: .spring))
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
}))
|
||||
} else {
|
||||
@ -385,7 +393,7 @@ public class AttachmentController: ViewController {
|
||||
}
|
||||
}
|
||||
|
||||
if let (inputContainerHeight, inputContainerNode) = self.controller?.getInputContainerNode() {
|
||||
if let (inputContainerHeight, inputContainerNode, _) = self.controller?.getInputContainerNode() {
|
||||
self.inputContainerHeight = inputContainerHeight
|
||||
self.inputContainerNode = inputContainerNode
|
||||
self.addSubnode(inputContainerNode)
|
||||
@ -560,6 +568,9 @@ public class AttachmentController: ViewController {
|
||||
}
|
||||
|
||||
func animateOut(completion: @escaping () -> Void = {}) {
|
||||
guard let controller = self.controller else {
|
||||
return
|
||||
}
|
||||
self.isDismissing = true
|
||||
|
||||
guard let layout = self.validLayout else {
|
||||
@ -583,6 +594,11 @@ public class AttachmentController: ViewController {
|
||||
alphaTransition.updateAlpha(node: self.dim, alpha: 0.0)
|
||||
|
||||
self.controller?.updateModalStyleOverlayTransitionFactor(0.0, transition: positionTransition)
|
||||
|
||||
if controller.fromMenu && self.hasButton, let (_, _, getTransition) = controller.getInputContainerNode(), let inputTransition = getTransition() {
|
||||
self.panel.animateTransitionOut(inputTransition: inputTransition, dismissed: true, transition: positionTransition)
|
||||
self.containerLayoutUpdated(layout, transition: positionTransition)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -604,6 +620,9 @@ public class AttachmentController: ViewController {
|
||||
|
||||
private var isUpdatingContainer = false
|
||||
private var switchingController = false
|
||||
|
||||
private var hasButton = false
|
||||
|
||||
func containerLayoutUpdated(_ layout: ContainerViewLayout, transition: ContainedViewLayoutTransition) {
|
||||
self.validLayout = layout
|
||||
|
||||
@ -657,7 +676,7 @@ public class AttachmentController: ViewController {
|
||||
containerHeight = layout.size.height
|
||||
}
|
||||
containerRect = CGRect(origin: CGPoint(), size: CGSize(width: layout.size.width, height: containerHeight))
|
||||
|
||||
|
||||
self.wrapperNode.cornerRadius = 0.0
|
||||
self.shadowNode.alpha = 0.0
|
||||
|
||||
@ -666,20 +685,32 @@ public class AttachmentController: ViewController {
|
||||
|
||||
var containerInsets = containerLayout.intrinsicInsets
|
||||
var hasPanel = false
|
||||
let hasButton = self.panel.isButtonVisible
|
||||
let previousHasButton = self.hasButton
|
||||
let hasButton = self.panel.isButtonVisible && !self.isDismissing
|
||||
self.hasButton = hasButton
|
||||
if let controller = self.controller, controller.buttons.count > 1 {
|
||||
hasPanel = true
|
||||
}
|
||||
|
||||
|
||||
let isEffecitvelyCollapsedUpdated = (self.selectionCount > 0) != (self.panel.isSelecting)
|
||||
var panelHeight = self.panel.update(layout: containerLayout, buttons: self.controller?.buttons ?? [], isSelecting: self.selectionCount > 0, elevateProgress: !hasPanel && !hasButton, transition: transition)
|
||||
if fromMenu && !hasButton, let inputContainerHeight = self.inputContainerHeight {
|
||||
panelHeight = inputContainerHeight
|
||||
}
|
||||
if hasPanel || hasButton {
|
||||
if hasPanel || hasButton || fromMenu {
|
||||
containerInsets.bottom = panelHeight
|
||||
}
|
||||
|
||||
var transitioning = false
|
||||
if fromMenu && previousHasButton != hasButton, let (_, _, getTransition) = controller.getInputContainerNode(), let inputTransition = getTransition() {
|
||||
if hasButton {
|
||||
self.panel.animateTransitionIn(inputTransition: inputTransition, transition: transition)
|
||||
} else {
|
||||
self.panel.animateTransitionOut(inputTransition: inputTransition, dismissed: false, transition: transition)
|
||||
}
|
||||
transitioning = true
|
||||
}
|
||||
|
||||
var panelTransition = transition
|
||||
if isEffecitvelyCollapsedUpdated {
|
||||
panelTransition = .animated(duration: 0.25, curve: .easeInOut)
|
||||
@ -694,12 +725,19 @@ public class AttachmentController: ViewController {
|
||||
if fromMenu {
|
||||
if hasButton {
|
||||
self.panel.isHidden = false
|
||||
self.inputContainerNode?.isHidden = true
|
||||
} else if !transitioning {
|
||||
if !self.panel.animatingTransition {
|
||||
self.panel.isHidden = true
|
||||
self.inputContainerNode?.isHidden = false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
panelTransition.updateFrame(node: self.panel, frame: CGRect(origin: CGPoint(x: 0.0, y: panelY), size: CGSize(width: containerRect.width, height: panelHeight)), completion: { [weak self] finished in
|
||||
if finished && fromMenu {
|
||||
if transitioning && finished {
|
||||
self?.panel.isHidden = !hasButton
|
||||
self?.inputContainerNode?.isHidden = hasButton
|
||||
}
|
||||
})
|
||||
|
||||
@ -745,7 +783,7 @@ public class AttachmentController: ViewController {
|
||||
completion(nil, nil)
|
||||
}
|
||||
|
||||
public var getInputContainerNode: () -> (CGFloat, ASDisplayNode)? = { return nil }
|
||||
public var getInputContainerNode: () -> (CGFloat, ASDisplayNode, () -> AttachmentController.InputPanelTransition?)? = { return nil }
|
||||
|
||||
public init(context: AccountContext, updatedPresentationData: (initial: PresentationData, signal: Signal<PresentationData, NoError>)? = nil, chatLocation: ChatLocation, buttons: [AttachmentButtonType], initialButton: AttachmentButtonType = .gallery, fromMenu: Bool = false) {
|
||||
self.context = context
|
||||
@ -785,6 +823,7 @@ public class AttachmentController: ViewController {
|
||||
self.displayNodeDidLoad()
|
||||
}
|
||||
|
||||
private var didDismiss = false
|
||||
public func _dismiss() {
|
||||
self.dismissed()
|
||||
super.dismiss(animated: false, completion: {})
|
||||
@ -793,10 +832,14 @@ public class AttachmentController: ViewController {
|
||||
public override func dismiss(animated flag: Bool, completion: (() -> Void)? = nil) {
|
||||
self.view.endEditing(true)
|
||||
if flag {
|
||||
self.node.animateOut(completion: { [weak self] in
|
||||
self?._dismiss()
|
||||
completion?()
|
||||
})
|
||||
if !self.didDismiss {
|
||||
self.didDismiss = true
|
||||
self.dismissed()
|
||||
self.node.animateOut(completion: { [weak self] in
|
||||
self?._dismiss()
|
||||
completion?()
|
||||
})
|
||||
}
|
||||
} else {
|
||||
self._dismiss()
|
||||
completion?()
|
||||
@ -815,4 +858,32 @@ public class AttachmentController: ViewController {
|
||||
self.validLayout = layout
|
||||
self.node.containerLayoutUpdated(layout, transition: transition)
|
||||
}
|
||||
|
||||
public final class InputPanelTransition {
|
||||
let inputNode: ASDisplayNode
|
||||
let accessoryPanelNode: ASDisplayNode?
|
||||
let menuButtonNode: ASDisplayNode
|
||||
let menuButtonBackgroundNode: ASDisplayNode
|
||||
let menuIconNode: ASDisplayNode
|
||||
let menuTextNode: ASDisplayNode
|
||||
let prepareForDismiss: () -> Void
|
||||
|
||||
public init(
|
||||
inputNode: ASDisplayNode,
|
||||
accessoryPanelNode: ASDisplayNode?,
|
||||
menuButtonNode: ASDisplayNode,
|
||||
menuButtonBackgroundNode: ASDisplayNode,
|
||||
menuIconNode: ASDisplayNode,
|
||||
menuTextNode: ASDisplayNode,
|
||||
prepareForDismiss: @escaping () -> Void
|
||||
) {
|
||||
self.inputNode = inputNode
|
||||
self.accessoryPanelNode = accessoryPanelNode
|
||||
self.menuButtonNode = menuButtonNode
|
||||
self.menuButtonBackgroundNode = menuButtonBackgroundNode
|
||||
self.menuIconNode = menuIconNode
|
||||
self.menuTextNode = menuTextNode
|
||||
self.prepareForDismiss = prepareForDismiss
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -384,21 +384,12 @@ public struct AttachmentMainButtonState {
|
||||
private final class MainButtonNode: HighlightTrackingButtonNode {
|
||||
private var state: AttachmentMainButtonState
|
||||
|
||||
private let backgroundNode: ASDisplayNode
|
||||
private let textNode: ImmediateTextNode
|
||||
fileprivate let textNode: ImmediateTextNode
|
||||
private let statusNode: SemanticStatusNode
|
||||
|
||||
override init(pointerStyle: PointerStyle? = nil) {
|
||||
self.state = AttachmentMainButtonState.initial
|
||||
|
||||
self.backgroundNode = ASDisplayNode()
|
||||
self.backgroundNode.allowsGroupOpacity = true
|
||||
self.backgroundNode.isUserInteractionEnabled = false
|
||||
self.backgroundNode.cornerRadius = 12.0
|
||||
if #available(iOS 13.0, *) {
|
||||
self.backgroundNode.layer.cornerCurve = .continuous
|
||||
}
|
||||
|
||||
self.textNode = ImmediateTextNode()
|
||||
self.textNode.textAlignment = .center
|
||||
|
||||
@ -406,23 +397,31 @@ private final class MainButtonNode: HighlightTrackingButtonNode {
|
||||
|
||||
super.init(pointerStyle: pointerStyle)
|
||||
|
||||
self.addSubnode(self.backgroundNode)
|
||||
self.backgroundNode.addSubnode(self.textNode)
|
||||
self.backgroundNode.addSubnode(self.statusNode)
|
||||
self.addSubnode(self.textNode)
|
||||
self.addSubnode(self.statusNode)
|
||||
|
||||
self.highligthedChanged = { [weak self] highlighted in
|
||||
if let strongSelf = self {
|
||||
if highlighted {
|
||||
strongSelf.backgroundNode.layer.removeAnimation(forKey: "opacity")
|
||||
strongSelf.backgroundNode.alpha = 0.65
|
||||
strongSelf.layer.removeAnimation(forKey: "opacity")
|
||||
strongSelf.alpha = 0.65
|
||||
} else {
|
||||
strongSelf.backgroundNode.alpha = 1.0
|
||||
strongSelf.backgroundNode.layer.animateAlpha(from: 0.65, to: 1.0, duration: 0.2)
|
||||
strongSelf.alpha = 1.0
|
||||
strongSelf.layer.animateAlpha(from: 0.65, to: 1.0, duration: 0.2)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override func didLoad() {
|
||||
super.didLoad()
|
||||
|
||||
self.cornerRadius = 12.0
|
||||
if #available(iOS 13.0, *) {
|
||||
self.layer.cornerCurve = .continuous
|
||||
}
|
||||
}
|
||||
|
||||
func updateLayout(size: CGSize, state: AttachmentMainButtonState, transition: ContainedViewLayoutTransition) {
|
||||
self.state = state
|
||||
|
||||
@ -434,9 +433,8 @@ private final class MainButtonNode: HighlightTrackingButtonNode {
|
||||
let textSize = self.textNode.updateLayout(size)
|
||||
self.textNode.frame = CGRect(origin: CGPoint(x: floorToScreenPixels((size.width - textSize.width) / 2.0), y: floorToScreenPixels((size.height - textSize.height) / 2.0)), size: textSize)
|
||||
|
||||
self.backgroundNode.backgroundColor = state.backgroundColor
|
||||
self.backgroundColor = state.backgroundColor
|
||||
}
|
||||
transition.updateFrame(node: self.backgroundNode, frame: CGRect(origin: CGPoint(), size: size))
|
||||
|
||||
let statusSize = CGSize(width: 20.0, height: 20.0)
|
||||
transition.updateFrame(node: self.statusNode, frame: CGRect(origin: CGPoint(x: size.width - statusSize.width - 15.0, y: floorToScreenPixels((size.height - statusSize.height) / 2.0)), size: statusSize))
|
||||
@ -472,8 +470,11 @@ final class AttachmentPanel: ASDisplayNode, UIScrollViewDelegate {
|
||||
private var buttons: [AttachmentButtonType] = []
|
||||
private var selectedIndex: Int = 0
|
||||
private(set) var isSelecting: Bool = false
|
||||
private(set) var isButtonVisible: Bool = false
|
||||
|
||||
private var _isButtonVisible: Bool = false
|
||||
var isButtonVisible: Bool {
|
||||
return self.mainButtonState.isVisible
|
||||
}
|
||||
|
||||
private var validLayout: ContainerViewLayout?
|
||||
private var scrollLayout: (width: CGFloat, contentSize: CGSize)?
|
||||
|
||||
@ -853,7 +854,7 @@ final class AttachmentPanel: ASDisplayNode, UIScrollViewDelegate {
|
||||
}
|
||||
self.scrollLayout = (layout.size.width, contentSize)
|
||||
|
||||
transition.updateFrameAsPositionAndBounds(node: self.scrollNode, frame: CGRect(origin: CGPoint(x: 0.0, y: self.isSelecting || self.isButtonVisible ? -buttonSize.height : 0.0), size: CGSize(width: layout.size.width, height: buttonSize.height)))
|
||||
transition.updateFrameAsPositionAndBounds(node: self.scrollNode, frame: CGRect(origin: CGPoint(x: 0.0, y: self.isSelecting || self._isButtonVisible ? -buttonSize.height : 0.0), size: CGSize(width: layout.size.width, height: buttonSize.height)))
|
||||
self.scrollNode.view.contentSize = contentSize
|
||||
|
||||
return true
|
||||
@ -903,13 +904,144 @@ final class AttachmentPanel: ASDisplayNode, UIScrollViewDelegate {
|
||||
self.mainButtonState = mainButtonState ?? currentButtonState
|
||||
}
|
||||
|
||||
let animatingTransitionPromise = ValuePromise<Bool>(false)
|
||||
private(set) var animatingTransition = false {
|
||||
didSet {
|
||||
self.animatingTransitionPromise.set(self.animatingTransition)
|
||||
}
|
||||
}
|
||||
|
||||
func animateTransitionIn(inputTransition: AttachmentController.InputPanelTransition, transition: ContainedViewLayoutTransition) {
|
||||
guard !self.animatingTransition, let inputNodeSnapshotView = inputTransition.inputNode.view.snapshotView(afterScreenUpdates: false) else {
|
||||
return
|
||||
}
|
||||
guard let menuIconSnapshotView = inputTransition.menuIconNode.view.snapshotView(afterScreenUpdates: false), let menuTextSnapshotView = inputTransition.menuTextNode.view.snapshotView(afterScreenUpdates: false) else {
|
||||
return
|
||||
}
|
||||
self.animatingTransition = true
|
||||
|
||||
let targetButtonColor = self.mainButtonNode.backgroundColor
|
||||
self.mainButtonNode.backgroundColor = inputTransition.menuButtonBackgroundNode.backgroundColor
|
||||
transition.updateBackgroundColor(node: self.mainButtonNode, color: targetButtonColor ?? .clear)
|
||||
|
||||
transition.animateFrame(layer: self.mainButtonNode.layer, from: inputTransition.menuButtonNode.frame)
|
||||
transition.animatePosition(node: self.mainButtonNode.textNode, from: CGPoint(x: inputTransition.menuButtonNode.frame.width / 2.0, y: inputTransition.menuButtonNode.frame.height / 2.0))
|
||||
|
||||
let targetButtonCornerRadius = self.mainButtonNode.cornerRadius
|
||||
self.mainButtonNode.cornerRadius = inputTransition.menuButtonNode.cornerRadius
|
||||
transition.updateCornerRadius(node: self.mainButtonNode, cornerRadius: targetButtonCornerRadius)
|
||||
self.mainButtonNode.subnodeTransform = CATransform3DMakeScale(0.2, 0.2, 1.0)
|
||||
transition.updateSublayerTransformScale(node: self.mainButtonNode, scale: 1.0)
|
||||
self.mainButtonNode.textNode.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2)
|
||||
|
||||
let menuContentDelta = (self.mainButtonNode.frame.width - inputTransition.menuButtonNode.frame.width) / 2.0
|
||||
menuIconSnapshotView.frame = inputTransition.menuIconNode.frame.offsetBy(dx: inputTransition.menuButtonNode.frame.minX, dy: inputTransition.menuButtonNode.frame.minY)
|
||||
self.view.addSubview(menuIconSnapshotView)
|
||||
menuIconSnapshotView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, removeOnCompletion: false, completion: { [weak menuIconSnapshotView] _ in
|
||||
menuIconSnapshotView?.removeFromSuperview()
|
||||
})
|
||||
transition.updatePosition(layer: menuIconSnapshotView.layer, position: CGPoint(x: menuIconSnapshotView.center.x + menuContentDelta, y: self.mainButtonNode.position.y))
|
||||
|
||||
menuTextSnapshotView.frame = inputTransition.menuTextNode.frame.offsetBy(dx: inputTransition.menuButtonNode.frame.minX + 19.0, dy: inputTransition.menuButtonNode.frame.minY)
|
||||
self.view.addSubview(menuTextSnapshotView)
|
||||
menuTextSnapshotView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, removeOnCompletion: false, completion: { [weak menuTextSnapshotView] _ in
|
||||
menuTextSnapshotView?.removeFromSuperview()
|
||||
})
|
||||
transition.updatePosition(layer: menuTextSnapshotView.layer, position: CGPoint(x: menuTextSnapshotView.center.x + menuContentDelta, y: self.mainButtonNode.position.y))
|
||||
|
||||
inputNodeSnapshotView.clipsToBounds = true
|
||||
inputNodeSnapshotView.contentMode = .right
|
||||
inputNodeSnapshotView.frame = CGRect(x: inputTransition.menuButtonNode.frame.maxX, y: 0.0, width: inputNodeSnapshotView.frame.width - inputTransition.menuButtonNode.frame.maxX, height: inputNodeSnapshotView.frame.height)
|
||||
self.view.addSubview(inputNodeSnapshotView)
|
||||
|
||||
let targetInputPosition = CGPoint(x: inputNodeSnapshotView.center.x + inputNodeSnapshotView.frame.width, y: self.mainButtonNode.position.y)
|
||||
transition.updatePosition(layer: inputNodeSnapshotView.layer, position: targetInputPosition, completion: { [weak inputNodeSnapshotView] _ in
|
||||
inputNodeSnapshotView?.removeFromSuperview()
|
||||
self.animatingTransition = false
|
||||
})
|
||||
}
|
||||
|
||||
private var dismissed = false
|
||||
func animateTransitionOut(inputTransition: AttachmentController.InputPanelTransition, dismissed: Bool, transition: ContainedViewLayoutTransition) {
|
||||
guard !self.animatingTransition, let inputNodeSnapshotView = inputTransition.inputNode.view.snapshotView(afterScreenUpdates: false) else {
|
||||
return
|
||||
}
|
||||
if dismissed {
|
||||
inputTransition.prepareForDismiss()
|
||||
}
|
||||
|
||||
self.animatingTransition = true
|
||||
self.dismissed = dismissed
|
||||
|
||||
let action = {
|
||||
guard let menuIconSnapshotView = inputTransition.menuIconNode.view.snapshotView(afterScreenUpdates: true), let menuTextSnapshotView = inputTransition.menuTextNode.view.snapshotView(afterScreenUpdates: false) else {
|
||||
return
|
||||
}
|
||||
|
||||
let sourceButtonColor = self.mainButtonNode.backgroundColor
|
||||
transition.updateBackgroundColor(node: self.mainButtonNode, color: inputTransition.menuButtonBackgroundNode.backgroundColor ?? .clear)
|
||||
|
||||
let sourceButtonFrame = self.mainButtonNode.frame
|
||||
transition.updateFrame(node: self.mainButtonNode, frame: inputTransition.menuButtonNode.frame)
|
||||
let sourceButtonTextPosition = self.mainButtonNode.textNode.position
|
||||
transition.updatePosition(node: self.mainButtonNode.textNode, position: CGPoint(x: inputTransition.menuButtonNode.frame.width / 2.0, y: inputTransition.menuButtonNode.frame.height / 2.0))
|
||||
|
||||
let sourceButtonCornerRadius = self.mainButtonNode.cornerRadius
|
||||
transition.updateCornerRadius(node: self.mainButtonNode, cornerRadius: inputTransition.menuButtonNode.cornerRadius)
|
||||
transition.updateSublayerTransformScale(node: self.mainButtonNode, scale: 0.2)
|
||||
self.mainButtonNode.textNode.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2, removeOnCompletion: false)
|
||||
|
||||
let menuContentDelta = (sourceButtonFrame.width - inputTransition.menuButtonNode.frame.width) / 2.0
|
||||
var menuIconSnapshotViewFrame = inputTransition.menuIconNode.frame.offsetBy(dx: inputTransition.menuButtonNode.frame.minX + menuContentDelta, dy: inputTransition.menuButtonNode.frame.minY)
|
||||
menuIconSnapshotViewFrame.origin.y = self.mainButtonNode.position.y - menuIconSnapshotViewFrame.height / 2.0
|
||||
menuIconSnapshotView.frame = menuIconSnapshotViewFrame
|
||||
self.view.addSubview(menuIconSnapshotView)
|
||||
menuIconSnapshotView.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2)
|
||||
transition.updatePosition(layer: menuIconSnapshotView.layer, position: CGPoint(x: menuIconSnapshotView.center.x - menuContentDelta, y: inputTransition.menuButtonNode.position.y))
|
||||
|
||||
var menuTextSnapshotViewFrame = inputTransition.menuTextNode.frame.offsetBy(dx: inputTransition.menuButtonNode.frame.minX + 19.0 + menuContentDelta, dy: inputTransition.menuButtonNode.frame.minY)
|
||||
menuTextSnapshotViewFrame.origin.y = self.mainButtonNode.position.y - menuTextSnapshotViewFrame.height / 2.0
|
||||
menuTextSnapshotView.frame = menuTextSnapshotViewFrame
|
||||
self.view.addSubview(menuTextSnapshotView)
|
||||
menuTextSnapshotView.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2)
|
||||
transition.updatePosition(layer: menuTextSnapshotView.layer, position: CGPoint(x: menuTextSnapshotView.center.x - menuContentDelta, y: inputTransition.menuButtonNode.position.y))
|
||||
|
||||
inputNodeSnapshotView.clipsToBounds = true
|
||||
inputNodeSnapshotView.contentMode = .right
|
||||
let targetInputFrame = CGRect(x: inputTransition.menuButtonNode.frame.maxX, y: 0.0, width: inputNodeSnapshotView.frame.width - inputTransition.menuButtonNode.frame.maxX, height: inputNodeSnapshotView.frame.height)
|
||||
inputNodeSnapshotView.frame = targetInputFrame.offsetBy(dx: targetInputFrame.width, dy: self.mainButtonNode.position.y - inputNodeSnapshotView.frame.height / 2.0)
|
||||
self.view.addSubview(inputNodeSnapshotView)
|
||||
transition.updateFrame(layer: inputNodeSnapshotView.layer, frame: targetInputFrame, completion: { [weak inputNodeSnapshotView, weak menuIconSnapshotView, weak menuTextSnapshotView] _ in
|
||||
inputNodeSnapshotView?.removeFromSuperview()
|
||||
self.animatingTransition = false
|
||||
|
||||
if !dismissed {
|
||||
menuIconSnapshotView?.removeFromSuperview()
|
||||
menuTextSnapshotView?.removeFromSuperview()
|
||||
|
||||
self.mainButtonNode.backgroundColor = sourceButtonColor
|
||||
self.mainButtonNode.frame = sourceButtonFrame
|
||||
self.mainButtonNode.textNode.position = sourceButtonTextPosition
|
||||
self.mainButtonNode.textNode.layer.removeAllAnimations()
|
||||
self.mainButtonNode.cornerRadius = sourceButtonCornerRadius
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
if dismissed {
|
||||
Queue.mainQueue().after(0.01, action)
|
||||
} else {
|
||||
action()
|
||||
}
|
||||
}
|
||||
|
||||
func update(layout: ContainerViewLayout, buttons: [AttachmentButtonType], isSelecting: Bool, elevateProgress: Bool, transition: ContainedViewLayoutTransition) -> CGFloat {
|
||||
self.validLayout = layout
|
||||
self.buttons = buttons
|
||||
self.elevateProgress = elevateProgress
|
||||
|
||||
let isButtonVisibleUpdated = self.isButtonVisible != self.mainButtonState.isVisible
|
||||
self.isButtonVisible = self.mainButtonState.isVisible
|
||||
let isButtonVisibleUpdated = self._isButtonVisible != self.mainButtonState.isVisible
|
||||
self._isButtonVisible = self.mainButtonState.isVisible
|
||||
|
||||
let isSelectingUpdated = self.isSelecting != isSelecting
|
||||
self.isSelecting = isSelecting
|
||||
@ -1025,8 +1157,12 @@ final class AttachmentPanel: ASDisplayNode, UIScrollViewDelegate {
|
||||
|
||||
let sideInset: CGFloat = 16.0
|
||||
let buttonSize = CGSize(width: layout.size.width - (sideInset + layout.safeInsets.left) * 2.0, height: 50.0)
|
||||
self.mainButtonNode.updateLayout(size: buttonSize, state: self.mainButtonState, transition: transition)
|
||||
transition.updateFrame(node: self.mainButtonNode, frame: CGRect(origin: CGPoint(x: layout.safeInsets.left + sideInset, y: isButtonVisible || self.fromMenu ? 8.0 : containerFrame.height), size: buttonSize))
|
||||
if !self.dismissed {
|
||||
self.mainButtonNode.updateLayout(size: buttonSize, state: self.mainButtonState, transition: transition)
|
||||
}
|
||||
if !self.animatingTransition {
|
||||
transition.updateFrame(node: self.mainButtonNode, frame: CGRect(origin: CGPoint(x: layout.safeInsets.left + sideInset, y: isButtonVisible || self.fromMenu ? 8.0 : containerFrame.height), size: buttonSize))
|
||||
}
|
||||
|
||||
return containerFrame.height
|
||||
}
|
||||
@ -1035,3 +1171,4 @@ final class AttachmentPanel: ASDisplayNode, UIScrollViewDelegate {
|
||||
self.updateViews(transition: .immediate)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3360,12 +3360,14 @@ public final class ChatControllerImpl: TelegramBaseController, ChatController, G
|
||||
|
||||
let openWebView = {
|
||||
if fromMenu {
|
||||
let params = WebAppParameters(peerId: peerId, botId: peerId, botName: botName, url: nil, queryId: nil, buttonText: buttonText, keepAliveSignal: nil, fromMenu: true)
|
||||
let params = WebAppParameters(peerId: peerId, botId: peerId, botName: botName, url: url, queryId: nil, buttonText: buttonText, keepAliveSignal: nil, fromMenu: true)
|
||||
let controller = standaloneWebAppController(context: strongSelf.context, updatedPresentationData: strongSelf.updatedPresentationData, params: params, openUrl: { [weak self] url in
|
||||
self?.openUrl(url, concealed: true, forceExternal: true)
|
||||
}, getInputContainerNode: { [weak self] in
|
||||
if let strongSelf = self {
|
||||
return (strongSelf.chatDisplayNode.getWindowInputAccessoryHeight(), strongSelf.chatDisplayNode.inputPanelContainerNode)
|
||||
return (strongSelf.chatDisplayNode.getWindowInputAccessoryHeight(), strongSelf.chatDisplayNode.inputPanelContainerNode, {
|
||||
return strongSelf.chatDisplayNode.textInputPanelNode?.makeAttachmentMenuTransition(accessoryPanelNode: nil)
|
||||
})
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
|
@ -22,6 +22,7 @@ import TextInputMenu
|
||||
import Pasteboard
|
||||
import ChatPresentationInterfaceState
|
||||
import ManagedAnimationNode
|
||||
import AttachmentUI
|
||||
|
||||
private let accessoryButtonFont = Font.medium(14.0)
|
||||
private let counterFont = Font.with(size: 14.0, design: .regular, traits: [.monospacedNumbers])
|
||||
@ -2755,6 +2756,10 @@ class ChatTextInputPanelNode: ChatInputPanelNode, ASEditableTextNodeDelegate {
|
||||
scrollOffset: textInputNode.textView.contentOffset.y
|
||||
)
|
||||
}
|
||||
|
||||
func makeAttachmentMenuTransition(accessoryPanelNode: ASDisplayNode?) -> AttachmentController.InputPanelTransition {
|
||||
return AttachmentController.InputPanelTransition(inputNode: self, accessoryPanelNode: accessoryPanelNode, menuButtonNode: self.menuButton, menuButtonBackgroundNode: self.menuButtonBackgroundNode, menuIconNode: self.menuButtonIconNode, menuTextNode: self.menuButtonTextNode, prepareForDismiss: { self.menuButtonIconNode.enqueueState(.app, animated: false) })
|
||||
}
|
||||
}
|
||||
|
||||
private enum MenuIconNodeState: Equatable {
|
||||
|
@ -149,7 +149,7 @@ public final class WebAppController: ViewController, AttachmentContainable {
|
||||
}
|
||||
})
|
||||
|
||||
if let url = controller.url {
|
||||
if let url = controller.url, !controller.fromMenu {
|
||||
self.queryId = controller.queryId
|
||||
if let parsedUrl = URL(string: url) {
|
||||
self.webView?.load(URLRequest(url: parsedUrl))
|
||||
@ -666,7 +666,7 @@ private final class WebAppContextReferenceContentSource: ContextReferenceContent
|
||||
}
|
||||
}
|
||||
|
||||
public func standaloneWebAppController(context: AccountContext, updatedPresentationData: (initial: PresentationData, signal: Signal<PresentationData, NoError>)? = nil, params: WebAppParameters, openUrl: @escaping (String) -> Void, getInputContainerNode: @escaping () -> (CGFloat, ASDisplayNode)? = { return nil }, completion: @escaping () -> Void = {}, dismissed: @escaping () -> Void = {}) -> ViewController {
|
||||
public func standaloneWebAppController(context: AccountContext, updatedPresentationData: (initial: PresentationData, signal: Signal<PresentationData, NoError>)? = nil, params: WebAppParameters, openUrl: @escaping (String) -> Void, getInputContainerNode: @escaping () -> (CGFloat, ASDisplayNode, () -> AttachmentController.InputPanelTransition?)? = { return nil }, completion: @escaping () -> Void = {}, dismissed: @escaping () -> Void = {}) -> ViewController {
|
||||
let controller = AttachmentController(context: context, updatedPresentationData: updatedPresentationData, chatLocation: .peer(id: params.peerId), buttons: [.standalone], initialButton: .standalone, fromMenu: params.fromMenu)
|
||||
controller.getInputContainerNode = getInputContainerNode
|
||||
controller.requestController = { _, present in
|
||||
|
Loading…
x
Reference in New Issue
Block a user