#import <UIKit/UIKit.h>

@class FVPullDownMenu;

/** 指示器状态*/
typedef enum
{
IndicatorStateShow = 0,
IndicatorStateHide
}
IndicatorStatus; /** 视图状态*/
typedef enum
{
BackGroundViewStatusShow = 0,
BackGroundViewStatusHide
}
BackGroundViewStatus; /** 选择回调 协议*/
@protocol FVPullDownMenuDelegate <NSObject> - (void)PullDownMenu:(FVPullDownMenu *)pullDownMenu didSelectRowAtColumn:(NSInteger)column row:(NSInteger)row; @end @interface FVPullDownMenu : UIView<UITableViewDelegate, UITableViewDataSource> - (FVPullDownMenu *)initWithArray:(NSArray *)array selectedColor:(UIColor *)color; @property (nonatomic) id<FVPullDownMenuDelegate> delegate; @end /** CALayer 扩展*/
@interface CALayer (FVAddAnimationAndValue) - (void)addAnimation:(CAAnimation *)anim andValue:(NSValue *)value forKeyPath:(NSString *)keyPath; @end

.m

#import "FVPullDownMenu.h"

@implementation FVPullDownMenu
{ UIColor *_menuColor; UIView *_backGroundView;
UITableView *_tableView; NSMutableArray *_titles;
NSMutableArray *_indicators; NSInteger _currentSelectedMenudIndex;
bool _show; NSInteger _numOfMenu; NSArray *_array; } - (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame]; if (self) { }
return self;
} - (FVPullDownMenu *)initWithArray:(NSArray *)array selectedColor:(UIColor *)color
{
self = [super init];
if (self) { self.frame = CGRectMake(0, 0, 160, 30); self.layer.borderWidth = 1;
self.layer.borderColor = [[UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:0.3] CGColor]; _menuColor = [UIColor colorWithRed:164.0/255.0 green:166.0/255.0 blue:169.0/255.0 alpha:1.0]; _array = array; _numOfMenu = 1; //_array.count; //需要多列的话换成_array.count CGFloat textLayerInterval = self.frame.size.width / ( _numOfMenu * 2);
CGFloat separatorLineInterval = self.frame.size.width / _numOfMenu; _titles = [[NSMutableArray alloc] initWithCapacity:_numOfMenu];
_indicators = [[NSMutableArray alloc] initWithCapacity:_numOfMenu]; for (int i = 0; i < _numOfMenu; i++) { CGPoint position = CGPointMake( (i * 2 + 1) * textLayerInterval , self.frame.size.height / 2);
CATextLayer *title = [self creatTextLayerWithNSString:_array[i][0][@"title"] withColor:_menuColor andPosition:position];
[self.layer addSublayer:title];
[_titles addObject:title]; CAShapeLayer *indicator = [self creatIndicatorWithColor:_menuColor andPosition:CGPointMake(position.x + title.bounds.size.width / 2 + 8, self.frame.size.height / 2)];
[self.layer addSublayer:indicator];
[_indicators addObject:indicator]; if (i != _numOfMenu - 1) {
CGPoint separatorPosition = CGPointMake((i + 1) * separatorLineInterval, self.frame.size.height / 2);
CAShapeLayer *separator = [self creatSeparatorLineWithColor:[UIColor colorWithRed:239.0/255.0 green:239.0/255.0 blue:243.0/255.0 alpha:1.0] andPosition:separatorPosition];
[self.layer addSublayer:separator];
} }
_tableView = [self creatTableViewAtPosition:CGPointMake(0, self.frame.origin.y + self.frame.size.height)];
_tableView.tintColor = color;
_tableView.dataSource = self;
_tableView.delegate = self; // 设置menu, 并添加手势
self.backgroundColor = [UIColor whiteColor];
UIGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(tapMenu:)];
[self addGestureRecognizer:tapGesture]; // 创建背景
_backGroundView = [[UIView alloc] initWithFrame:[UIScreen mainScreen].bounds];
_backGroundView.backgroundColor = [UIColor colorWithWhite:0.0 alpha:0.0];
_backGroundView.opaque = NO;
UIGestureRecognizer *gesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(tapBackGround:)];
[_backGroundView addGestureRecognizer:gesture]; _currentSelectedMenudIndex = -1;
_show = NO;
}
return self;
} #pragma mark - tapEvent // 处理菜单点击事件.
- (void)tapMenu:(UITapGestureRecognizer *)paramSender
{ CGPoint touchPoint = [paramSender locationInView:self]; // 得到tapIndex NSInteger tapIndex = touchPoint.x / (self.frame.size.width / _numOfMenu); for (int i = 0; i < _numOfMenu; i++) {
if (i != tapIndex) {
[self animateIndicator:_indicators[i] Forward:NO complete:^{
[self animateTitle:_titles[i] show:NO complete:^{
}];
}];
}
} if (tapIndex == _currentSelectedMenudIndex && _show) { [self animateIdicator:_indicators[_currentSelectedMenudIndex] background:_backGroundView tableView:_tableView title:_titles[_currentSelectedMenudIndex] forward:NO complecte:^{
_currentSelectedMenudIndex = tapIndex;
_show = NO; }]; } else { _currentSelectedMenudIndex = tapIndex;
[_tableView reloadData];
[self animateIdicator:_indicators[tapIndex] background:_backGroundView tableView:_tableView title:_titles[tapIndex] forward:YES complecte:^{
_show = YES;
}]; } } - (void)tapBackGround:(UITapGestureRecognizer *)paramSender
{ [self animateIdicator:_indicators[_currentSelectedMenudIndex] background:_backGroundView tableView:_tableView title:_titles[_currentSelectedMenudIndex] forward:NO complecte:^{
_show = NO;
}]; } #pragma mark - tableViewDelegate - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{ [self confiMenuWithSelectRow:indexPath.row];
[self.delegate PullDownMenu:self didSelectRowAtColumn:_currentSelectedMenudIndex row:indexPath.row]; } #pragma mark tableViewDataSource - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return [_array[_currentSelectedMenudIndex] count];
} - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cell"];
if (!cell) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"cell"];
cell.textLabel.font = [UIFont systemFontOfSize:13.0];
} [cell.textLabel setTextColor:[UIColor grayColor]];
[cell setAccessoryType:UITableViewCellAccessoryNone];
cell.textLabel.text = _array[_currentSelectedMenudIndex][indexPath.row][@"title"]; if (cell.textLabel.text == [(CATextLayer *)[_titles objectAtIndex:_currentSelectedMenudIndex] string]) {
[cell setAccessoryType:UITableViewCellAccessoryCheckmark];
[cell.textLabel setTextColor:[tableView tintColor]];
} return cell;
} #pragma mark - animation - (void)animateIndicator:(CAShapeLayer *)indicator Forward:(BOOL)forward complete:(void(^)())complete
{
[CATransaction begin];
[CATransaction setAnimationDuration:0.25];
[CATransaction setAnimationTimingFunction:[CAMediaTimingFunction functionWithControlPoints:0.4 :0.0 :0.2 :1.0]]; CAKeyframeAnimation *anim = [CAKeyframeAnimation animationWithKeyPath:@"transform.rotation"];
anim.values = forward ? @[ @0, @(M_PI) ] : @[ @(M_PI), @0 ]; if (!anim.removedOnCompletion) {
[indicator addAnimation:anim forKey:anim.keyPath];
} else {
[indicator addAnimation:anim andValue:anim.values.lastObject forKeyPath:anim.keyPath];
} [CATransaction commit]; indicator.fillColor = forward ? _tableView.tintColor.CGColor : _menuColor.CGColor; complete();
} - (void)animateBackGroundView:(UIView *)view show:(BOOL)show complete:(void(^)())complete
{ if (show) { [self.superview addSubview:view];
[view.superview addSubview:self]; [UIView animateWithDuration:0.2 animations:^{
view.backgroundColor = [UIColor colorWithWhite:0.0 alpha:0.3];
}]; } else {
[UIView animateWithDuration:0.2 animations:^{
view.backgroundColor = [UIColor colorWithWhite:0.0 alpha:0.0];
} completion:^(BOOL finished) {
[view removeFromSuperview];
}]; }
complete(); } - (void)animateTableView:(UITableView *)tableView show:(BOOL)show complete:(void(^)())complete
{
if (show) { tableView.frame = CGRectMake(self.frame.origin.x, self.frame.origin.y + self.frame.size.height, self.frame.size.width, 0);
[self.superview addSubview:tableView]; CGFloat tableViewHeight = ([tableView numberOfRowsInSection:0] > 5) ? (5 * tableView.rowHeight) : ([tableView numberOfRowsInSection:0] * tableView.rowHeight); [UIView animateWithDuration:0.2 animations:^{
_tableView.frame = CGRectMake(self.frame.origin.x, self.frame.origin.y + self.frame.size.height, self.frame.size.width, tableViewHeight);
}]; } else { [UIView animateWithDuration:0.2 animations:^{
_tableView.frame = CGRectMake(self.frame.origin.x, self.frame.origin.y + self.frame.size.height, self.frame.size.width, 0);
} completion:^(BOOL finished) {
[tableView removeFromSuperview];
}]; }
complete(); } - (void)animateTitle:(CATextLayer *)title show:(BOOL)show complete:(void(^)())complete
{
if (show) {
title.foregroundColor = _tableView.tintColor.CGColor;
} else {
title.foregroundColor = _menuColor.CGColor;
}
CGSize size = [self calculateTitleSizeWithString:title.string];
CGFloat sizeWidth = (size.width < (self.frame.size.width / _numOfMenu) - 25) ? size.width : self.frame.size.width / _numOfMenu - 25;
title.bounds = CGRectMake(0, 0, sizeWidth, size.height); complete();
} - (void)animateIdicator:(CAShapeLayer *)indicator background:(UIView *)background tableView:(UITableView *)tableView title:(CATextLayer *)title forward:(BOOL)forward complecte:(void(^)())complete{ [self animateIndicator:indicator Forward:forward complete:^{
[self animateTitle:title show:forward complete:^{
[self animateBackGroundView:background show:forward complete:^{
[self animateTableView:tableView show:forward complete:^{
}];
}];
}];
}]; complete();
} #pragma mark - drawing - (CAShapeLayer *)creatIndicatorWithColor:(UIColor *)color andPosition:(CGPoint)point
{
CAShapeLayer *layer = [CAShapeLayer new]; UIBezierPath *path = [UIBezierPath new];
[path moveToPoint:CGPointMake(0, 0)];
[path addLineToPoint:CGPointMake(8, 0)];
[path addLineToPoint:CGPointMake(4, 5)];
[path closePath]; layer.path = path.CGPath;
layer.lineWidth = 1.0;
layer.fillColor = color.CGColor; CGPathRef bound = CGPathCreateCopyByStrokingPath(layer.path, nil, layer.lineWidth, kCGLineCapButt, kCGLineJoinMiter, layer.miterLimit);
layer.bounds = CGPathGetBoundingBox(bound);
CGPathRelease(bound);
layer.position = point; return layer;
} - (CAShapeLayer *)creatSeparatorLineWithColor:(UIColor *)color andPosition:(CGPoint)point
{
CAShapeLayer *layer = [CAShapeLayer new]; UIBezierPath *path = [UIBezierPath new];
[path moveToPoint:CGPointMake(160,0)];
[path addLineToPoint:CGPointMake(160, 20)]; layer.path = path.CGPath;
layer.lineWidth = 1.0;
layer.strokeColor = color.CGColor; CGPathRef bound = CGPathCreateCopyByStrokingPath(layer.path, nil, layer.lineWidth, kCGLineCapButt, kCGLineJoinMiter, layer.miterLimit);
layer.bounds = CGPathGetBoundingBox(bound);
CGPathRelease(bound);
layer.position = point; return layer;
} - (CATextLayer *)creatTextLayerWithNSString:(NSString *)string withColor:(UIColor *)color andPosition:(CGPoint)point
{ CGSize size = [self calculateTitleSizeWithString:string]; CATextLayer *layer = [CATextLayer new];
CGFloat sizeWidth = (size.width < (self.frame.size.width / _numOfMenu) - 25) ? size.width : self.frame.size.width / _numOfMenu - 25;
layer.bounds = CGRectMake(0, 0, sizeWidth, size.height);
layer.string = string;
layer.fontSize = 13.0;
layer.alignmentMode = kCAAlignmentCenter;
layer.foregroundColor = color.CGColor; layer.contentsScale = [[UIScreen mainScreen] scale]; layer.position = point; return layer;
} - (UITableView *)creatTableViewAtPosition:(CGPoint)point
{
UITableView *tableView = [UITableView new]; tableView.frame = CGRectMake(point.x, point.y, self.frame.size.width, 0);
tableView.rowHeight = 25; return tableView;
} #pragma mark - otherMethods - (CGSize)calculateTitleSizeWithString:(NSString *)string
{
CGFloat fontSize = 13.0;
NSDictionary *dic = @{NSFontAttributeName: [UIFont systemFontOfSize:fontSize]};
CGSize size = [string boundingRectWithSize:CGSizeMake(280, 0) options:NSStringDrawingTruncatesLastVisibleLine | NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingUsesFontLeading attributes:dic context:nil].size;
return size;
} - (void)confiMenuWithSelectRow:(NSInteger)row
{ CATextLayer *title = (CATextLayer *)_titles[_currentSelectedMenudIndex]; title.string = [[_array objectAtIndex:_currentSelectedMenudIndex] objectAtIndex:row][@"title"]; [self animateIdicator:_indicators[_currentSelectedMenudIndex] background:_backGroundView tableView:_tableView title:_titles[_currentSelectedMenudIndex] forward:NO complecte:^{
_show = NO; }]; CAShapeLayer *indicator = (CAShapeLayer *)_indicators[_currentSelectedMenudIndex];
indicator.position = CGPointMake(title.position.x + title.frame.size.width / 2 + 8, indicator.position.y);
} @end #pragma mark - CALayer Category @implementation CALayer (FVAddAnimationAndValue) - (void)addAnimation:(CAAnimation *)anim andValue:(NSValue *)value forKeyPath:(NSString *)keyPath
{
[self addAnimation:anim forKey:keyPath];
[self setValue:value forKeyPath:keyPath];
} @end

