好像最近,看到好多Android上的抽屉效果,也忍不住想要自己写一个。在Android里面可以用SlidingDrawer,很方便的实现。IOS上面就只有自己写了。其实原理很简单就是 UIView 的移动,和一些手势的操作。
[cpp] view plain copy print ?
-
-
-
-
-
-
-
-
- #import <UIKit/UIKit.h>
-
- typedef enum
- {
- DrawerViewStateUp = 0,
- DrawerViewStateDown
- }DrawerViewState;
-
- @interface DrawerView : UIView<UIGestureRecognizerDelegate>
- {
- UIImageView *arrow;
-
- CGPoint upPoint;
- CGPoint downPoint;
-
- UIView *parentView;
- UIView *contentView;
-
- DrawerViewState drawState;
- }
-
- - (id)initWithView:(UIView *) contentview parentView :(UIView *) parentview;
- - (void)handlePan:(UIPanGestureRecognizer *)recognizer;
- - (void)handleTap:(UITapGestureRecognizer *)recognizer;
- - (void)transformArrow:(DrawerViewState) state;
-
- @property (nonatomic,retain) UIView *parentView;
- @property (nonatomic,retain) UIView *contentView;
- @property (nonatomic,retain) UIImageView *arrow;
- @property (nonatomic) DrawerViewState drawState;
-
- @end
//
// DrawerView.h
// DrawerDemo
//
// Created by Zhouhaifeng on 12-3-27.
// Copyright (c) 2012年 CJLU. All rights reserved.
//
#import <UIKit/UIKit.h>
typedef enum
{
DrawerViewStateUp = 0,
DrawerViewStateDown
}DrawerViewState;
@interface DrawerView : UIView<UIGestureRecognizerDelegate>
{
UIImageView *arrow; //向上拖拽时显示的图片
CGPoint upPoint; //抽屉拉出时的中心点
CGPoint downPoint; //抽屉收缩时的中心点
UIView *parentView; //抽屉所在的view
UIView *contentView; //抽屉里面显示的内容
DrawerViewState drawState; //当前抽屉状态
}
- (id)initWithView:(UIView *) contentview parentView :(UIView *) parentview;
- (void)handlePan:(UIPanGestureRecognizer *)recognizer;
- (void)handleTap:(UITapGestureRecognizer *)recognizer;
- (void)transformArrow:(DrawerViewState) state;
@property (nonatomic,retain) UIView *parentView;
@property (nonatomic,retain) UIView *contentView;
@property (nonatomic,retain) UIImageView *arrow;
@property (nonatomic) DrawerViewState drawState;
@end
[cpp] view plain copy print ?
-
-
-
-
-
-
-
-
- #import "DrawerView.h"
-
- @implementation DrawerView
- @synthesize contentView,parentView,drawState;
- @synthesize arrow;
-
- - (id)initWithView:(UIView *) contentview parentView :(UIView *) parentview;
- {
- self = [super initWithFrame:CGRectMake(0,0,contentview.frame.size.width, contentview.frame.size.height+40)];
- if (self) {
-
- contentView = contentview;
- parentView = parentview;
-
-
- [parentView setUserInteractionEnabled:YES];
-
-
- UIImage *drawer_bg = [UIImage imageNamed:@"drawer_content.png"];
- UIImageView *view_bg = [[UIImageView alloc]initWithImage:drawer_bg];
- [view_bg setFrame:CGRectMake(0,40,contentview.frame.size.width, contentview.bounds.size.height+40)];
- [self addSubview:view_bg];
-
-
- UIImage *drawer_handle = [UIImage imageNamed:@"drawer_handlepng.png"];
- UIImageView *view_handle = [[UIImageView alloc]initWithImage:drawer_handle];
- [view_handle setFrame:CGRectMake(0,0,contentview.frame.size.width,40)];
- [self addSubview:view_handle];
-
-
- UIImage *drawer_arrow = [UIImage imageNamed:@"drawer_arrow.png"];
- arrow = [[UIImageView alloc]initWithImage:drawer_arrow];
- [arrow setFrame:CGRectMake(0,0,28,28)];
- arrow.center = CGPointMake(contentview.frame.size.width/2, 20);
- [self addSubview:arrow];
-
-
- [contentView setFrame:CGRectMake(0,40,contentview.frame.size.width, contentview.bounds.size.height+40)];
- [self addSubview:contentview];
-
-
- UIPanGestureRecognizer *panRcognize=[[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(handlePan:)];
- panRcognize.delegate=self;
- [panRcognize setEnabled:YES];
- [panRcognize delaysTouchesEnded];
- [panRcognize cancelsTouchesInView];
-
- [self addGestureRecognizer:panRcognize];
-
-
- UITapGestureRecognizer *tapRecognize = [[UITapGestureRecognizer alloc]initWithTarget:self action:@selector(handleTap:)];
- tapRecognize.numberOfTapsRequired = 1;
- tapRecognize.delegate = self;
- [tapRecognize setEnabled :YES];
- [tapRecognize delaysTouchesBegan];
- [tapRecognize cancelsTouchesInView];
-
- [self addGestureRecognizer:tapRecognize];
-
-
- downPoint = CGPointMake(parentview.frame.size.width/2, parentview.frame.size.height+contentview.frame.size.height/2-40);
- upPoint = CGPointMake(parentview.frame.size.width/2, parentview.frame.size.height-contentview.frame.size.height/2-40);
- self.center = downPoint;
-
-
- drawState = DrawerViewStateDown;
- }
- return self;
- }
-
-
- #pragma UIGestureRecognizer Handles
-
- - (void)handlePan:(UIPanGestureRecognizer *)recognizer {
-
-
- CGPoint translation = [recognizer translationInView:parentView];
- if (self.center.y + translation.y < upPoint.y) {
- self.center = upPoint;
- }else if(self.center.y + translation.y > downPoint.y)
- {
- self.center = downPoint;
- }else{
- self.center = CGPointMake(self.center.x,self.center.y + translation.y);
- }
- [recognizer setTranslation:CGPointMake(0, 0) inView:parentView];
-
- if (recognizer.state == UIGestureRecognizerStateEnded) {
- [UIView animateWithDuration:0.75 delay:0.15 options:UIViewAnimationOptionCurveEaseOut animations:^{
- if (self.center.y < downPoint.y*4/5) {
- self.center = upPoint;
- [self transformArrow:DrawerViewStateUp];
- }else
- {
- self.center = downPoint;
- [self transformArrow:DrawerViewStateDown];
- }
-
- } completion:nil];
-
- }
- }
-
-
- -(void) handleTap:(UITapGestureRecognizer *)recognizer
- {
- [UIView animateWithDuration:0.75 delay:0.15 options:UIViewAnimationOptionTransitionCurlUp animations:^{
- if (drawState == DrawerViewStateDown) {
- self.center = upPoint;
- [self transformArrow:DrawerViewStateUp];
- }else
- {
- self.center = downPoint;
- [self transformArrow:DrawerViewStateDown];
- }
- } completion:nil];
-
- }
-
-
-
- -(void)transformArrow:(DrawerViewState) state
- {
-
- [UIView animateWithDuration:0.3 delay:0.35 options:UIViewAnimationOptionCurveEaseOut animations:^{
- if (state == DrawerViewStateUp){
- arrow.transform = CGAffineTransformMakeRotation(M_PI);
- }else
- {
- arrow.transform = CGAffineTransformMakeRotation(0);
- }
- } completion:^(BOOL finish){
- drawState = state;
- }];
-
-
- }
-
- @end
//
// DrawerView.m
// DrawerDemo
//
// Created by Zhouhaifeng on 12-3-27.
// Copyright (c) 2012年 CJLU. All rights reserved.
//
#import "DrawerView.h"
@implementation DrawerView
@synthesize contentView,parentView,drawState;
@synthesize arrow;
- (id)initWithView:(UIView *) contentview parentView :(UIView *) parentview;
{
self = [super initWithFrame:CGRectMake(0,0,contentview.frame.size.width, contentview.frame.size.height+40)];
if (self) {
// Initialization code
contentView = contentview;
parentView = parentview;
//一定要开启
[parentView setUserInteractionEnabled:YES];
//嵌入内容区域的背景
UIImage *drawer_bg = [UIImage imageNamed:@"drawer_content.png"];
UIImageView *view_bg = [[UIImageView alloc]initWithImage:drawer_bg];
[view_bg setFrame:CGRectMake(0,40,contentview.frame.size.width, contentview.bounds.size.height+40)];
[self addSubview:view_bg];
//头部拉拽的区域背景
UIImage *drawer_handle = [UIImage imageNamed:@"drawer_handlepng.png"];
UIImageView *view_handle = [[UIImageView alloc]initWithImage:drawer_handle];
[view_handle setFrame:CGRectMake(0,0,contentview.frame.size.width,40)];
[self addSubview:view_handle];
//箭头的图片
UIImage *drawer_arrow = [UIImage imageNamed:@"drawer_arrow.png"];
arrow = [[UIImageView alloc]initWithImage:drawer_arrow];
[arrow setFrame:CGRectMake(0,0,28,28)];
arrow.center = CGPointMake(contentview.frame.size.width/2, 20);
[self addSubview:arrow];
//嵌入内容的UIView
[contentView setFrame:CGRectMake(0,40,contentview.frame.size.width, contentview.bounds.size.height+40)];
[self addSubview:contentview];
//移动的手势
UIPanGestureRecognizer *panRcognize=[[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(handlePan:)];
panRcognize.delegate=self;
[panRcognize setEnabled:YES];
[panRcognize delaysTouchesEnded];
[panRcognize cancelsTouchesInView];
[self addGestureRecognizer:panRcognize];
//单击的手势
UITapGestureRecognizer *tapRecognize = [[UITapGestureRecognizer alloc]initWithTarget:self action:@selector(handleTap:)];
tapRecognize.numberOfTapsRequired = 1;
tapRecognize.delegate = self;
[tapRecognize setEnabled :YES];
[tapRecognize delaysTouchesBegan];
[tapRecognize cancelsTouchesInView];
[self addGestureRecognizer:tapRecognize];
//设置两个位置的坐标
downPoint = CGPointMake(parentview.frame.size.width/2, parentview.frame.size.height+contentview.frame.size.height/2-40);
upPoint = CGPointMake(parentview.frame.size.width/2, parentview.frame.size.height-contentview.frame.size.height/2-40);
self.center = downPoint;
//设置起始状态
drawState = DrawerViewStateDown;
}
return self;
}
#pragma UIGestureRecognizer Handles
/*
* 移动图片处理的函数
* @recognizer 移动手势
*/
- (void)handlePan:(UIPanGestureRecognizer *)recognizer {
CGPoint translation = [recognizer translationInView:parentView];
if (self.center.y + translation.y < upPoint.y) {
self.center = upPoint;
}else if(self.center.y + translation.y > downPoint.y)
{
self.center = downPoint;
}else{
self.center = CGPointMake(self.center.x,self.center.y + translation.y);
}
[recognizer setTranslation:CGPointMake(0, 0) inView:parentView];
if (recognizer.state == UIGestureRecognizerStateEnded) {
[UIView animateWithDuration:0.75 delay:0.15 options:UIViewAnimationOptionCurveEaseOut animations:^{
if (self.center.y < downPoint.y*4/5) {
self.center = upPoint;
[self transformArrow:DrawerViewStateUp];
}else
{
self.center = downPoint;
[self transformArrow:DrawerViewStateDown];
}
} completion:nil];
}
}
/*
* handleTap 触摸函数
* @recognizer UITapGestureRecognizer 触摸识别器
*/
-(void) handleTap:(UITapGestureRecognizer *)recognizer
{
[UIView animateWithDuration:0.75 delay:0.15 options:UIViewAnimationOptionTransitionCurlUp animations:^{
if (drawState == DrawerViewStateDown) {
self.center = upPoint;
[self transformArrow:DrawerViewStateUp];
}else
{
self.center = downPoint;
[self transformArrow:DrawerViewStateDown];
}
} completion:nil];
}
/*
* transformArrow 改变箭头方向
* state DrawerViewState 抽屉当前状态
*/
-(void)transformArrow:(DrawerViewState) state
{
//NSLog(@"DRAWERSTATE :%d STATE:%d",drawState,state);
[UIView animateWithDuration:0.3 delay:0.35 options:UIViewAnimationOptionCurveEaseOut animations:^{
if (state == DrawerViewStateUp){
arrow.transform = CGAffineTransformMakeRotation(M_PI);
}else
{
arrow.transform = CGAffineTransformMakeRotation(0);
}
} completion:^(BOOL finish){
drawState = state;
}];
}
@end
这样就是实现了,图片是从360里面抠出来,处理的不是很好,大家见谅。
Demo的下载地址:http://download.csdn.net/detail/toss156/4177553