// // LayerDebugging.swift // lottie-swift // // Created by Brandon Withrow on 1/24/19. // import Foundation import QuartzCore // MARK: - LayerDebugStyle struct LayerDebugStyle { let anchorColor: CGColor let boundsColor: CGColor let anchorWidth: CGFloat let boundsWidth: CGFloat } // MARK: - LayerDebugging protocol LayerDebugging { var debugStyle: LayerDebugStyle { get } } // MARK: - CustomLayerDebugging protocol CustomLayerDebugging { func layerForDebugging() -> CALayer } // MARK: - DebugLayer class DebugLayer: CALayer { init(style: LayerDebugStyle) { super.init() zPosition = 1000 bounds = CGRect(x: 0, y: 0, width: style.anchorWidth, height: style.anchorWidth) backgroundColor = style.anchorColor } required init?(coder _: NSCoder) { fatalError("init(coder:) has not been implemented") } } extension CALayer { @nonobjc public func logLayerTree(withIndent: Int = 0) { var string = "" for _ in 0...withIndent { string = string + " " } string = string + "|_" + String(describing: self) LottieLogger.shared.info(string) if let sublayers = sublayers { for sublayer in sublayers { sublayer.logLayerTree(withIndent: withIndent + 1) } } } } // MARK: - CompositionLayer + CustomLayerDebugging extension CompositionLayer: CustomLayerDebugging { func layerForDebugging() -> CALayer { contentsLayer } } extension CALayer { @nonobjc func setDebuggingState(visible: Bool) { var sublayers = self.sublayers if let cust = self as? CustomLayerDebugging { sublayers = cust.layerForDebugging().sublayers } if let sublayers = sublayers { for i in 0.. LayerDebugStyle { let colorSpace = CGColorSpaceCreateDeviceRGB() let anchorColor = CGColor(colorSpace: colorSpace, components: [1, 0, 0, 1])! let boundsColor = CGColor(colorSpace: colorSpace, components: [1, 1, 0, 1])! return LayerDebugStyle( anchorColor: anchorColor, boundsColor: boundsColor, anchorWidth: 10, boundsWidth: 2) } static func topLayerStyle() -> LayerDebugStyle { let colorSpace = CGColorSpaceCreateDeviceRGB() let anchorColor = CGColor(colorSpace: colorSpace, components: [1, 0.5, 0, 0])! let boundsColor = CGColor(colorSpace: colorSpace, components: [0, 1, 0, 1])! return LayerDebugStyle( anchorColor: anchorColor, boundsColor: boundsColor, anchorWidth: 10, boundsWidth: 2) } static func nullLayerStyle() -> LayerDebugStyle { let colorSpace = CGColorSpaceCreateDeviceRGB() let anchorColor = CGColor(colorSpace: colorSpace, components: [0, 0, 1, 0])! let boundsColor = CGColor(colorSpace: colorSpace, components: [0, 1, 0, 1])! return LayerDebugStyle( anchorColor: anchorColor, boundsColor: boundsColor, anchorWidth: 10, boundsWidth: 2) } static func shapeLayerStyle() -> LayerDebugStyle { let colorSpace = CGColorSpaceCreateDeviceRGB() let anchorColor = CGColor(colorSpace: colorSpace, components: [0, 1, 0, 0])! let boundsColor = CGColor(colorSpace: colorSpace, components: [0, 1, 0, 1])! return LayerDebugStyle( anchorColor: anchorColor, boundsColor: boundsColor, anchorWidth: 10, boundsWidth: 2) } static func shapeRenderLayerStyle() -> LayerDebugStyle { let colorSpace = CGColorSpaceCreateDeviceRGB() let anchorColor = CGColor(colorSpace: colorSpace, components: [0, 1, 1, 0])! let boundsColor = CGColor(colorSpace: colorSpace, components: [0, 1, 0, 1])! return LayerDebugStyle( anchorColor: anchorColor, boundsColor: boundsColor, anchorWidth: 10, boundsWidth: 2) } } extension Array where Element == LayerModel { var parents: [Int] { var array = [Int]() for layer in self { if let parent = layer.parent { array.append(parent) } else { array.append(-1) } } return array } }