You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
130 lines
3.4 KiB
130 lines
3.4 KiB
//
|
|
|
|
import Foundation
|
|
import UIKit
|
|
|
|
@IBDesignable
|
|
class CustomPageControl: UIControl {
|
|
//MARK:- Properties
|
|
|
|
private var numberOfDots = [UIView]() {
|
|
didSet{
|
|
if numberOfDots.count == numberOfPages {
|
|
setupViews()
|
|
}
|
|
}
|
|
}
|
|
|
|
@IBInspectable var numberOfPages: Int = 0 {
|
|
didSet{
|
|
|
|
for tag in 0 ..< numberOfPages {
|
|
let dot = getDotView()
|
|
dot.tag = tag
|
|
dot.backgroundColor = pageIndicatorTintColor
|
|
self.numberOfDots.append(dot)
|
|
}
|
|
}
|
|
}
|
|
|
|
var currentPage: Int = 0 {
|
|
didSet{
|
|
onPageControlSwipe()
|
|
}
|
|
}
|
|
|
|
@IBInspectable var pageIndicatorTintColor: UIColor? = .blue
|
|
@IBInspectable var currentPageIndicatorTintColor: UIColor? = .green
|
|
|
|
private lazy var stackView = UIStackView.init(frame: self.bounds)
|
|
private lazy var constantSpace = ((stackView.spacing) * CGFloat(numberOfPages - 1) + ((self.bounds.height * 0.45) * CGFloat(numberOfPages)) - self.bounds.width)
|
|
|
|
|
|
override var bounds: CGRect {
|
|
didSet{
|
|
self.numberOfDots.forEach { (dot) in
|
|
self.setupDotAppearance(dot: dot)
|
|
}
|
|
}
|
|
}
|
|
|
|
//MARK:- Intialisers
|
|
convenience init() {
|
|
self.init(frame: .zero)
|
|
}
|
|
|
|
init(withNoOfPages pages: Int) {
|
|
self.numberOfPages = pages
|
|
self.currentPage = 0
|
|
super.init(frame: .zero)
|
|
setupViews()
|
|
}
|
|
|
|
override init(frame: CGRect) {
|
|
super.init(frame: frame)
|
|
setupViews()
|
|
}
|
|
|
|
required init?(coder aDecoder: NSCoder) {
|
|
super.init(coder: aDecoder)
|
|
|
|
}
|
|
private func setupViews() {
|
|
|
|
self.numberOfDots.forEach { (dot) in
|
|
self.stackView.addArrangedSubview(dot)
|
|
}
|
|
|
|
stackView.alignment = .center
|
|
stackView.axis = .horizontal
|
|
stackView.distribution = .fillEqually
|
|
stackView.spacing = 8
|
|
stackView.translatesAutoresizingMaskIntoConstraints = false
|
|
self.addSubview(stackView)
|
|
|
|
self.addConstraints([
|
|
stackView.centerXAnchor.constraint(equalTo: self.centerXAnchor),
|
|
stackView.centerYAnchor.constraint(equalTo: self.centerYAnchor),
|
|
stackView.heightAnchor.constraint(equalTo: self.heightAnchor),
|
|
])
|
|
|
|
self.numberOfDots.forEach { dot in
|
|
self.addConstraints([
|
|
dot.centerYAnchor.constraint(equalTo: self.stackView.centerYAnchor),
|
|
dot.widthAnchor.constraint(equalToConstant: 7),
|
|
dot.heightAnchor.constraint(equalToConstant: 7),
|
|
])
|
|
}
|
|
self.numberOfDots.forEach { dot in
|
|
dot.layer.cornerRadius = dot.bounds.height / 2
|
|
}
|
|
}
|
|
|
|
@objc private func onPageControlSwipe() {
|
|
_ = numberOfDots.map { (dot) in
|
|
setupDotAppearance(dot: dot)
|
|
if dot.tag == currentPage {
|
|
UIView.animate(withDuration: 0.2, animations: {
|
|
dot.layer.cornerRadius = dot.bounds.height / 5
|
|
dot.transform = CGAffineTransform.init(scaleX: 2, y: 1)
|
|
dot.backgroundColor = self.currentPageIndicatorTintColor
|
|
})
|
|
}
|
|
}
|
|
}
|
|
|
|
//MARK: Helper methods...
|
|
private func getDotView() -> UIView {
|
|
let dot = UIView()
|
|
dot.translatesAutoresizingMaskIntoConstraints = false
|
|
self.setupDotAppearance(dot: dot)
|
|
return dot
|
|
}
|
|
|
|
private func setupDotAppearance(dot: UIView) {
|
|
dot.transform = .identity
|
|
dot.layer.cornerRadius = dot.bounds.height / 2
|
|
dot.layer.masksToBounds = true
|
|
dot.backgroundColor = pageIndicatorTintColor
|
|
}
|
|
}
|