[swift4] UIPageViewControllerでニュースアプリっぽいページング機能を実装

環境:xcode9 , swift4

ニュースアプリっぽく、画面上にページング機能を実装したく、PagingMenuControllerやら、XLPagerTabStripやらを導入してみたものの、podファイルがなぜか読み込めず、UIPageViewControllerを使用してswiftネイティブ機能で実装。

目次

ContainerViewにPageViewControllerをEmbed

StoryboardでViewControllerを配置、その上にContainerViewを適切な大きさで配置。

ContainerViewを配置すると自動的についてくるEmbedされてくるViewは不要なので、削除。

PageViewControllerを配置し、ContainerViewから矢印でEmbed。

ViewControllerには画面切り替えのUISegmentedControlを上部に配置。(あとでサイズや色を変えることができる)

スクリーンショット 2017-12-26 21.41.28

FirstViewControllerとSecondViewControllerを作成

StoryBoardにそれぞれのページ内容を表示するFirstViewControllerとSecondViewControllerを配置。

それぞれのViewControllerのIdentityのStoryBoard IDに「First」「Second」と入力。

スクリーンショット 2017-12-26 22.01.43

 

コード実装

MainViewController.swiftを新たに作成し、Storyboardの最初のViewControllerと紐付け。

MainViewController.swiftに以下のコードを実装

class MainViewController: UIViewController, UIPageViewControllerDataSource, UIPageViewControllerDelegate {
 
 let idList: [String] = ["first", "second"]
 
 var pageViewController: UIPageViewController!
 var viewControllers: [UIViewController] = []
 
 @IBOutlet weak var selectTab: UISegmentedControl!
 
 override func viewDidLoad() {
  super.viewDidLoad()
 
  selectTab.setTitle("1枚目", forSegmentAt: 0)
  selectTab.setTitle("2枚目", forSegmentAt: 1)
 
  for id in idList {
   viewControllers.append((storyboard?.instantiateViewController(withIdentifier: id))!)
  }
 
  pageViewController = childViewControllers[0] as! UIPageViewController
  pageViewController.setViewControllers([viewControllers[0]], direction: .forward, animated: true, completion: nil)
  pageViewController.dataSource = self
  pageViewController.delegate = self
 }
 
 override func didReceiveMemoryWarning() {
  super.didReceiveMemoryWarning()
 }
 
 func pageViewController(_ pageViewController: UIPageViewController, viewControllerBefore viewController: UIViewController) -> UIViewController? {
  let index = idList.index(of: viewController.restorationIdentifier!)!
  if (index > 0) {
   return storyboard!.instantiateViewController(withIdentifier: idList[index - 1])
  }
   return nil
 }
 
 func pageViewController(_ pageViewController: UIPageViewController, viewControllerAfter viewController: UIViewController) -> UIViewController? {
  let index = idList.index(of: viewController.restorationIdentifier!)!
  if (index < idList.count - 1) {
   return storyboard!.instantiateViewController(withIdentifier: idList[index + 1])
  }
  return nil
 }
 
 func pageViewController(_ pageViewController: UIPageViewController, didFinishAnimating finished: Bool, previousViewControllers: [UIViewController], transitionCompleted completed: Bool) {
  let index = idList.index(of: (pageViewController.viewControllers?.first!.restorationIdentifier)!)
  self.selectTab.selectedSegmentIndex = index!
 }
 
 @IBAction func selectedTab(_ sender: UISegmentedControl) {
  switch sender.selectedSegmentIndex {
   case 0:
    pageViewController.setViewControllers([viewControllers[0]], direction: .reverse, animated: true, completion: nil)
    break
   case 1:
    pageViewController.setViewControllers([viewControllers[1]], direction: .forward, animated: true, completion: nil)
    break
   default:
    return
   }
 }
 
}

 

これで画面をフリックするかセグメントボタンを押すことで画面を切り替えることができる。

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です