简单的拖动手势控制侧拉view显示

时间:2023-03-08 22:40:04
简单的拖动手势控制侧拉view显示

通过 UIPanGestureRecognizer  手势来控制侧拉view的显示

在QHLViewController.m文件中,先添加一些宏定义和参数等等。

#define QHLAnimatingDuration 0.5
#define QHLMainViewMaxOffsetX 250
#define QHLLeftViewOriginX -50 typedef enum{
QHLViewControllerStateClosed = ,
QHLViewControllerStateOpening,
QHLViewControllerStateOpened,
QHLViewControllerStateClosing
}QHLViewControllerState; @interface QHLViewController ()<UITableViewDataSource> @property (nonatomic, assign) CGPoint point;
@property (nonatomic, assign) CGPoint location;
@property (nonatomic, strong) UIView *leftV;
@property (nonatomic, strong) UIView *mainV; @property (nonatomic, strong) UITapGestureRecognizer *tapGesTureR;
@property (nonatomic, strong) UIPanGestureRecognizer *panGesTureR;
@property (nonatomic, assign) QHLViewControllerState state;
@end

在viewWillAppear:(BOOL)animated方法中,创建需要的leftV和mainV这两个view

- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated]; //创建并设置leftV的属性
UITableView *leftV = [[UITableView alloc] initWithFrame:CGRectMake(QHLLeftViewOriginX, , self.view.bounds.size.width, self.view.bounds.size.height)];
leftV.backgroundColor = [UIColor whiteColor];
leftV.dataSource = self;
self.leftV = leftV;
[self.view addSubview:leftV]; //创建并设置mainView的属性
UIView *mainV = [[UIView alloc] initWithFrame:self.view.bounds];
mainV.backgroundColor = [UIColor purpleColor];
self.mainV = mainV;
[self.view addSubview:mainV];
}

在viewDidLoad中先设置自身的状态为关闭,创建拖动和点击的手势,并且先添加拖动手势到控制器

- (void)viewDidLoad {
[super viewDidLoad];
//设置默认状态下自身控制器的state状态
self.state = QHLViewControllerStateClosed; //添加拖动手势
self.panGesTureR = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(observePanGestureRecognizer:)];
[self.view addGestureRecognizer:self.panGesTureR]; //设置点击手势
self.tapGesTureR =[[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(observeTapGesTureRecognizer:)];
}

根据手势的不同状态来实现手势的触发方法,在不同手势状态下,给自身设置不同的state。

/**
* 拖动手势的实现方法
*/
- (void)observePanGestureRecognizer:(UIPanGestureRecognizer *)panGestureRecognizer {
//获取当前拖动手势的状态
UIGestureRecognizerState state = panGestureRecognizer.state; CGPoint location = [panGestureRecognizer locationInView:self.view]; //位置 CGRect main = self.mainV.frame;
CGRect left = self.leftV.frame; switch (state) {
//手势开始时候
case UIGestureRecognizerStateBegan:
//获取开始位置的point
self.point = location; //根据手势触发之前的自身状态来设置现在的状态
if (self.state == QHLViewControllerStateClosed) {
self.state = QHLViewControllerStateOpening; //opening
} else {
self.state = QHLViewControllerStateClosing; //closing
}
break; //手势变化时候
case UIGestureRecognizerStateChanged:
{
//偏移量x
CGFloat offsetX = ; //下面2种情况,offsetX都是大于等于0的
if (self.state == QHLViewControllerStateOpening) { //此时自身状态只有QHLViewControllerStateOpening和QHLViewControllerStateClosing
offsetX = location.x - self.point.x;
} else {
offsetX = QHLMainViewMaxOffsetX - (self.point.x - location.x);
} if (offsetX > QHLMainViewMaxOffsetX) { left.origin.x = ;
main.origin.x = QHLMainViewMaxOffsetX;
} else if (offsetX < ) { left.origin.x = QHLLeftViewOriginX;
main.origin.x = ;
}else { main.origin.x = offsetX;
left.origin.x = QHLLeftViewOriginX - offsetX * QHLLeftViewOriginX / QHLMainViewMaxOffsetX;
}
self.mainV.frame = main;
self.leftV.frame = left;
break;
}
//手势结束时候
case UIGestureRecognizerStateEnded:
{ //结束之前的那一刻,只会有2种状态 QHLViewControllerStateOpening 和 QHLViewControllerStateClosing
CGFloat endX = main.origin.x; if (self.state == QHLViewControllerStateOpening) { // x 取值 >= 0 if (endX == QHLMainViewMaxOffsetX) { // 结束时候的 x 取最大值 self.state = QHLViewControllerStateOpened;
} else if (endX > QHLMainViewMaxOffsetX / ) { // 结束时候的 x 大于 最大值的 1/2 [self animatingOpen];
} else { // 结束时候的 x 小于 最大值的 1/2 [self animatingClose];
} } else { // x 取值 0 ~ 250 if (endX > QHLMainViewMaxOffsetX / ) {
[self animatingOpen];
} else {
[self animatingClose];
}
}
break;
}
}
}

点击手势要等mainV偏移量达到最大的时候才添加进去!!!

/**
* 点击手势的实现方法
*/
- (void)observeTapGesTureRecognizer:(UITapGestureRecognizer *)tapGestureRecognizer {
[UIView animateWithDuration:QHLAnimatingDuration animations:^{
self.mainV.frame = [UIScreen mainScreen].bounds;
self.leftV.frame = CGRectMake(QHLLeftViewOriginX, , self.view.frame.size.width, self.view.frame.size.height);
} completion:^(BOOL finished) {
self.state = QHLViewControllerStateClosed;
}];
}

当mainV的偏移量达到一定要求后就会调用下面2个方法

当以动画形式打开 在完成时候,添加点击手势

当以动画形式关闭 在完成时候,移除点击手势

/**
* 以动画形式打开
*/
- (void)animatingOpen {
CGRect main = self.mainV.frame; [UIView animateWithDuration:0.5 delay: usingSpringWithDamping:0.7 initialSpringVelocity:0.7 options:UIViewAnimationOptionAllowAnimatedContent animations:^{
self.mainV.frame = CGRectMake(QHLMainViewMaxOffsetX, , main.size.width, main.size.height);
self.leftV.frame = self.view.bounds;
} completion:^(BOOL finished) {
//设置state状态
self.state = QHLViewControllerStateOpened;
//添加点击手势
[self.mainV addGestureRecognizer:self.tapGesTureR];
}];
} /**
* 以动画形式关闭
*/
- (void)animatingClose {
CGRect main = self.mainV.frame; [UIView animateWithDuration:0.5 delay: usingSpringWithDamping:1.0 initialSpringVelocity:0.7 options:UIViewAnimationOptionAllowAnimatedContent animations:^{
self.mainV.frame = self.view.bounds;
self.leftV.frame =CGRectMake(QHLLeftViewOriginX, , main.size.width, main.size.height);
} completion:^(BOOL finished) {
//设置state状态
self.state = QHLViewControllerStateClosed;
//移除点击手势
[self.mainV removeGestureRecognizer:self.tapGesTureR];
}];
}

侧拉leftV的dataSource方法

#pragma mark - table view delegate & data source
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return ;
} - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *ID = @"cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID]; if (!cell) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:ID];
} cell.textLabel.text = [NSString stringWithFormat:@"Message - %ld",(long)indexPath.row]; return cell;
}

对于QQ左上角按钮点击之后弹出的设置页面   导航控制器的bar和底部的tabBar会跟随着移动,有知道的大牛给点思路!!!!

渣渣已经脑细胞死光了v_v