使用一个UIImageView实现无限轮播功能
比如:
1.使用GCD定时器来解决NSTimer使用过程中的坑
GCD定时器使用如下
/// GCD定时器
let timer = DispatchSource.makeTimerSource(queue: DispatchQueue.global())
然后在设置UI时添加触发方法----这里一定要注意,刷新UI一定要回到主线程去操作
fileprivate func updateviews() {
contentMode = .scaleAspectFill
layer.masksToBounds = true
isUserInteractionEnabled = true
***添加手势****
kf.indicatorType = .activity
//GCD定时器执行方法
timer.scheduleRepeating(deadline: DispatchTime.now() + config.duration, interval: config.duration)
timer.setEventHandler {
[weak self] in
guard let strongSelf = self else { return }
var new = strongSelf.index
new = new + 1
if new == strongSelf.urls.count {
new = 0
}
DispatchQueue.main.async {
strongSelf.index = new
strongSelf.animator(UISwipeGestureRecognizerDirection.down)
}
}
**设置pageController**
}
- 属性
/// 数据源--字符串
var dataSource: [String] = [] {
didSet {
urls = dataSource.flatMap { URL(string: $0) }
}
}
/// URL地址----这里使用flatMap转化并去掉不正确的URL
fileprivate var urls: [URL] = [] {
didSet {
//使用Kingfisher加载网络图片
ImagePrefetcher(resources: urls).start()
kf.setImage(with: urls.first)
guard urls.count > 1 else {
return
}
timer.resume()
pageControl.numberOfPages = urls.count
}
}
//当前index
fileprivate var index: Int = 0 {
didSet {
if Thread.isMainThread {
pageControl.currentPage = index > urls.count ? urls.count : index
} else {
DispatchQueue.main.async { [weak self] in
guard let strongSelf = self else { return }
strongSelf.pageControl.currentPage = strongSelf.index > strongSelf.urls.count ? strongSelf.urls.count : strongSelf.index
}
}
}
}
/// 动画函数--- 这里是只初始化一个动画对象---防止重建多个对象
其中 typealias Animator = (UISwipeGestureRecognizerDirection) -> ()
fileprivate var animator: Animator!
fileprivate func setAnimator() -> Animator {
let transition = CATransition()
return { direction in
guard self.urls.count > 1 else {
return
}
self.kf.setImage(with: self.urls[self.index])
if direction == UISwipeGestureRecognizerDirection.left {
transition.duration = 0.5
transition.type = self.config.gestureAnimator.rawValue
transition.subtype = "fromRight"
} else if direction == UISwipeGestureRecognizerDirection.right {
transition.duration = 0.5
transition.type = self.config.gestureAnimator.rawValue
transition.subtype = "fromLeft"
} else {
transition.duration = 1
transition.type = self.config.motionAnimator.rawValue
transition.subtype = "fromRight"
}
self.layer.add(transition, forKey: nil)
}
}
最终初始化方法---其中config是采用回调方式设置轮播图
/// 初始化轮播图
///
/// - Parameters:
/// - frame: 位置
/// - placeholder: 默认uiimage
/// - config: 轮播图配置
/// - delegate: 代理
/// - callBack: 点击回调
typealias RunConfig = () -> RunloopViewConfig
init(frame: CGRect, placeholder: UIImage? = nil, config: RunConfig? = nil, delegate: RunloopViewDelegate? = nil, callBack: Select? = nil) {
self.callBack = callBack
if let config = config {
self.config = config()
}
if let delegate = delegate {
self.delegate = delegate
}
super.init(frame: frame)
updateviews()
self.image = placeholder
animator = setAnimator()
}
/// 轮播图设置
struct RunloopViewConfig {
/// 图片轮播时间---默认5s
var duration: TimeInterval = 5
/// pageControl圆点颜色---默认white
var pageColor: UIColor = UIColor.white
/// pageControl当前颜色---默认green
var currentColor: UIColor = UIColor.green
/// 手势动画---默认新图推旧图
var gestureAnimator: AnimatorMode = .push
/// 定时动画---默认水滴波
var motionAnimator: AnimatorMode = .ripple
}
/// 动画类型
///
/// - fade: 淡出效果
/// - moveIn: 新视图移动到旧视图上
/// - push: 新视图推出旧视图
/// - reveal: 移开旧视图显示新视图
/// - cube: 立方体翻转效果
/// - ripple: 水滴波纹效果
/// - oglFlip: 翻转效果
enum AnimatorMode: String {
case fade
case moveIn
case push
case reveal
case cube
case ripple = "rippleEffect"
case oglFlip
}
外界调用
let runView = RunloopView(frame: CGRect.init(x: 0, y: 80, width: UIScreen.main.bounds.width, height: 200), config: { _ in
var a = RunloopViewConfig()
a.gestureAnimator = .cube
return a
}) { (index) in
print("----\(index)")
}
runView.dataSource = [
"http://pic.qiantucdn.com/58pic/18/14/83/54d58PICtkn_1024.jpg",
"http://pic.qiantucdn.com/58pic/13/71/43/67I58PICJ4r_1024.jpg",
"http://pic16.nipic.com/20110927/3101644_080616110148_2.jpg",
"http://pic30.nipic.com/20130619/13053351_060617500180_2.jpg",
"http://pic125.nipic.com/file/20170323/13452884_100721331000_2.jpg",
"http://pic125.nipic.com/file/20170323/13452884_100713250000_2.jpg"
]