LeadKit/TIUIElements/Sources/Separators/ContainerSeparatorTableView...

147 lines
5.5 KiB
Swift

//
// Copyright (c) 2023 Touch Instinct
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the Software), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED AS IS, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
//
import UIKit
open class ContainerSeparatorTableViewCell<View: UIView>: ContainerTableViewCell<View>, SeparatorsConfigurable {
private lazy var topSeparatorView = createTopSeparator()
private lazy var bottomSeparatorView = createBottomSeparator()
private lazy var topSeparatorConstraints: SubviewConstraints = {
subviewConstraints(for: topSeparatorView)
}()
private lazy var bottomSeparatorConstraints: SubviewConstraints = {
subviewConstraints(for: bottomSeparatorView)
}()
open func createTopSeparator() -> UIView {
.init()
}
open func createBottomSeparator() -> UIView {
.init()
}
open func add(topSeparatorView: UIView) {
contentView.addSubview(topSeparatorView)
}
open func add(bottomSeparatorView: UIView) {
contentView.addSubview(bottomSeparatorView)
}
// MARK: - SeparatorsConfigurable
public func configureSeparators(with separatorsConfiguration: SeparatorsConfiguration) {
topSeparatorView.isHidden = separatorsConfiguration.topIsHidden
bottomSeparatorView.isHidden = separatorsConfiguration.bottomIsHidden
switch separatorsConfiguration {
case .none:
break
case let .bottom(appearance):
updateBottomSeparator(with: appearance)
case let .top(appearance):
updateTopSeparator(with: appearance)
case let .full(topAppearance, bottomAppearance):
updateTopSeparator(with: topAppearance)
updateBottomSeparator(with: bottomAppearance)
}
}
open override func prepareForReuse() {
super.prepareForReuse()
configureSeparators(with: .none)
}
// MARK: - InitializableView
open override func addViews() {
super.addViews()
add(topSeparatorView: topSeparatorView)
add(bottomSeparatorView: bottomSeparatorView)
}
open override func configureLayout() {
super.configureLayout()
for view in [topSeparatorView, bottomSeparatorView] {
view.translatesAutoresizingMaskIntoConstraints = false
}
}
open override func configureAppearance() {
super.configureAppearance()
for view in [topSeparatorView, bottomSeparatorView] {
view.isHidden = true
view.backgroundColor = .black
}
}
// MARK: - Private
private func updateTopSeparator(with appearance: SeparatorAppearance) {
topSeparatorView.configureUIView(appearance: appearance)
topSeparatorConstraints.update(from: appearance.layout)
}
private func updateBottomSeparator(with appearance: SeparatorAppearance) {
bottomSeparatorView.configureUIView(appearance: appearance)
bottomSeparatorConstraints.update(from: appearance.layout)
}
private func subviewConstraints(for seperatorView: UIView) -> SubviewConstraints {
let leadingConstraint = seperatorView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor)
let trailingConstraint = seperatorView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor)
let topConstraint = seperatorView.topAnchor.constraint(equalTo: contentView.topAnchor)
let bottomConstraint = seperatorView.bottomAnchor.constraint(equalTo: contentView.bottomAnchor)
let edgeConstraints = EdgeConstraints(leadingConstraint: leadingConstraint,
trailingConstraint: trailingConstraint,
topConstraint: topConstraint,
bottomConstraint: bottomConstraint)
let centerXConstraint = seperatorView.centerXAnchor.constraint(equalTo: contentView.centerXAnchor)
let centerYConstraint = seperatorView.centerYAnchor.constraint(equalTo: contentView.centerYAnchor)
let centerConstraints = CenterConstraints(centerXConstraint: centerXConstraint,
centerYConstraint: centerYConstraint)
let sizeConstraints = SizeConstraints(widthConstraint: seperatorView.widthAnchor.constraint(equalToConstant: .zero),
heightConstraint: seperatorView.heightAnchor.constraint(equalToConstant: .zero))
return SubviewConstraints(edgeConstraints: edgeConstraints,
centerConstraints: centerConstraints,
sizeConstraints: sizeConstraints)
}
}