【轉載請註明出處】
之前在看iOS7滑動返回時,發現了一個iOS6 SDK下的第三方實現,今天偶然間發現了作者在其部落格上對該實現的一些心得,讀來深覺之前的思考太過膚淺,許多實際的問題沒有考慮到。帖子連結如下:
http://www.vinqon.com/codeblog/?detail/11108
工程github地址如下:
https://github.com/vinqon/MultiLayerNavigation
在帖子中作者貼出了實現程式碼,此處只說明一下思路和可能產生不相容的情況,貼別人程式碼這麼Low的行為還是算了。
程式碼中是通過繼承UINavigationController,並在其中新增了一個UIPanGestureRecognizer實現的,大體思路如下:
1、過載pushViewController和popViewController,在push之前,擷取當前介面儲存為UIImage,在pop之前,移除最近儲存的截圖;
2、在UIPanGestureRecognizer的target中,做4件事:
(1)當手勢觸發時(panGestureRecognizer.state == UIGestureRecognizerStateBegan),把最近儲存的截圖(通常來說即上一級介面的截圖,特殊情況見下文)放到當前viewController.view的下方;
(2)當手指在螢幕上移動時,相應地修改當前viewController.view.frame,使其下方的截圖逐漸露出;
(3)當手勢結束時(panGestureRecognizer.state ==UIGestureRecognizerStateEnded),呼叫過載的popViewController;
(4)當手勢取消時(panGestureRecognizer.state ==UIGestureRecognizerStateEnded),將當前viewController.view.frame恢復原樣。
如此就基本實現了滑動返回的手勢支援,要進一步加強的,應該說有兩方面:
1、效果上儘可能接近iOS7原生手勢的體驗:
(1)判斷手勢觸發時的位置,只在螢幕邊緣才起作用【Mark:沒有找到具體的數字說明觸發的範圍】;
(2)手勢觸發時修改當前viewController.view及其所有子view的透明度;
(3)導航欄的漸變:當前介面的導航欄漸漸淡出,上一級選單的導航欄的漸漸清晰。事實上上一級選單的整個介面都應有一個漸漸清晰的效果,只是導航欄作為多個ViewController共享的部分,需要同時顯示兩種效果確實需要一定當量的腦細胞。(作者在帖子中描述了網易新聞和新浪微博各自的實現)此外,預設的導航欄中生成的左上角返回鍵,其文字就是上一級選單的主標題,這種情況下“返回會漸漸變成主標題”。
2、實現中沒有考慮的一些因素:
(1)setViewControllers的支援:一次性向棧中加入多個ViewController時,僅僅過載push就顯得無能為力了;
(2)記憶體的控制:每進入一級介面都需要擷取上一級介面,當層級較多時對記憶體的壓力不小,似乎可以通過降低擷取圖的解析度來達到一定的改善。將截圖儲存到disk上也可以,只是在快速進出時,是否會造成卡頓尚未驗證。
(3)對介面中可能造成手勢衝突的相容:比如UIScrollView就內建了一個panGestureRecognizer,還有UIWebView的手勢支援。
(4)當前介面可能能夠造成上一級介面發生更改:比如更換主題這樣的功能,以截圖的方式來做的話,基本無解。
(5)截圖的方式是直接擷取viewController.view,沒有考慮tabbar等情況,在有tabbar的情況下,下方會有一道黑邊。
【參考】
1、iOS頁面右滑返回互動實現方案