Swift-QQ最新版抽屜側滑和彈框視圖

導讀

  • 簡單用Swift寫了一個抽屜效果,可以直接使用并且簡單;
  • 很多軟件都運了抽屜效果咱扣,比如qq的左抽屜,英雄聯(lián)盟,滴滴打車,和uber等等都運用了抽屜;
  • GitHub上有代表性的是MMDrawerController.

效果

image.gif

iOS抽屜式結構實現(xiàn)分析

  • 主要是在控制器的View上添加了兩個View,一個左側leftView和一個mainView躯舔。這里我們自定義一個DrawerViewController,init(mainVC: UIViewController, leftMenuVC: UIViewController, leftWidth: CGFloat)設置兔港,一個mainVC庸毫,一個leftMenuVC,和一個寬度,將mainVC和leftMenuVC的view添加到controller的view上(menuVC的view在下面)衫樊。
        view.addSubview(leftMenuVC.view)
        view.addSubview(mainVC.view)
        
        addChildViewController(leftMenuVC)
        addChildViewController(mainVC)
  • 然后首先實現(xiàn)點擊方法openLeftMenu和closeLeftMenu(這兩個方法主要是計算mainVC的view的位置)方便以后調用飒赃。
//MARK: - 打開左側菜單
    func openLeftMenu() {
        
        UIView.animate(withDuration: 0.25, delay: 0, options: UIViewAnimationOptions.curveLinear, animations: {
        
            self.leftVC?.view.transform = CGAffineTransform.identity
            self.mainVC?.view.transform = CGAffineTransform(translationX: self.maxWidth, y: 0)
            
        
        }, completion: {
        
            (finish: Bool) -> () in
            
            self.mainVC?.view.addSubview(self.coverBtn)
            
        })
        
    }
    
    //MARK: - 關閉左側菜單
    func closeLeftMenu() {
        
        UIView.animate(withDuration: 0.25, delay: 0, options: UIViewAnimationOptions.curveLinear, animations: {
            
            self.leftVC?.view.transform = CGAffineTransform(translationX: -self.maxWidth, y: 0)
            self.mainVC?.view.transform = CGAffineTransform.identity
            
            
        }, completion: {
            
            (finish: Bool) -> () in
            
            self.coverBtn.removeFromSuperview()
            
        })
        
        
    }
  • 最后給mainVC的view添加屏幕邊緣手勢,實現(xiàn)mainVC的view跟隨手指移動科侈。
    循環(huán)遍歷view給每一個一級視圖添加手勢
for childViewController in (mainVC?.childViewControllers)! {
            
            addScreenEdgePanGestureRecognizerToView(view: childViewController.view)
            
        }
