From 2397f3c5b176a38a94d194d92d3cdc2bcfaaa7f3 Mon Sep 17 00:00:00 2001 From: Ali <> Date: Mon, 6 Dec 2021 16:22:43 +0400 Subject: [PATCH] Temp --- .../ContainedViewLayoutTransition.swift | 96 +++++++++++++++++-- .../ChatMessageTextBubbleContentNode.swift | 1 + 2 files changed, 87 insertions(+), 10 deletions(-) diff --git a/submodules/Display/Source/ContainedViewLayoutTransition.swift b/submodules/Display/Source/ContainedViewLayoutTransition.swift index 4d5b64f7bc..cb4294c0e2 100644 --- a/submodules/Display/Source/ContainedViewLayoutTransition.swift +++ b/submodules/Display/Source/ContainedViewLayoutTransition.swift @@ -1443,6 +1443,7 @@ extension CGFloat: AnyValueProviding { var anyValue: ControlledTransitionProperty.AnyValue { return ControlledTransitionProperty.AnyValue( value: self, + nsValue: self as NSNumber, stringValue: { "\(self)" }, isEqual: { other in if let otherValue = other.value as? CGFloat { @@ -1471,6 +1472,7 @@ extension Float: AnyValueProviding { var anyValue: ControlledTransitionProperty.AnyValue { return ControlledTransitionProperty.AnyValue( value: self, + nsValue: self as NSNumber, stringValue: { "\(self)" }, isEqual: { other in if let otherValue = other.value as? Float { @@ -1497,6 +1499,7 @@ extension CGPoint: AnyValueProviding { var anyValue: ControlledTransitionProperty.AnyValue { return ControlledTransitionProperty.AnyValue( value: self, + nsValue: NSValue(cgPoint: self), stringValue: { "\(self)" }, isEqual: { other in if let otherValue = other.value as? CGPoint { @@ -1523,6 +1526,7 @@ extension CGSize: AnyValueProviding { var anyValue: ControlledTransitionProperty.AnyValue { return ControlledTransitionProperty.AnyValue( value: self, + nsValue: NSValue(cgSize: self), stringValue: { "\(self)" }, isEqual: { other in if let otherValue = other.value as? CGSize { @@ -1549,6 +1553,7 @@ extension CGRect: AnyValueProviding { var anyValue: ControlledTransitionProperty.AnyValue { return ControlledTransitionProperty.AnyValue( value: self, + nsValue: NSValue(cgRect: self), stringValue: { "\(self)" }, isEqual: { other in if let otherValue = other.value as? CGRect { @@ -1570,17 +1575,20 @@ extension CGRect: AnyValueProviding { final class ControlledTransitionProperty { final class AnyValue: Equatable, CustomStringConvertible { let value: Any + let nsValue: NSValue let stringValue: () -> String let isEqual: (AnyValue) -> Bool let interpolate: (AnyValue, CGFloat) -> AnyValue init( value: Any, + nsValue: NSValue, stringValue: @escaping () -> String, isEqual: @escaping (AnyValue) -> Bool, interpolate: @escaping (AnyValue, CGFloat) -> AnyValue ) { self.value = value + self.nsValue = nsValue self.stringValue = stringValue self.isEqual = isEqual self.interpolate = interpolate @@ -1600,32 +1608,82 @@ final class ControlledTransitionProperty { } let layer: CALayer + let path: String let keyPath: AnyKeyPath - private let write: (CALayer, AnyValue) -> Void var fromValue: AnyValue let toValue: AnyValue private(set) var lastValue: AnyValue private let completion: ((Bool) -> Void)? - init(layer: CALayer, keyPath: ReferenceWritableKeyPath, fromValue: T, toValue: T, completion: ((Bool) -> Void)?) where T: AnyValueProviding { + private var animator: AnyObject? + + init(layer: CALayer, path: String, keyPath: ReferenceWritableKeyPath, fromValue: T, toValue: T, completion: ((Bool) -> Void)?) where T: AnyValueProviding { self.layer = layer + self.path = path self.keyPath = keyPath - self.write = { layer, value in - layer[keyPath: keyPath] = value.value as! T - } self.fromValue = fromValue.anyValue self.toValue = toValue.anyValue self.lastValue = self.fromValue self.completion = completion + + if #available(iOS 10.0, *) { + layer[keyPath: keyPath] = fromValue + let animator = UIViewPropertyAnimator(duration: 1.0, curve: .linear, animations: { + layer[keyPath: keyPath] = toValue + }) + self.animator = animator + animator.pauseAnimation() + layer[keyPath: keyPath] = toValue + } + + self.update(at: 0.0) + } + + deinit { + if #available(iOS 10.0, *) { + if let animator = self.animator as? UIViewPropertyAnimator { + animator.stopAnimation(true) + self.animator = nil + } + } } func update(at fraction: CGFloat) { let value = self.fromValue.interpolate(toValue, fraction) self.lastValue = value - self.write(self.layer, value) + //self.write(self.layer, value) + + if #available(iOS 10.0, *) { + if let animator = self.animator as? UIViewPropertyAnimator { + animator.fractionComplete = fraction + } + } + + /*let animation = CABasicAnimation() + animation.speed = 0.0 + animation.duration = 1.0 + animation.fillMode = .both + animation.fromValue = value.nsValue + animation.toValue = self.toValue.nsValue + animation.keyPath = self.path + if let previousAnimation = self.layer.animation(forKey: self.animationKey) { + self.layer.removeAnimation(forKey: self.animationKey) + let _ = previousAnimation + } + self.layer.add(animation, forKey: self.animationKey)*/ } func complete(atEnd: Bool) { + if #available(iOS 10.0, *) { + if let animator = self.animator as? UIViewPropertyAnimator { + animator.stopAnimation(true) + /*if atEnd { + animator.finishAnimation(at: .current) + }*/ + self.animator = nil + } + } + self.completion?(atEnd) } } @@ -1713,40 +1771,58 @@ public final class ControlledTransition { } public func updateAlpha(layer: CALayer, alpha: CGFloat, completion: ((Bool) -> Void)?) { + let fromValue = layer.presentation()?.opacity ?? layer.opacity + //layer.opacity = Float(alpha) self.add(animation: ControlledTransitionProperty( layer: layer, + path: "opacity", keyPath: \.opacity, - fromValue: layer.opacity, + fromValue: fromValue, toValue: Float(alpha), completion: completion )) } public func updatePosition(layer: CALayer, position: CGPoint, completion: ((Bool) -> Void)?) { + let fromValue = layer.presentation()?.position ?? layer.position + //layer.position = position self.add(animation: ControlledTransitionProperty( layer: layer, + path: "position", keyPath: \.position, - fromValue: layer.position, + fromValue: fromValue, toValue: position, completion: completion )) } public func updateBounds(layer: CALayer, bounds: CGRect, completion: ((Bool) -> Void)?) { + let fromValue = layer.presentation()?.bounds ?? layer.bounds + //layer.bounds = bounds self.add(animation: ControlledTransitionProperty( layer: layer, + path: "bounds", keyPath: \.bounds, - fromValue: layer.bounds, + fromValue: fromValue, toValue: bounds, completion: completion )) } public func updateFrame(layer: CALayer, frame: CGRect, completion: ((Bool) -> Void)?) { + if layer.frame == frame { + return + } + let fromValue = layer.presentation()?.frame ?? layer.frame + if let presentation = layer.presentation(), presentation.frame != layer.frame { + assert(true) + } + //layer.frame = frame self.add(animation: ControlledTransitionProperty( layer: layer, + path: "frame", keyPath: \.frame, - fromValue: layer.frame, + fromValue: fromValue, toValue: frame, completion: completion )) diff --git a/submodules/TelegramUI/Sources/ChatMessageTextBubbleContentNode.swift b/submodules/TelegramUI/Sources/ChatMessageTextBubbleContentNode.swift index ede3a8e43d..a320abae7e 100644 --- a/submodules/TelegramUI/Sources/ChatMessageTextBubbleContentNode.swift +++ b/submodules/TelegramUI/Sources/ChatMessageTextBubbleContentNode.swift @@ -365,6 +365,7 @@ class ChatMessageTextBubbleContentNode: ChatMessageBubbleContentNode { let _ = textApply() animation.animator.updateFrame(layer: strongSelf.textNode.layer, frame: textFrame, completion: nil) + //strongSelf.textNode.frame = textFrame if let (_, spoilerTextApply) = spoilerTextLayoutAndApply { let spoilerTextNode = spoilerTextApply()