数据格式

数据格式

NSArray * testArray = @[
@[
@{@"title":@"1111@qq.com" ,@"uid": @"111"},
@{@"title":@"2222@qq.com" ,@"uid": @"222"},
@{@"title":@"3333@qq.com" ,@"uid": @"333"}
],
@[@""]
];

使用

NSInteger selectrow;

FVPullDownMenu *menu = [[FVPullDownMenu alloc] initWithArray:_accountArray selectedColor:[UIColor colorWithRed:32/255.0 green:144/255.0 blue:21/255.0 alpha:1.0]];
menu.delegate = self;
menu.frame = CGRectMake(110, 16, 160, 30);
[self.view addSubview:menu]; //委托回调方法
- (void)PullDownMenu:(FVPullDownMenu *)pullDownMenu didSelectRowAtColumn:(NSInteger)column row:(NSInteger)row
{
selectrow = row;
} //得到选择的数据
NSString * title = testArray[0][selectrow][@"title"];
 
 

ios 下拉列表的更多相关文章

  1. iOS中Safari浏览器select下拉列表文字太长被截断的处理方法

    网页中的select下拉列表,文字太长的话在iOS的Safari浏览器里会被自动截断,显示成下面这种: 安卓版的浏览器则没有这个问题. 如何让下拉列表中的文字在iOS的Safari浏览器里显示完整呢? ...

  2. 20130829ios cocos2d下拉列表的向上弹出实现(ios开发遇到的frame的问题)

    前几天仔细区分了ios中frame,bounds,center之间的关系. Frame:边框矩形,是视图相对于其父坐标的位置和大小 Bounds:边界矩形,是本地坐标系统(一般较少使用) Center ...

  3. ios 导航栏 点击barbutton的按钮 下拉列表

    环境:xocde5.0.2+ios7.0.1 1.导航栏 ----点击科目--------下拉列表 代码:NGRightTableViewViewController.h #import <UI ...

  4. iOS自定义下拉列表

    实现效果如下: 点击导航栏的“点击”,弹出下拉列表. 注意:绿色的是控制器的view背景,又一个遮罩层,点击可以隐藏列表. Github地址: https://github.com/PengSiSi/ ...

  5. iOS系列 基础篇 06 标签和按钮 (Label & Button)

    iOS系列 基础篇 06 标签和按钮 (Label & Button) 目录: 标签控件 按钮控件 小结 标签和按钮是两个常用的控件,下面咱们逐一学习. 1. 标签控件 使用Single Vi ...

  6. ios项目里扒出来的json文件

    p.p1 { margin: 0.0px 0.0px 0.0px 0.0px; font: 13.0px Menlo; color: #000000 } p.p2 { margin: 0.0px 0. ...

  7. Github上关于iOS的各种开源项目集合(强烈建议大家收藏,查看,总有一款你需要)

    下拉刷新 EGOTableViewPullRefresh - 最早的下拉刷新控件. SVPullToRefresh - 下拉刷新控件. MJRefresh - 仅需一行代码就可以为UITableVie ...

  8. iOS各种开源类库

    KissXml——xml解析库 相关教程:http://www.iteye.com/topic/625849 http://sencho.blog.163.com/blog/static/830562 ...

  9. iOS 资源大全

    这是个精心编排的列表,它包含了优秀的 iOS 框架.库.教程.XCode 插件.组件等等. 这个列表分为以下几个部分:框架( Frameworks ).组件( Components ).测试( Tes ...

随机推荐

  1. Eclipse启动和手动启动tomcat访问localhost:8080显示404问题总结

    前言:建议对tomcat的文件结构和相关属性有较多了解.本文以eclipse的DynamicWebProject为讲解对象. 目录: eclipse添加tomcat关联注意点 tomcat404问题归 ...

  2. 【bzoj2422】 Times 前缀和

    本来想练一下树状数组的,看到网上某人的blog后点了进来. 第一眼发现不会,出去上了个厕所发现离散化后不是一道简单前缀和题吗. 考虑到每一个人出现且仅出现一次,且出现的时间是在一个连续的区间内. 那么 ...

  3. 【NOIP2017】 宝藏 状压dp

    为啥我去年这么菜啊..... 我现在想了$20min$后打了$10min$就过了$qwq$. 我们用$f[i][j]$表示当前深度为$i$,访问了状态$j$中的所有点的最小代价. 显然$f[i][j] ...

  4. Linux实用指令

    Linux实用指令 Rpm&Yum ​ 一种用于互联网下载包的打包和安装工具,它包含某些Linux分发版中,它生产具有 .rpm 扩展名的文件.RPM 是 RedHat Package Man ...

  5. HBase 安装设置

    一.安装环境 1. JDK:jdk-7u79-linux-x64.tar.gz 2. HBase:hbase-0.98.13-hadoop1-bin.tar.gz 3. Hadoop:hadoop-1 ...

  6. ElasticSearch-SQL 安装和使用

    ES上线之后,用lucene语法来查询数据,学习成本略高,所以考虑用es-sql来简化这部分的操作. ES版本:5.4.0,节点部署如下: master node:3 client node:2,po ...

  7. Ajax关于readyState和status的讨论

    熟悉web开发的程序员想必对Ajax也不会陌生.现在已经有很多js框架封装了ajax实现,例如JQuery的ajax函数,调用起来非常方便.当然本文不打算讲框架的使用,我们将从Ajax的javascr ...

  8. spark 中如何查看单个RDD分区的内容(创建分区,查看分区数)

    spark 创建分区 val scores = Array(("Fred", 88), ("Fred", 95), ("Fred", 91) ...

  9. php中session的简单使用

    两个页面之间共享session,或者通过session来传递参数(其实session只是一个域而已,一个会话) 1. a.php中 <?php session_start();//开启sessi ...

  10. [转]Pass a ViewBag instance to a HiddenFor field in Razor

    本文转自:https://stackoverflow.com/questions/27456983/pass-a-viewbag-instance-to-a-hiddenfor-field-in-ra ...