//MARK: - 添加屏幕邊緣手勢
    private func addScreenEdgePanGestureRecognizerToView(view: UIView) {
        
        let pan = UIScreenEdgePanGestureRecognizer(target: self, action: #selector(edgPanGesture(_:)))
        pan.edges = UIRectEdge.left
        view.addGestureRecognizer(pan)
        
    }

  • 在平移手勢調用的方法中载佳,通過偏移量來確定mainView的frame,實現(xiàn)動畫效果

    • 首先通過pan.translation(in: pan.view).x方法獲取偏移量,通過偏移量的正負確定拖動的方向
    • 當手指松開后需要根據mainView的x值確定其視圖是定位到原始位置還是其縮放的位置
  • 打開手勢

//MARK: - 屏幕左邊緣手勢
    func edgPanGesture(_ pan: UIScreenEdgePanGestureRecognizer) {
        
        let offsetX = pan.translation(in: pan.view).x
        
        if pan.state == UIGestureRecognizerState.changed && offsetX <= maxWidth {
            
            mainVC?.view.transform = CGAffineTransform(translationX: max(offsetX, 0), y: 0)
            leftVC?.view.transform = CGAffineTransform(translationX: -maxWidth + offsetX, y: 0)
            
        } else if pan.state == UIGestureRecognizerState.ended || pan.state == UIGestureRecognizerState.cancelled || pan.state == UIGestureRecognizerState.failed {
            
            if offsetX > screenW * 0.5 {
                
                openLeftMenu()
                
            } else {
                
                closeLeftMenu()
            }
            
        }
        
    }

  • 關閉遮蓋手勢
//MARK: - 遮蓋按鈕手勢
    func panCloseLeftMenu(_ pan: UIPanGestureRecognizer) {
        
        let offsetX = pan.translation(in: pan.view).x
        if offsetX > 0 {return}
        
        if pan.state == UIGestureRecognizerState.changed && offsetX >= -maxWidth {
            
            let distace = maxWidth + offsetX
            
            mainVC?.view.transform = CGAffineTransform(translationX: distace, y: 0)
            leftVC?.view.transform = CGAffineTransform(translationX: offsetX, y: 0)
            
        } else if pan.state == UIGestureRecognizerState.ended || pan.state == UIGestureRecognizerState.cancelled || pan.state == UIGestureRecognizerState.failed {
            
            if offsetX > screenW * 0.5 {
                
                openLeftMenu()
                
            } else {
                
                closeLeftMenu()
            }
            
        }
        
    }

UIPresentationController簡介

  • UIPresentationController是 iOS8 新增的一個API臀栈,蘋果的官方定義是:對象為所呈現(xiàn)的視圖控制器提供高級視圖的轉換管理(從呈現(xiàn)視圖控制器的時間直到它被消除期間);
  • iOS 8以前就是自定義view,去畫一個三角和長方形;
  • 簡單直接的方法用圖片

直接貼代碼不講廢話

@IBAction func showAlert(_ sender: UIBarButtonItem) {
        
        let popVC = PopViewController()
        popVC.modalPresentationStyle = UIModalPresentationStyle.popover
        popVC.popoverPresentationController?.barButtonItem = sender
        popVC.popoverPresentationController?.delegate = self
        //可控制三角顏色
        popVC.popoverPresentationController?.backgroundColor = UIColor.white
        present(popVC, animated: true, completion: nil)
        
    }


    func adaptivePresentationStyle(for controller: UIPresentationController) -> UIModalPresentationStyle {
        return UIModalPresentationStyle.none
    }
    
    func popoverPresentationControllerShouldDismissPopover(_ popoverPresentationController: UIPopoverPresentationController) -> Bool {
        return true
    }

具體代碼可以從這里下載,后續(xù)還有更實用的功能.

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
  • 序言:七十年代末蔫慧,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子权薯,更是在濱河造成了極大的恐慌姑躲,老刑警劉巖,帶你破解...
    沈念sama閱讀 221,548評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件盟蚣,死亡現(xiàn)場離奇詭異黍析,居然都是意外死亡,警方通過查閱死者的電腦和手機屎开,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,497評論 3 399
  • 文/潘曉璐 我一進店門阐枣,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人奄抽,你說我怎么就攤上這事蔼两。” “怎么了逞度?”我有些...
    開封第一講書人閱讀 167,990評論 0 360
  • 文/不壞的土叔 我叫張陵额划,是天一觀的道長。 經常有香客問我档泽,道長锁孟,這世上最難降的妖魔是什么彬祖? 我笑而不...
    開封第一講書人閱讀 59,618評論 1 296
  • 正文 為了忘掉前任,我火速辦了婚禮品抽,結果婚禮上,老公的妹妹穿的比我還像新娘甜熔。我一直安慰自己圆恤,他們只是感情好,可當我...
    茶點故事閱讀 68,618評論 6 397
  • 文/花漫 我一把揭開白布腔稀。 她就那樣靜靜地躺著盆昙,像睡著了一般。 火紅的嫁衣襯著肌膚如雪焊虏。 梳的紋絲不亂的頭發(fā)上淡喜,一...
    開封第一講書人閱讀 52,246評論 1 308
  • 那天,我揣著相機與錄音诵闭,去河邊找鬼炼团。 笑死,一個胖子當著我的面吹牛疏尿,可吹牛的內容都是我干的瘟芝。 我是一名探鬼主播,決...
    沈念sama閱讀 40,819評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼褥琐,長吁一口氣:“原來是場噩夢啊……” “哼锌俱!你這毒婦竟也來了?” 一聲冷哼從身側響起敌呈,我...
    開封第一講書人閱讀 39,725評論 0 276
  • 序言:老撾萬榮一對情侶失蹤贸宏,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后磕洪,有當地人在樹林里發(fā)現(xiàn)了一具尸體吭练,經...
    沈念sama閱讀 46,268評論 1 320
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 38,356評論 3 340
  • 正文 我和宋清朗相戀三年褐鸥,在試婚紗的時候發(fā)現(xiàn)自己被綠了线脚。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 40,488評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡叫榕,死狀恐怖浑侥,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情晰绎,我是刑警寧澤寓落,帶...
    沈念sama閱讀 36,181評論 5 350
  • 正文 年R本政府宣布,位于F島的核電站荞下,受9級特大地震影響伶选,放射性物質發(fā)生泄漏史飞。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,862評論 3 333
  • 文/蒙蒙 一仰税、第九天 我趴在偏房一處隱蔽的房頂上張望构资。 院中可真熱鬧,春花似錦陨簇、人聲如沸吐绵。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,331評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽己单。三九已至,卻和暖如春耙饰,著一層夾襖步出監(jiān)牢的瞬間纹笼,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,445評論 1 272
  • 我被黑心中介騙來泰國打工苟跪, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留廷痘,地道東北人。 一個月前我還...
    沈念sama閱讀 48,897評論 3 376
  • 正文 我出身青樓削咆,卻偏偏與公主長得像牍疏,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子拨齐,可洞房花燭夜當晚...
    茶點故事閱讀 45,500評論 2 359

推薦閱讀更多精彩內容