Files
divkit/client/ios/Core/BasePublic/LinearGradientView+Layer.swift
T
2023-03-28 12:17:21 +03:00

75 lines
1.8 KiB
Swift

// Copyright 2016 Yandex LLC. All rights reserved.
import Foundation
import UIKit
public final class LinearGradientView: UIView {
private var gradientLayer: LinearGradientLayer {
layer as! LinearGradientLayer
}
public func set(gradient: Gradient.Linear) {
gradientLayer.gradient = gradient
}
public init(_ gradient: Gradient.Linear) {
super.init(frame: .zero)
set(gradient: gradient)
isOpaque = false
layer.needsDisplayOnBoundsChange = true
}
public convenience init(
startColor: Color,
endColor: Color,
direction: Gradient.Linear.Direction
) {
self.init(.init(
startColor: startColor,
endColor: endColor,
direction: direction
))
}
@available(*, unavailable)
public required init(coder _: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
public override class var layerClass: AnyClass {
LinearGradientLayer.self
}
}
// https://stackoverflow.com/questions/38821631/cagradientlayer-diagonal-gradient/43176174
public final class LinearGradientLayer: CALayer {
public var gradient: Gradient.Linear? {
didSet {
guard gradient != oldValue else { return }
setNeedsDisplay()
}
}
public override func draw(in ctx: CGContext) {
guard let gradient = gradient else {
return
}
guard let cgGradient = CGGradient(
colorsSpace: CGColorSpaceCreateDeviceRGB(),
colors: gradient.colors.map { $0.cgColor } as CFArray,
locations: gradient.locations
) else {
assertionFailure()
return
}
ctx.drawLinearGradient(
cgGradient,
start: gradient.direction.from.absolutePosition(in: bounds),
end: gradient.direction.to.absolutePosition(in: bounds),
options: [.drawsBeforeStartLocation, .drawsAfterEndLocation]
)
}
}