見出し画像

UITabViewControllerとUIPageViewControllerのスワイプ動作制御方法

みなさん、UITabViewControllerとUIPageViewControllerを同時使用した時に全てのタブに対して、PageViewのスワイプ動作が効いてしまうので例えば、TableViewのセル横スライドなどを実装した時になかなか思うような動作にならないと思います。その時の対処法です。

TabViewController

override func viewDidLoad() {
        super.viewDidLoad()
        let center = NotificationCenter.default
        center.addObserver(self, selector: #selector(userBaseScroll(center:)), name: Notification.Name("USERBASESCROLL"), object: nil)

    }




// ページによってスワイプ移動を禁止にするためのメソッド
    @objc func userBaseScroll(center: Notification) {
        if let value = center.userInfo {
            if let bool = value["bool"] {
                let isScroll = bool as! Bool
                for view in self.view.subviews {
                    if view.isKind(of: UIScrollView.classForCoder()) {
                        let scroll = view as! UIScrollView
                        scroll.isScrollEnabled = isScroll
                    }
                }
            }
        }
    }

Notificationに登録されているuserBaseScrollメソッドの解説

for view in self.view.subviews {
                    if view.isKind(of: UIScrollView.classForCoder()) {
                        let scroll = view as! UIScrollView
                        scroll.isScrollEnabled = isScroll
                    }
                }

上記のメソッドは、TabViewControllerのSuViewをfor文によって目的のものを取得してきています。ここでいう目的のメソッドはUIScrollViewをクラスに持つものになります。
そこで、

  if view.isKind(of: UIScrollView.classForCoder()) {
                        let scroll = view as! UIScrollView
                        scroll.isScrollEnabled = isScroll
                    }

上記コードで、UIScrollViewがクラスなのかを調べます。ここでif文をかまさないと、下の let scroll = view as! UIScrollViewでエラーとなってしまう可能性がありますので、必ずif文で確認をした方が安全だと思います。

あとは、必要に応じて、各画面にNotificationに登録をされているメソッドを必要な場所で、定義していただくと制御をすることができます。

例)AViewControllerが表示された時、そして、画面を戻る時に制御をかけたい場合は、viewWillAppearでtrueをuserInfoによって渡してあげるとスワイプ動作が禁止です。

override func viewWillAppear(_ animated: Bool) {
    NotificationCenter.default.post(name: Notification.Name("USERBASESCROLL"), object: nil, userInfo: ["bool": false])
}

そして画面を戻る時の制御はviewWillDisappearに書いていただけたらと思います。

override func viewWillDisappear(_ animated: Bool) {
        NotificationCenter.default.post(name: Notification.Name("USERBASESCROLL"), object: nil, userInfo: ["bool": true])
    }

自分の備忘録かねがね書いたので文章がとても拙いかもしれませんが、お役に立てれば幸いですorz



この記事が気に入ったらサポートをしてみませんか?