iOS-自定義導(dǎo)航欄后側(cè)滑返回失效
從iOS7開始,系統(tǒng)為UINavigationController提供了一個interactivePopGestureRecognizer用于右滑返回(pop),但是,如果自定了當前視圖控制器leftBarButtonItem,或自定義導(dǎo)航欄后該手勢就失效了。
解決方法:
自定義UINavigationController,實現(xiàn)其代理方法:
#import "DYNavigationController.h"
@interface DYNavigationController () <UINavigationControllerDelegate>
@property (nonatomic,strong) id popDelegate;
@end
@implementation DYNavigationController
- (void)viewDidLoad {
[super viewDidLoad];
//代理
self.popDelegate = self.interactivePopGestureRecognizer.delegate;
self.delegate = self;
}
#pragma UINavigationControllerDelegate方法
- (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated {
//實現(xiàn)滑動返回功能
//清空滑動返回手勢的代理就能實現(xiàn)
self.interactivePopGestureRecognizer.delegate = viewController == self.viewControllers[0]? self.popDelegate : nil;
}
@end
控制器添加ScrollView后側(cè)滑返回失效
大概思路就是,既然你攔截了我的手勢,那我就要想辦法讓手勢傳遞下去,不被你攔截,所以最后的解決辦法就是對Scrollview加個Category,重寫它代理的方法,讓手勢能夠傳遞下去
解決方法:
自定義UIScrollView的分類,重寫代理方法:
#import "UIScrollView+DY.h"
@implementation UIScrollView (DY)
#define KScreenHeight [UIScreen mainScreen].bounds.size.height //屏幕的高度
#define KScreenWidth [UIScreen mainScreen].bounds.size.width // 屏幕的寬度
//是否支持多手勢觸發(fā),返回YES,則可以多個手勢一起觸發(fā)方法,返回NO則為互斥.
//是否允許多個手勢識別器共同識別,一個控件的手勢識別后是否阻斷手勢識別繼續(xù)向下傳播,默認返回NO;如果為YES,響應(yīng)者鏈上層對象觸發(fā)手勢識別后,如果下層對象也添加了手勢并成功識別也會繼續(xù)執(zhí)行,否則上層對象識別后則不再繼續(xù)傳播
//一句話總結(jié)就是此方法返回YES時,手勢事件會一直往下傳遞,不論當前層次是否對該事件進行響應(yīng)。
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer {
if ([self panBack:gestureRecognizer]) {
return YES;
}
return NO;
}
//location_X可自己定義,其代表的是滑動返回距左邊的有效長度
- (BOOL)panBack:(UIGestureRecognizer *)gestureRecognizer {
//是滑動返回距左邊的有效長度
int location_X = 0.15*KScreenWidth;
if (gestureRecognizer == self.panGestureRecognizer) {
UIPanGestureRecognizer *pan = (UIPanGestureRecognizer *)gestureRecognizer;
CGPoint point = [pan translationInView:self];
UIGestureRecognizerState state = gestureRecognizer.state;
if (UIGestureRecognizerStateBegan == state ||UIGestureRecognizerStatePossible == state) {
CGPoint location = [gestureRecognizer locationInView:self];
//這是允許每張圖片都可實現(xiàn)滑動返回
//int temp1 = location.x;
//int temp2 = KScreenWidth;
//NSInteger XX = temp1 % temp2;
//if (point.x > 0 && XX < location_X) {
// return YES;
//}
//下面的是只允許在第一張時滑動返回生效
if (point.x > 0 && location.x < location_X && self.contentOffset.x <= 0) {
return YES;
}
}
}
return NO;
}
- (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer {
if ([self panBack:gestureRecognizer]) {
return NO;
}
return YES;
}
@end