Shared media updates

This commit is contained in:
Ali 2021-10-26 00:33:25 +04:00
parent c982717eec
commit af7b97d835
4 changed files with 37 additions and 21 deletions

View File

@ -15,6 +15,7 @@ swift_library(
"//submodules/SSignalKit/SwiftSignalKit:SwiftSignalKit", "//submodules/SSignalKit/SwiftSignalKit:SwiftSignalKit",
"//submodules/ComponentFlow:ComponentFlow", "//submodules/ComponentFlow:ComponentFlow",
"//submodules/AnimationUI:AnimationUI", "//submodules/AnimationUI:AnimationUI",
"//submodules/TelegramPresentationData:TelegramPresentationData",
], ],
visibility = [ visibility = [
"//visibility:public", "//visibility:public",

View File

@ -3,6 +3,7 @@ import UIKit
import Display import Display
import AsyncDisplayKit import AsyncDisplayKit
import SwiftSignalKit import SwiftSignalKit
import TelegramPresentationData
private final class NullActionClass: NSObject, CAAction { private final class NullActionClass: NSObject, CAAction {
@objc func run(forKey event: String, object anObject: Any, arguments dict: [AnyHashable : Any]?) { @objc func run(forKey event: String, object anObject: Any, arguments dict: [AnyHashable : Any]?) {
@ -129,8 +130,7 @@ private final class Shimmer {
if let image = self.image { if let image = self.image {
layer.contents = image.cgImage layer.contents = image.cgImage
let shiftedContentsRect = CGRect(origin: CGPoint(x: frame.minX / containerSize.width, y: frame.minY / containerSize.height), size: CGSize(width: frame.width / containerSize.width, height: frame.height / containerSize.height)) let shiftedContentsRect = CGRect(origin: CGPoint(x: 0.0, y: frame.minY / containerSize.height), size: CGSize(width: 1.0, height: frame.height / containerSize.height))
let _ = shiftedContentsRect
layer.contentsRect = shiftedContentsRect layer.contentsRect = shiftedContentsRect
if layer.animation(forKey: "shimmer") == nil { if layer.animation(forKey: "shimmer") == nil {
@ -140,7 +140,7 @@ private final class Shimmer {
animation.isAdditive = true animation.isAdditive = true
animation.repeatCount = .infinity animation.repeatCount = .infinity
animation.duration = 0.8 animation.duration = 0.8
animation.beginTime = 1.0 animation.beginTime = layer.convertTime(1.0, from: nil)
layer.add(animation, forKey: "shimmer") layer.add(animation, forKey: "shimmer")
} }
} }
@ -429,6 +429,8 @@ public final class SparseItemGrid: ASDisplayNode {
private let scrollView: UIScrollView private let scrollView: UIScrollView
private let shimmer: Shimmer private let shimmer: Shimmer
var theme: PresentationTheme
var layout: Layout? var layout: Layout?
var items: Items? var items: Items?
var visibleItems: [AnyHashable: VisibleItem] = [:] var visibleItems: [AnyHashable: VisibleItem] = [:]
@ -446,7 +448,8 @@ public final class SparseItemGrid: ASDisplayNode {
let coveringOffsetUpdated: (Viewport, ContainedViewLayoutTransition) -> Void let coveringOffsetUpdated: (Viewport, ContainedViewLayoutTransition) -> Void
init(zoomLevel: ZoomLevel, maybeLoadHoleAnchor: @escaping (HoleAnchor, HoleLocation) -> Void, coveringOffsetUpdated: @escaping (Viewport, ContainedViewLayoutTransition) -> Void) { init(theme: PresentationTheme, zoomLevel: ZoomLevel, maybeLoadHoleAnchor: @escaping (HoleAnchor, HoleLocation) -> Void, coveringOffsetUpdated: @escaping (Viewport, ContainedViewLayoutTransition) -> Void) {
self.theme = theme
self.zoomLevel = zoomLevel self.zoomLevel = zoomLevel
self.maybeLoadHoleAnchor = maybeLoadHoleAnchor self.maybeLoadHoleAnchor = maybeLoadHoleAnchor
self.coveringOffsetUpdated = coveringOffsetUpdated self.coveringOffsetUpdated = coveringOffsetUpdated
@ -766,6 +769,8 @@ public final class SparseItemGrid: ASDisplayNode {
let visibleRange = layout.visibleItemRange(for: visibleBounds, count: items.count) let visibleRange = layout.visibleItemRange(for: visibleBounds, count: items.count)
for index in visibleRange.minIndex ... visibleRange.maxIndex { for index in visibleRange.minIndex ... visibleRange.maxIndex {
if let item = items.item(at: index) { if let item = items.item(at: index) {
let itemFrame = layout.frame(at: index)
let itemLayer: VisibleItem let itemLayer: VisibleItem
if let current = self.visibleItems[item.id] { if let current = self.visibleItems[item.id] {
itemLayer = current itemLayer = current
@ -794,7 +799,6 @@ public final class SparseItemGrid: ASDisplayNode {
itemLayer.shimmerLayer = placeholderLayer itemLayer.shimmerLayer = placeholderLayer
} }
let itemFrame = layout.frame(at: index)
placeholderLayer.frame = itemFrame placeholderLayer.frame = itemFrame
self.shimmer.update(colors: shimmerColors, layer: placeholderLayer, containerSize: layout.containerLayout.size, frame: itemFrame.offsetBy(dx: 0.0, dy: -visibleBounds.minY)) self.shimmer.update(colors: shimmerColors, layer: placeholderLayer, containerSize: layout.containerLayout.size, frame: itemFrame.offsetBy(dx: 0.0, dy: -visibleBounds.minY))
placeholderLayer.update(size: itemFrame.size) placeholderLayer.update(size: itemFrame.size)
@ -805,7 +809,7 @@ public final class SparseItemGrid: ASDisplayNode {
validIds.insert(item.id) validIds.insert(item.id)
itemLayer.frame = layout.frame(at: index) itemLayer.frame = itemFrame
} else { } else {
let placeholderLayer: SparseItemGridShimmerLayer let placeholderLayer: SparseItemGridShimmerLayer
if self.visiblePlaceholders.count > usedPlaceholderCount { if self.visiblePlaceholders.count > usedPlaceholderCount {
@ -851,6 +855,7 @@ public final class SparseItemGrid: ASDisplayNode {
} else if let view = item.view { } else if let view = item.view {
view.removeFromSuperview() view.removeFromSuperview()
} }
item.shimmerLayer?.removeFromSuperlayer()
} }
} }
@ -948,6 +953,7 @@ public final class SparseItemGrid: ASDisplayNode {
contentOffset: self.scrollView.bounds.minY, contentOffset: self.scrollView.bounds.minY,
isScrolling: self.scrollView.isDragging || self.scrollView.isDecelerating, isScrolling: self.scrollView.isDragging || self.scrollView.isDecelerating,
dateString: dateString ?? "", dateString: dateString ?? "",
theme: self.theme,
transition: .immediate transition: .immediate
) )
} }
@ -1075,6 +1081,7 @@ public final class SparseItemGrid: ASDisplayNode {
private var tapRecognizer: UITapGestureRecognizer? private var tapRecognizer: UITapGestureRecognizer?
private var pinchRecognizer: UIPinchGestureRecognizer? private var pinchRecognizer: UIPinchGestureRecognizer?
private var theme: PresentationTheme
private var containerLayout: ContainerLayout? private var containerLayout: ContainerLayout?
private var items: Items? private var items: Items?
@ -1099,7 +1106,9 @@ public final class SparseItemGrid: ASDisplayNode {
public var cancelExternalContentGestures: (() -> Void)? public var cancelExternalContentGestures: (() -> Void)?
override public init() { public init(theme: PresentationTheme) {
self.theme = theme
self.scrollingArea = SparseItemGridScrollingArea() self.scrollingArea = SparseItemGridScrollingArea()
super.init() super.init()
@ -1152,7 +1161,7 @@ public final class SparseItemGrid: ASDisplayNode {
let progress = (scale - interactiveState.initialScale) / (interactiveState.targetScale - interactiveState.initialScale) let progress = (scale - interactiveState.initialScale) / (interactiveState.targetScale - interactiveState.initialScale)
var replacedTransition = false var replacedTransition = false
//print("progress: \(progress), scale: \(scale), initial: \(interactiveState.initialScale), target: \(interactiveState.targetScale)")
if progress < 0.0 || progress > 1.0 { if progress < 0.0 || progress > 1.0 {
let boundaryViewport = progress > 1.0 ? currentViewportTransition.toViewport : currentViewportTransition.fromViewport let boundaryViewport = progress > 1.0 ? currentViewportTransition.toViewport : currentViewportTransition.fromViewport
let zoomLevels = self.availableZoomLevels(width: containerLayout.size.width, startingAt: boundaryViewport.zoomLevel) let zoomLevels = self.availableZoomLevels(width: containerLayout.size.width, startingAt: boundaryViewport.zoomLevel)
@ -1193,7 +1202,7 @@ public final class SparseItemGrid: ASDisplayNode {
let restoreScrollPosition: (y: CGFloat, index: Int)? = (anchorItemFrame.minY, nextAnchorItemIndex) let restoreScrollPosition: (y: CGFloat, index: Int)? = (anchorItemFrame.minY, nextAnchorItemIndex)
let nextViewport = Viewport(zoomLevel: nextZoomLevel, maybeLoadHoleAnchor: { [weak self] holeAnchor, location in let nextViewport = Viewport(theme: self.theme, zoomLevel: nextZoomLevel, maybeLoadHoleAnchor: { [weak self] holeAnchor, location in
guard let strongSelf = self else { guard let strongSelf = self else {
return return
} }
@ -1243,7 +1252,7 @@ public final class SparseItemGrid: ASDisplayNode {
let restoreScrollPosition: (y: CGFloat, index: Int)? = (anchorItemFrame.minY, anchorItem.index) let restoreScrollPosition: (y: CGFloat, index: Int)? = (anchorItemFrame.minY, anchorItem.index)
let anchorItemIndex = anchorItem.index let anchorItemIndex = anchorItem.index
let nextViewport = Viewport(zoomLevel: nextZoomLevel, maybeLoadHoleAnchor: { [weak self] holeAnchor, location in let nextViewport = Viewport(theme: self.theme, zoomLevel: nextZoomLevel, maybeLoadHoleAnchor: { [weak self] holeAnchor, location in
guard let strongSelf = self else { guard let strongSelf = self else {
return return
} }
@ -1302,7 +1311,8 @@ public final class SparseItemGrid: ASDisplayNode {
} }
} }
public func update(size: CGSize, insets: UIEdgeInsets, scrollIndicatorInsets: UIEdgeInsets, lockScrollingAtTop: Bool, fixedItemHeight: CGFloat?, items: Items, synchronous: Bool) { public func update(size: CGSize, insets: UIEdgeInsets, scrollIndicatorInsets: UIEdgeInsets, lockScrollingAtTop: Bool, fixedItemHeight: CGFloat?, items: Items, theme: PresentationTheme, synchronous: Bool) {
self.theme = theme
let containerLayout = ContainerLayout(size: size, insets: insets, scrollIndicatorInsets: scrollIndicatorInsets, lockScrollingAtTop: lockScrollingAtTop, fixedItemHeight: fixedItemHeight) let containerLayout = ContainerLayout(size: size, insets: insets, scrollIndicatorInsets: scrollIndicatorInsets, lockScrollingAtTop: lockScrollingAtTop, fixedItemHeight: fixedItemHeight)
self.containerLayout = containerLayout self.containerLayout = containerLayout
self.items = items self.items = items
@ -1312,7 +1322,7 @@ public final class SparseItemGrid: ASDisplayNode {
self.pinchRecognizer?.isEnabled = fixedItemHeight == nil && !lockScrollingAtTop self.pinchRecognizer?.isEnabled = fixedItemHeight == nil && !lockScrollingAtTop
if self.currentViewport == nil { if self.currentViewport == nil {
let currentViewport = Viewport(zoomLevel: self.initialZoomLevel ?? ZoomLevel(rawValue: 3), maybeLoadHoleAnchor: { [weak self] holeAnchor, location in let currentViewport = Viewport(theme: self.theme, zoomLevel: self.initialZoomLevel ?? ZoomLevel(rawValue: 3), maybeLoadHoleAnchor: { [weak self] holeAnchor, location in
guard let strongSelf = self else { guard let strongSelf = self else {
return return
} }
@ -1394,7 +1404,7 @@ public final class SparseItemGrid: ASDisplayNode {
self.currentViewport = nil self.currentViewport = nil
previousViewport.removeFromSupernode() previousViewport.removeFromSupernode()
let currentViewport = Viewport(zoomLevel: level, maybeLoadHoleAnchor: { [weak self] holeAnchor, location in let currentViewport = Viewport(theme: self.theme, zoomLevel: level, maybeLoadHoleAnchor: { [weak self] holeAnchor, location in
guard let strongSelf = self else { guard let strongSelf = self else {
return return
} }

View File

@ -5,6 +5,7 @@ import AsyncDisplayKit
import ComponentFlow import ComponentFlow
import SwiftSignalKit import SwiftSignalKit
import AnimationUI import AnimationUI
import TelegramPresentationData
public final class MultilineText: Component { public final class MultilineText: Component {
public let text: String public let text: String
@ -474,7 +475,7 @@ private final class SparseItemGridScrollingIndicatorComponent: CombinedComponent
component: Text( component: Text(
text: context.component.dateString, text: context.component.dateString,
font: Font.medium(13.0), font: Font.medium(13.0),
color: .black color: context.component.foregroundColor
), ),
availableSize: CGSize(width: 200.0, height: 100.0), availableSize: CGSize(width: 200.0, height: 100.0),
transition: .immediate transition: .immediate
@ -482,7 +483,7 @@ private final class SparseItemGridScrollingIndicatorComponent: CombinedComponent
let rect = rect.update( let rect = rect.update(
component: ShadowRoundedRectangle( component: ShadowRoundedRectangle(
color: .white color: context.component.backgroundColor
), ),
availableSize: CGSize(width: text.size.width + 26.0, height: 32.0), availableSize: CGSize(width: text.size.width + 26.0, height: 32.0),
transition: .immediate transition: .immediate
@ -646,6 +647,8 @@ public final class SparseItemGridScrollingArea: ASDisplayNode {
public var displayTooltip: DisplayTooltip? public var displayTooltip: DisplayTooltip?
private var theme: PresentationTheme?
override public init() { override public init() {
self.dateIndicator = ComponentHostView<Empty>() self.dateIndicator = ComponentHostView<Empty>()
self.lineIndicator = ComponentHostView<Empty>() self.lineIndicator = ComponentHostView<Empty>()
@ -781,9 +784,11 @@ public final class SparseItemGridScrollingArea: ASDisplayNode {
contentOffset: CGFloat, contentOffset: CGFloat,
isScrolling: Bool, isScrolling: Bool,
dateString: String, dateString: String,
theme: PresentationTheme,
transition: ContainedViewLayoutTransition transition: ContainedViewLayoutTransition
) { ) {
self.containerSize = containerSize self.containerSize = containerSize
self.theme = theme
if self.dateIndicator.alpha.isZero { if self.dateIndicator.alpha.isZero {
let transition: ContainedViewLayoutTransition = .immediate let transition: ContainedViewLayoutTransition = .immediate
@ -797,9 +802,9 @@ public final class SparseItemGridScrollingArea: ASDisplayNode {
let indicatorSize = self.dateIndicator.update( let indicatorSize = self.dateIndicator.update(
transition: .immediate, transition: .immediate,
component: AnyComponent(SparseItemGridScrollingIndicatorComponent( component: AnyComponent(SparseItemGridScrollingIndicatorComponent(
backgroundColor: .white, backgroundColor: theme.list.itemHighlightedBackgroundColor,
shadowColor: .black, shadowColor: .black,
foregroundColor: .black, foregroundColor: theme.list.itemPrimaryTextColor,
dateString: dateString dateString: dateString
)), )),
environment: {}, environment: {},
@ -858,7 +863,7 @@ public final class SparseItemGridScrollingArea: ASDisplayNode {
} }
private func updateLineIndicator(transition: ContainedViewLayoutTransition) { private func updateLineIndicator(transition: ContainedViewLayoutTransition) {
guard let indicatorPosition = self.indicatorPosition, let scrollIndicatorHeight = self.scrollIndicatorHeight else { guard let indicatorPosition = self.indicatorPosition, let scrollIndicatorHeight = self.scrollIndicatorHeight, let theme = self.theme else {
return return
} }
@ -873,7 +878,7 @@ public final class SparseItemGridScrollingArea: ASDisplayNode {
let _ = self.lineIndicator.update( let _ = self.lineIndicator.update(
transition: mappedTransition, transition: mappedTransition,
component: AnyComponent(RoundedRectangle( component: AnyComponent(RoundedRectangle(
color: UIColor(white: 0.0, alpha: 0.3) color: theme.list.scrollIndicatorColor
)), )),
environment: {}, environment: {},
containerSize: lineIndicatorSize containerSize: lineIndicatorSize

View File

@ -1384,7 +1384,7 @@ final class PeerInfoVisualMediaPaneNode: ASDisplayNode, PeerInfoPaneNode, UIScro
self.stateTag = tagMaskForType(contentType) self.stateTag = tagMaskForType(contentType)
self.contextGestureContainerNode = ContextControllerSourceNode() self.contextGestureContainerNode = ContextControllerSourceNode()
self.itemGrid = SparseItemGrid() self.itemGrid = SparseItemGrid(theme: self.context.sharedContext.currentPresentationData.with({ $0 }).theme)
self.directMediaImageCache = DirectMediaImageCache(account: context.account) self.directMediaImageCache = DirectMediaImageCache(account: context.account)
let useListItems: Bool let useListItems: Bool
@ -2160,7 +2160,7 @@ final class PeerInfoVisualMediaPaneNode: ASDisplayNode, PeerInfoPaneNode, UIScro
fixedItemHeight = nil fixedItemHeight = nil
} }
self.itemGrid.update(size: size, insets: UIEdgeInsets(top: topInset, left: sideInset, bottom: bottomInset, right: sideInset), scrollIndicatorInsets: UIEdgeInsets(top: 0.0, left: sideInset, bottom: bottomInset, right: sideInset), lockScrollingAtTop: isScrollingLockedAtTop, fixedItemHeight: fixedItemHeight, items: items, synchronous: wasFirstTime) self.itemGrid.update(size: size, insets: UIEdgeInsets(top: topInset, left: sideInset, bottom: bottomInset, right: sideInset), scrollIndicatorInsets: UIEdgeInsets(top: 0.0, left: sideInset, bottom: bottomInset, right: sideInset), lockScrollingAtTop: isScrollingLockedAtTop, fixedItemHeight: fixedItemHeight, items: items, theme: self.itemGridBinding.chatPresentationData.theme.theme, synchronous: wasFirstTime)
} }
} }