本文執行個體為大家分享了iOS抽屜效果開發執行個體,供大家參考,具體內容如下
在顯示在視窗的控制器上添加三個view(如果只需要往一邊滑動就只加2個view)
先聲明三個view
#import "ViewController.h" @interface ViewController ()@property(nonatomic, weak) UIView *mainV;@property(nonatomic, weak) UIView *leftV;@property(nonatomic, weak) UIView *rightV;@end
添加view到控制器view上
#pragma mark - 添加子控制項- (void)setUpChildViews { UIView *leftV = [[UIView alloc]initWithFrame:self.view.bounds]; leftV.backgroundColor = [UIColor orangeColor]; [self.view addSubview:leftV]; _leftV = leftV; UIView *rightV = [[UIView alloc]initWithFrame:self.view.bounds]; rightV.backgroundColor = [UIColor groupTableViewBackgroundColor]; [self.view addSubview:rightV]; _rightV = rightV; UIView *mainV = [[UIView alloc]initWithFrame:self.view.bounds]; mainV.backgroundColor = [UIColor yellowColor]; [self.view addSubview:mainV]; _mainV = mainV;} - (void)viewDidLoad { [super viewDidLoad]; //添加子控制項 [self setUpChildViews]; //添加Pan手勢 UIPanGestureRecognizer *pan = [[UIPanGestureRecognizer alloc]initWithTarget:self action:@selector(pan:)]; [self.view addGestureRecognizer:pan]; //添加點按手勢,在主視圖上任意位置點擊回到螢幕開始位置 UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc]initWithTarget:self action:@selector(tap)]; [self.view addGestureRecognizer:tap]; }
#pragma mark - 手勢識別方法#define targetL -230#define targetR 200#define screenW [UIScreen mainScreen].bounds.size.width- (void)pan:(UIPanGestureRecognizer *)pan { //擷取手勢移動的位置 CGPoint tranP = [pan translationInView:self.view]; //擷取x的位移量 CGFloat offsetX = tranP.x; //修改mainV的frame _mainV.frame = [self frameWithOffsetX:offsetX]; //判斷mainV的x是否大於0 [self observeValueForKeyPath:nil ofObject:nil change:nil context:nil]; //複位 [pan setTranslation:CGPointZero inView:self.view]; //判斷當手勢結束的時候,定位 if (pan.state == UIGestureRecognizerStateEnded) { CGFloat target = 0; if (_mainV.frame.origin.x > screenW * 0.5) { //定位到右邊 target = targetR; }else if(CGRectGetMaxX(_mainV.frame) < screenW * 0.5) { //定位到左邊 target = targetL; } //擷取X軸需要移動的位移量 CGFloat offsetX = target - _mainV.frame.origin.x; [UIView animateWithDuration:0.25 animations:^{ _mainV.frame = target == 0 ? self.view.bounds : [self frameWithOffsetX:offsetX]; }]; } }
- (void)tap { [UIView animateWithDuration:0.25 animations:^{ _mainV.frame = self.view.bounds; }]; }#define kMaxY 80#pragma mark - 根據offsetX計算mainV的frame- (CGRect)frameWithOffsetX:(CGFloat)offsetX { //擷取上一次的frame CGRect frame = _mainV.frame; //擷取螢幕的高度 CGFloat screenH = [UIScreen mainScreen].bounds.size.height; //擷取螢幕的寬度 //CGFloat screenW = [UIScreen mainScreen].bounds.size.width; //X軸平移一點對應Y軸需要平移的距離 CGFloat offsetY = offsetX * kMaxY / screenW; //擷取上一次的高度 CGFloat preH = frame.size.height; //擷取上一次的寬度 CGFloat preW = frame.size.width; //擷取當前高度 CGFloat curH = preH - 2 * offsetY; //如果是向左滑動 if(frame.origin.x < 0) { curH = preH + 2 * offsetY; } //擷取尺寸的縮放比例 CGFloat scale = curH / preH; //擷取當前寬度 CGFloat curW = preW * scale; //擷取當前x frame.origin.x += offsetX; //擷取當前y CGFloat y = (screenH - curH) / 2; frame.origin.y = y; frame.size.width = curW; frame.size.height = curH; return frame; }
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSString *,id> *)change context:(void *)context { if(_mainV.frame.origin.x > 0) {//往右邊滑動 _rightV.hidden = YES; }else if(_mainV.frame.origin.x < 0) {//往左邊滑動 _rightV.hidden = NO; } }
如果想要在mainV主視圖中顯示tableView,就新建立一個TableViewController,在這裡面顯示tableView的資料,
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { return 30;} - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { static NSString *ID = @"cell"; UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID]; if(cell == nil) { cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:ID]; } cell.textLabel.text = [NSString stringWithFormat:@"第%ld行", indexPath.row]; return cell;}
再建立一個在storyboard中顯示的控制器XXMainViewController,繼承自實現了抽屜效果的ViewController,並且在storyboard中將class改為這個控制的類名,還要將顯示tableView的控製成為他的子控制器
- (void)viewDidLoad { [super viewDidLoad]; XXViewController *vc = [[XXViewController alloc]init]; vc.view.frame = self.view.bounds; //讓vc成為主視圖控制器的子控制器 [self addChildViewController:vc]; //主視圖展示tableView [self.mainV addSubview:vc.view]; }
為了在XXMainViewController中只能訪問mainV而不能修改他的值,所以將子控制項的view暴露在ViewController.h中,並添加read-only
#import <UIKit/UIKit.h> @interface ViewController : UIViewController@property(nonatomic, weak, readonly) UIView *mainV;@property(nonatomic, weak, readonly) UIView *leftV;@property(nonatomic, weak, readonly) UIView *rightV;@end
運行效果圖:
以上就是本文的全部內容,希望對大家學習iOS程式設計有所協助。