前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >iOS开发之三个Button实现图片无限轮播(参考手机淘宝,Swift版)

iOS开发之三个Button实现图片无限轮播(参考手机淘宝,Swift版)

作者头像
lizelu
发布2018-01-11 11:57:58
2.2K0
发布2018-01-11 11:57:58
举报
文章被收录于专栏:青玉伏案

这两天使用Reveal工具查看"手机淘宝"App的UI层次时,发现其图片轮播使用了三个UIButton的复用来实现的图片循环无缝滚动。于是乎就有了今天这篇博客,看到“手机淘宝”这个幻灯片的UI层级时,就想要动手使用三个Button来实现一下,当然本篇博客使用是Swift语言,思路就是使用三个Button进行图片无限轮播。之前发过两篇关于图片轮播的博客,一个是没有使用ImageView复用的,一个是使用两张ImageView进行复用来实现图片轮播的,都是使用的Objective-C实现的,并在github上进行了代码分享。

本篇博客就是介绍如何去一步步的封装这个三个Button的无限轮播的组件的。在实现时将该无限轮播的组件进行了封装,需要你在实例化该组件后,传入一个存放图片地址的数组,数组中可以是本地图片的名字,也可以是一个网络图片的地址。如果是网络图片的地址,组件中会使用NSRULSession并采用合适的缓存策略从网络加载图片,加载完后在我们的组件上进行显示。废话少说,进入我们今天的主题。

今天的博客完全是个人兴趣爱好,也不是公司中项目要使用的缘故才去实现的。就是看到了淘宝中的轮播图,从UI层级上感觉这样可以实现,于是乎就打开Xcode,创建个Swift工程实现一把,过程还是蛮愉快的。当然今天封装组件的名称是以公司的名称首字母做的前缀了,这也便于在以后的工作中遇到该问题直接拿过来就用呢。

一、对“手机淘宝”UI层次的简单分析

下方截图就是当时我用Reveal工具查看的手机淘宝App的UI层级,下方只是幻灯片的部分。下方整个页面是使用UICollectionView来实现的了,下方的幻灯片所在的UIScrollView就放在UICollectionView上的一个Cell上。当然这不是我们今天的重点,我们将目光转移到左边红框中的数学层级上。可以明显的看出UIScrollView上贴了三个UIButton,而每个UIButton上又贴了一个UIImageView。

需要注意的一点是你看到UIButton是三个Button的中间一个,从下面UI视图中我们不难分析出,无论当前显示的是第几张图片,你看到的永远是中间Button上显示的图片。也就是将要显示的图片放到中间的Button上,左边的Button存放上一张图片,右边的Button存放下一张图片。当用户左划或者右划后,我们要做的事情就是将中间按钮放到可视区,并且设置成要显示的图片,当然左右两个Button都得设置成相应的图片,便于用户下次移动。当然这只是我的个人猜测,上面这种思路使用代码来实现是完全可行的,并且可以实现无循环无缝滚动了。

当然,上面说的原理比较简单,具体使用代码实现起来还是需要许多细节的。比如用户滑动时定时器的挂起和唤醒,用户左右滑动方向的记录,便于自动轮播时的方向与用户上次滑动的方向一致,异步加载网络请求图片,加载后显示在相应的Button上,通过Closure回调出用户点击事件可当前图片的索引信息等等需要注意的细节。敲代码也有几年时间了,有一点感触挺深的就是“说和做”完全是两码事,也就是你有思路和你把你的思路用代码实现,这是完全不同的概念。当然正确的思路固然重要,但是不去实现再好的思路也是枉费,实践出真知吗。说这么多,有回到了说与做的问题上,这话题就不多讨论了,高执行力,高自制力好处是多多的。言归正传,回到今天的主题。

二、从“原理图”中来看今天轮播的主题

下方就是今天要实现的轮播组件的原理图,思路就是这么个思路,要实现起来还得靠代码往上摞呢。下方解析图是以轮播5张图片为例。初始化状态是你看到的是第一张图片,第一张图片位于三个Button的中间,然后左边就是最后一张图片,右边是第二张图片。如果用户想右滑动显示的第二张图片(对应着下方的第一步),当第二张图片已经完全显示出来后,我们要做的第一件事情就是将用户移动的位置进行复位,也就是将第二个Button移动到显示的位置,然后设置按钮上显示相应的图片。第一个按钮就显示当前图片的前一张图片,如果当前显示的是第一张图片,那么第一个按钮上就显示最后一张图片。第三个按钮就显示当前图片的下一张图片,如果当前显示的图片是最后一张图片的话,那么第三个按钮上就显示第一张图片。这样就可以图片轮播了。

