iOS实现左右拖动抽屉效果
本文实例介绍了iOS实现左右拖动抽屉效果,具体内容如下
利用了触摸事件滑动touchesMoved:来触发左右视图的出现和消失利用loadView方法中添加view在self.view载入前就把左右中View都设置好frame每一个方法都由单独的功能。
#import"DarwViewController.h" @interfaceDarwViewController() @property(nonatomic,weak)UIView*leftView; @property(nonatomic,weak)UIView*rightView; @property(nonatomic,weak)UIView*mainView; /** *动画是否进行 */ @property(nonatomic,assign)BOOLanimating; @end @implementationDarwViewController -(void)viewDidLoad{ [superviewDidLoad]; } -(void)loadView { self.view=[[UIViewalloc]initWithFrame:[UIScreenmainScreen].bounds]; //左边view UIView*leftView=[[UIViewalloc]initWithFrame:self.view.frame]; [self.viewaddSubview:leftView]; leftView.backgroundColor=[UIColorredColor]; self.leftView=leftView; //右边View UIView*rightView=[[UIViewalloc]initWithFrame:self.view.frame]; [self.viewaddSubview:rightView]; rightView.backgroundColor=[UIColorblueColor]; self.rightView=rightView; //主页面 UIView*mainView=[[UIViewalloc]initWithFrame:self.view.frame]; [self.viewaddSubview:mainView]; mainView.backgroundColor=[UIColoryellowColor]; self.mainView=mainView; //KVO监听 [self.mainViewaddObserver:selfforKeyPath:@"frame"options:NSKeyValueObservingOptionNewcontext:nil]; } /** *KVO回调方法当mainViewFrame值改变时触发 * *@paramkeyPath<#keyPathdescription#> *@paramobject<#objectdescription#> *@paramchange<#changedescription#> *@paramcontext<#contextdescription#> */ -(void)observeValueForKeyPath:(NSString*)keyPathofObject:(id)objectchange:(NSDictionary<NSString*,id>*)changecontext:(void*)context { if(self.animating)return;//如果mainView正在动画就不执行 if(self.mainView.frame.origin.x>0) { //X>0就隐藏右边View显示左边View self.rightView.hidden=YES; self.leftView.hidden=NO; } elseif(self.mainView.frame.origin.x<0) { //X<0就隐藏左边View显示右边VIew self.leftView.hidden=YES; self.rightView.hidden=NO; } } #pragmamark--触摸事件 -(void)touchesMoved:(NSSet<UITouch*>*)toucheswithEvent:(UIEvent*)event { //获得触摸对象 UITouch*touch=[touchesanyObject]; //获得当前触摸点 CGPointcurrentPoint=[touchlocationInView:self.view]; //获得上一个触摸点 CGPointpreviousPoint=[touchpreviousLocationInView:self.view]; //计算x方向的偏移量 CGFloatoffsetX=currentPoint.x-previousPoint.x; //根据x的偏移量计算y的偏移量 self.mainView.frame=[selfrectWithOffsetX:offsetX]; } #definescreenW[UIScreenmainScreen].bounds.size.width #definescreenH[UIScreenmainScreen].bounds.size.height /** *计算主视图的frame * *@paramoffsetXx的偏移量 * *@return偏移后新的frame */ -(CGRect)rectWithOffsetX:(CGFloat)offsetX { //Y轴的偏移量 CGFloatoffsetY=(screenH*1/5)*(offsetX/screenW); //比例:(用于宽高的缩放) CGFloatscale=(screenH-offsetY*2)/screenH; if(self.mainView.frame.origin.x<0) { //如果x是负数及左边View要显示 //比例就要设为比1小 scale=2-scale; } //获取当前mainView的frame CGRectframe=self.mainView.frame; //重新设置mainView的frame值 frame.size.width=frame.size.width*scale>screenW?screenW:frame.size.width*scale; frame.size.height=frame.size.height*scale>screenH?screenH:frame.size.height*scale; frame.origin.x+=offsetX; frame.origin.y=(screenH-frame.size.height)*0.5; //返回偏移后新的frame returnframe; } #definemaxRightX(screenW*0.8) #definemaxLeftX(-screenW*0.6) -(void)touchesEnded:(NSSet<UITouch*>*)toucheswithEvent:(UIEvent*)event { CGFloattargetX=0; //如果松手的那一下当前mainVIew的x大于屏幕的一半 if(self.mainView.frame.origin.x>screenW*0.5) { //向右边定位 targetX=maxRightX; } //如果松手的那一下当前mainVIew的最大X值小于屏幕的一半 elseif(CGRectGetMaxX(self.mainView.frame)<screenW*0.5) { //向左边定位 targetX=maxLeftX; } //计算偏移量 CGFloatoffsetX=targetX-self.mainView.frame.origin.x; self.animating=YES; [UIViewanimateWithDuration:0.4animations:^{ if(targetX==0) { //如果targetX==0复位 self.mainView.frame=self.view.frame; } else { //如果targetX!=0那就到指定位置 self.mainView.frame=[selfrectWithOffsetX:offsetX]; } }completion:^(BOOLfinished){ self.animating=NO; }]; } @end
以上就是本文的全部内容,希望对大家的学习有所帮助。