视图控制器与导航模式

视图导航器与导航模式

1.导航模式

  • 平铺导航模式:内容没有层次关系,展示的内容都放置在一个主屏幕上,采用分屏或者分页控制器进行导航,可以左右或者上下滑动屏幕查看内容。
  • 标签导航模式:内容被分成几个功能模块,每个功能模块之间没有什么关系。通过标签管理各个功能模块,点击标签可以切换功能模块。
  • 树形结构导航模式:内容是有层次的,从上到下细分或者具有分类包含等关系。

2.模态视图

在导航过程中,有时候需要放弃主要任务转而做其他次要任务,然后再返回到主要任务,这个次要任务就是在模态视图中完成的。默认情况下,模态视图是从屏幕下方滑出来的。完成的时候需要关闭这个模块视图,如果不关闭,就不能做别的事情,这就是“模态”的含义。它具有响应处理的意思。
视图控制器与导航模式
负责控制模态视图的控制器称为模态视图控制器。模态视图控制器并非一个专门的类,它可以是上面提到的控制器的子类。负责主要任务视图的控制器称为主视图控制器,它与模态视图控制器之间是父子关系。由于UIViewController类提供了如下两个方法,所以任何视图控制器中都可以呈现和关闭模态视图。

  • presentViewController:animated:completion。呈现模态视图。
  • dismissViewControllerAnimated:completion。关闭模态视图。
    在呈现模态视图时,有两个选择:
  • 代码实现:UIViewController的presentViewController:animated:completion方法实现。
  • Interface Builder实现:在storyboard的过渡(segue)中实现,不需要编写代码。

3.平铺导航

3.1 基于分屏导航的实现

基于分屏导航是平铺导航模式的主要实现方式,涉及的控件有分屏控件(UIPageControl)和屏幕滚动视图(UIscrollView)
基于分屏导航的手势有两种:1、点击高亮小点的左边(右边)或者上边(下边)实现翻屏;2、是用手在屏幕上滑动实现翻屏。**屏幕的总数应该限制在20个以内,超过20个小点的分屏控件就会溢出。**事实上,当一个应用超过10屏时,使用基于分屏导航模式就不是很方便了。

示例:

import UIKit
//定义屏幕的高度和宽度
let S_Width:CGFloat = UIScreen.main.bounds.size.width
let S_Height:CGFloat = UIScreen.main.bounds.size.height

class ViewController: UIViewController,UIScrollViewDelegate {
    
    var imageView_01:UIImageView!
    var imageView_02:UIImageView!
    var imageView_03:UIImageView!
    var scrollView:UIScrollView!
    var pageControl:UIPageControl!

    override func viewDidLoad() {
        super.viewDidLoad()
        self.scrollView = UIScrollView()
        self.view.addSubview(self.scrollView)
       //设置委托对象
        self.scrollView.delegate = self
        
        //设置滚动视图中内容视图的大小
        self.scrollView.contentSize = CGSize(width: S_Width * 3, height: S_Height) //预计要放多少(n)屏,相应的宽度就是S_Width * n
        self.scrollView.frame = self.view.frame //设置frame属性为当前视图大小
        self.scrollView.isPagingEnabled = true //设置屏幕滚动视图每次滑动时翻一屏
        self.scrollView.showsVerticalScrollIndicator = false
        self.scrollView.showsHorizontalScrollIndicator = false
        //添加视图的素材图片
        self.imageView_01 = UIImageView(frame: CGRect(x: 0, y: 0, width: S_Width, height: S_Height))
        self.imageView_01.image = UIImage(named: "girl_01")
        self.scrollView.addSubview(self.imageView_01)
        
        self.imageView_02 = UIImageView(frame: CGRect(x: S_Width, y: 0, width: S_Width, height: S_Height))
        self.imageView_02.image = UIImage(named: "girl_02")
        self.scrollView.addSubview(self.imageView_02)
        
        self.imageView_03 = UIImageView(frame: CGRect(x: S_Width * 2, y: 0, width: S_Width, height: S_Height))
        self.imageView_03.image = UIImage(named: "girl_03")
        self.scrollView.addSubview(self.imageView_03)
        
        let pageConrolWidth:CGFloat = 300.0
        let pageControlHeight:CGFloat = 37.0
        self.pageControl = UIPageControl(frame: CGRect(x: (S_Width - pageConrolWidth)/2, y: S_Height - pageControlHeight, width: pageConrolWidth, height: pageControlHeight))
        self.pageControl.numberOfPages = 3
        self.pageControl.addTarget(self, action: #selector(changePage(_:)), for: .valueChanged)
        self.view.addSubview(self.pageControl)
        
    }
    //显示当前页面为第几屏
    func scrollViewDidScroll(_ scrollView: UIScrollView) {
        //ScrollViewdelegate委托协议的实现方法(当屏幕滚动时,会回调该方法)
        let offset = scrollView.contentOffset //内容视图的原点到滚动视图偏移的点
        self.pageControl.currentPage = Int(offset.x / S_Width)
        //用偏移距离除以屏幕宽度,得出当前页面是第几屏,并通过高亮点显示到界面上
    }
    //切换当前页面
 @objc func changePage(_ sender:AnyObject){
        UIView.animate(withDuration: 0.3,animations: {
            let whichPage = self.pageControl.currentPage
            self.scrollView.contentOffset = CGPoint(x: Int(S_Width) * whichPage, y: 0)
            
        })
    }

} 

效果如下图所示:
视图控制器与导航模式
视图控制器与导航模式
视图控制器与导航模式

3.2 基于电子书导航的实现

在基于电子书导航实现的应用中,需要的类和协议有UIPageViewControllerDataSourse协议、UIPageViewControllerDelegate协议和UIPageViewController类。其中UIPageViewController类没有对应的视图类。
UIPageViewControllerDataSourse数据源协议中必须实现的方法有以下两个:

  • pageViewController:viewControllerBeforeViewController:。返回当前视图控制器之前的视图控制器,用于上一个页面的显示。
  • pageViewController:viewControllerAfterViewController:。返回当前视图控制器之后的视图控制器,用于下一个页面的显示。
    在UIPageViewControllerDelegate委托协议中,最重要的方法为pageViewController:spineLocationForInterfaceOrientation:,它根据屏幕旋转方向设置书脊位置(spineLocation)和初始化首页。
    UIPageViewController*有两个常用的属性**:双面显示(double Sided)和书脊位置(spine Location)**
  • 双面显示:doubleSided设置为true,则翻起偶数页面会在背面显示。为false时为单面显示,即用户在页面翻起时,看到页面的背面是当前页面透过去的,与当前内容是相反的镜像。
  • 书脊位置:也是很重要的属性,但是它是只读的。书脊位置由枚举UIPageViewControllerSpineLocation定义,该枚举类型下的成员变量如下所示:
    min:定义了书脊位置在书的最左边(或最上面)
    max:定义了书脊位置在书的最右边(或最下面)
    mid:定义了书脊位置在书的中间。
上一篇:五、 ImageView图片控件


下一篇:2021-11-09