三、该自定义控件的视图层级

下图就是我们按照上面的思路,使用ScrollView上添加3个Button来实现的图片轮播,无缝滚动的效果还是蛮OK的。在下方运行效果中美女图片是从本地加载的,而风景图片是使用NSURLSession和GCD的东西并行异步的从网络获取的,获取完后再加载到相应Button的ImageView上。下方就是我们本篇博客相关Demo的运行效果,单从效果上来看,与之前所发布的图片轮播没有什么区别,但是其内部实现机制还是有较大区别的。接下来就逐步的看一下代码实现。

上面是运行效果,下方是UI的层级。当然也是用我们强大的Reveal来查看的了,下方红框中就是我们图片轮播的视图层级。该视图层级与“手机淘宝”上是一致的,都是在UIScrollView上贴了三个Button,然后在每个Button上贴了一个ImageView。层级比较简单,而你看到的当然是中间Button上的ImageView了,更多细节请看下图。

四、代码实现

运行效果看完了,UI层级结构也看完了,那么接下来就到了我们代码实现的时刻了。下方从组件的调用方式入手,逐步的去看一下上述效果是如何实现的。

1.上述组件的调用方式

下方代码段就是上述组件的实例化和调用方式,首先进行初始化,然后将该组件添加到父视图上。之后将要显示的图片数组imagesNameArray传入组件中,最后设置一下组件的闭包回调即可,该回调将每个按钮点击的时间回调给组件的使用者,该Closure的参数是当前点击按钮上所显示的Image的索引,说白了也就是你当前点击的第几张图片。

在调用组件时,传入给组件的参数是一个数组,下方代码就是我们初始化imagesNameArray的函数。从该代码段中我们不难看出,该数组中存储的有本地图片的名字,也有UIImage的对象,也有网络图片的URL。将含有三种元素的数组传给我们的组件实例,这些数组中的资源就可以按照数组中的顺序依次的循环轮播了。

2.上述组件的核心代码

组件调用方式还是蛮简单的,看完调用方式,接下来来看一下具体的代码实现。下方是我们组件中比较核心的实现部分。

(1).异步加载网络图片

下方代码段就是遍历我们的ImagesNameArray,找出该数组中所有的网络图片的URL,每找到一个URL就开启一个线程来请求该地址中的图片。下方的queue是并行队列,此处当然是并行队列的异步执行了。关于GCD的东西,请参考之前的博客《Grand Central Dispatch详解》。

下方代码段就是requestImage()方法中的内容了,该方法中使用NSSession并配置相应的缓存策略来请求网络图片。加载完图片后,将ImagesNameArray中相应的URL替换成相应的UIImage对象,然后在主线程中更新UI显示相应的图片,具体代码如下所示。

(2)moveImageView()方法的实现

该方法负责将按钮归位与赋值,该方法对应着上述原理图的第二和第三步。上面网络请求完一张图片后就会调用该方法更新UI。该方法的具体实现如下所示。下方代码中首先获取当前显示的页数,也就是当前显示的Image的索引,然后将第二个Button移动到可视区,最后调用setButtonImage()函数将每个Button上的ImageView设置成相应的Image。

(3)、定时器的实现

图片要隔段时间自动轮播,此处我们使用的是dispatch_source中的定时器类型来实现的自动轮播。下方就是我们定时器的实现,如下所示,代码比较简单,在此就不做过多的赘述了,创建完定时器我们不要忘了对定时器的source进行唤醒即可。

当用户进行手动切换时,我们要对定时器进行相应的挂起和唤醒操作。也就是说当用户开始滑动时我们要对定时器进行挂起,当用户滑动结束后要对定时器进行唤醒。当然这些都是在ScrollView相应的代理方法中进行处理的,具体如下所示:

(4)、滑动结束后更新按钮的位置和图片

无论是手动滑动,还是使用定时器滑动,滑动结束后我们都需要更新一下按钮的位置和按钮上要显示的图片。所以我们还需要使用到UIScrollView上的一个代理方法,那就是scrollViewDidScroll(),在该代理方法中我们调用了moveImage()方法来更新Button的位置和Button上ImageView要显示的图片信息。没有这个方法,图片就动不起来了,具体代码如下所示:

上述是该Demo的核心代码,更为详细的代码请移步于github: https://github.com/lizelu/CEImagesScrollDisplay, 因本篇博客篇幅有限,更具体的细节在此就不做过多赘述了,Demo已在上述github上进行分享。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2016-07-15 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
图像处理
图像处理基于腾讯云深度学习等人工智能技术,提供综合性的图像优化处理服务,包括图像质量评估、图像清晰度增强、图像智能裁剪等。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档