您的位置:首页 > 产品设计 > UI/UE

iOS UITableView的细致功能(滑动删除,拖动排序,添加行,搜索过滤)

2014-10-21 16:18 645 查看
对于UITableView,相信大家都并不陌生,每一个iOS app 几乎都离不开UITableViewCell,创建UITableViewCell的过程也很简单,所以也无需纪录,昨天在工作闲余时间学习了一下UITableView更细致的一些功能,这些功能使得UITableView更加强大和使用。

1、删除

删除通常有两种方式:

一是点击一个按钮后,所有的tableViewCell的最左边都出现一个红色的按钮,中间有一条横杆,点击这个按钮后右侧就会出现删除按钮

二是滑动tableViewCell,右侧会出现删除按钮。

先说第一种的实现:

创建一个UIViewController类,通过Interface Builder添加一个UItableView,为这个类添加一个数组作为成员变量,用于记录tableView的数据,头文件代码如下:

#import <UIKit/UIKit.h>

@interface ViewControllerX : UIViewController<UITableViewDataSource,UITableViewDelegate>

@property (nonatomic,retain) IBOutlet UITableView *SeanTableView;

@property (nonatomic,retain) NSMutableArray *array;

@end


在类的实现文件的ViewDidRoad方法中,加载数组数据,创建两个UIBarButtonItem类对象,即创建一个垃圾桶样式的按钮和一个➕样式的按钮,代码如下:

- (void)viewDidLoad {
[super viewDidLoad];
self.array = [NSMutableArray arrayWithArray:@[@"Lin Sean",@"Lin wade",@"D wade",@"Lin James",@"CB"]];

UIBarButtonItem *left = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemTrash target:self action:@selector(delete)];
self.navigationItem.leftBarButtonItem = left;

UIBarButtonItem *right = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self action:@selector(add)];
self.navigationItem.rightBarButtonItem = right;
}


要实现第一种删除方法,实际上是要让tableView进入编辑模式,所以垃圾筒按钮的响应函数代码如下:

- (void) delete
{
[self.SeanTableView setEditing:YES animated:YES]; //使tableView进入编辑模式
}


到这里,点击垃圾筒按钮,就可以出现以下的情况了





但是,这里点击了delete按钮,也没有反应,因为还需要实现协议的一个方法

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath

接着说滑动删除的方法:
这里一下子跳到滑动删除的原因,是因为只要实现了上述提到的
- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath方法,tableView就能实现滑动删除了。实现这个方法的代码如下:

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
[self.array removeObjectAtIndex:indexPath.row];
[tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationAutomatic];
}
方法里首先肯定是要对数组进行删除操作,然后就是对tableView进行操作,这里没有在删除数组之后执行tableView reloadData的原因是reloadData这个方法是重新刷新整个tableView,比较耗费性能,而这里知识更改了一行数据,所以只要调用上面的第二个语句的方法,系统就会重新刷新一行的数据,这样效率会高很多。

至此,删除功能就能够完成了,可能这里还会存在很多错漏之处,但这也只是简介,更精密的代码还有待大家更具实际需求来做具体的设计。
2、添加

添加其实跟删除很类似,点击了一个添加按钮之后,所有的tableViewCell前面都会弹出一个绿色的按钮。

操作方法也是一样,当点击了➕按钮后,tableView进入编辑模式,代码如下:

- (void) add
{
[self.SeanTableView setEditing:YES animated:YES];
}


这里就有问题了,点击删除也是进入编辑模式,点击添加也是进入编辑模式,那系统是怎样区分是删除还是添加呢?
这里就需要再实现另一个协议的方法

- (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath,为了区别到底是点了那个按钮,我们还需要在头文件创建一个标志变量来记录当前是那种模式。下面代码中的isInsert就是标志变量。

- (void) delete
{
isInsert = NO;   // 加上标志记录
[self.SeanTableView setEditing:YES animated:YES];
}

- (void) add
{
isInsert = YES;   // 加上标志纪录
[self.SeanTableView setEditing:YES animated:YES];
}
// 使tableView进入何种编辑模式,由这个函数的返回值进行决定
- (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
if (isInsert == YES) {
return UITableViewCellEditingStyleInsert;
}
else
{
return UITableViewCellEditingStyleDelete;
}
}


到这里,就可以点击垃圾桶进入删除的编辑模式,点击➕按钮就进入添加的编辑模式了。但是,这时即便进入了添加模式,点击左侧的添加按钮,会发现响应的依然是删除的功能。这事因为进入编辑模式后,系统执行何种操作,还是由上述的
- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath


方法决定的,这个方法的参数editingStyle就是用户判断是何种编辑模式的,所以还需要在该方法中进行判断,代码如下:

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
if (editingStyle == UITableViewCellEditingStyleDelete) {
[self.array removeObjectAtIndex:indexPath.row];
[tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewAutomaticDimension];
}
else
{
UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
[self.array insertObject:cell.textLabel.text atIndex:indexPath.row];
[tableView insertRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewAutomaticDimension];
}

}


这样,一个可以大概实现增加和删除的UITableView就粗略地实现了,效果如下:





3.排序
其实排序,也无非是实现协议中的方法就可以实现了,只不过你以后tableViewCell后,你的数组应该如何调整,这就是逻辑问题了,需要自己去实现。
要使得tableView可以在进入编辑模式后可以排序,只要实现一下这个方法就行了,实现代码可以为空。如下:

- (void) tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)sourceIndexPath toIndexPath:(NSIndexPath *)destinationIndexPath
{
//这里为空,进入编辑模式后,tableView的cell也可以拖动排序,但是一般需要在这个函数里面进行一个数组元素位置的调整
}
效果如下:



这时只要长按右侧的三道杠,然后拖动cell,就可以排序了。

4、搜索过滤

搜索过滤与前面三个不同,它不属于tableView的编辑模式下进行的操作。但是在学习的过程中也接触到了,而且非常常用,所以也纪录一下
首先肯定是要添加一个搜索栏,这里为了简便,我把它添加到了navigationbar的titleView里面去,为完善搜索栏的各种功能,还需在头文件中实现UISearchBarDelegate协议,代码如下:

@interface ViewControllerX : UIViewController<UITableViewDataSource,UITableViewDelegate,UISearchBarDelegate>


<pre name="code" class="objc">- (void)viewDidLoad {
[super viewDidLoad];
self.array = [NSMutableArray arrayWithArray:@[@"Lin Sean",@"Lin wade",@"D wade",@"Lin James",@"CB"]];

UIBarButtonItem *left = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemTrash target:self action:@selector(delete)];
self.navigationItem.leftBarButtonItem = left;

UIBarButtonItem *right = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self action:@selector(add)];
self.navigationItem.rightBarButtonItem = right;
isInsert = NO;

// 在navigationBar添加一个搜索栏
UISearchBar *sb = [[UISearchBar alloc]initWithFrame:CGRectMake(0, 0, 60, 20)];
sb.showsCancelButton = YES;
self.navigationItem.titleView = sb;
sb.delegate = self;

self.searchArray = [[NSMutableArray alloc]init];
}

// 点击搜索栏cancel按钮时执行的操作
- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar
{
[searchBar resignFirstResponder]; //键盘退回
[self.SeanTableView reloadData];
}



要实时监测searchbar输入的内容,根据内容进行表格数据的过滤,我们需要实现以下的协议方法,并创建一个新的数组和一个标志变量,用户纪录搜索的结果和判断当前是否正在搜索,代码如下:

头文件:

@interface ViewControllerX : UIViewController<UITableViewDataSource,UITableViewDelegate,UISearchBarDelegate>
{
bool isInsert;
bool isSearch;
}
@property (nonatomic,retain) IBOutlet UITableView *SeanTableView;
@property (nonatomic,retain) NSMutableArray *array;
@property (nonatomic,retain) NSMutableArray *searchArray;
@end


实现文件:

// 点击搜索栏cancel按钮时执行的操作
- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar
{
isSearch = NO;
[searchBar resignFirstResponder]; //键盘退回
[self.SeanTableView reloadData];
}

- (void)searchBar:(UISearchBar *)searchBar textDidChange:(NSString *)searchText
{
isSearch = YES;
if (self.searchArray.count != 0) {
[self.searchArray removeAllObjects];
}
for (id sean in self.array)
{
if ([sean containsString:searchText]) {
[self.searchArray addObject:sean];
[self.SeanTableView reloadData];
}
else
{
[self.SeanTableView reloadData];
}
}

}


因为在搜索栏输入内容的时候需要tableView需要reloadData,所以需要修改代码如下:

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
if (isSearch == YES) {
return self.searchArray.count;
}
return self.array.count;
}

- (UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *str = nil;
if (isSearch == YES) {
str = [self.searchArray objectAtIndex:indexPath.row];
}
else
{
str = [self.array objectAtIndex:indexPath.row];
}
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cell"];
if (cell == nil) {
cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"cell"];
}
cell.textLabel.text = str;

return cell;
}


至此,一个简单的搜索功能就实现了。效果如下:



头文件的完整代码如下:

#import <UIKit/UIKit.h>

@interface ViewControllerX : UIViewController<UITableViewDataSource,UITableViewDelegate,UISearchBarDelegate>
{
bool isInsert;
bool isSearch;
}

@property (nonatomic,retain) IBOutlet UITableView *SeanTableView;

@property (nonatomic,retain) NSMutableArray *array;

@property (nonatomic,retain) NSMutableArray *searchArray;

@end


实现文件的完整代码如下:

#import "ViewControllerX.h"

@interface ViewControllerX ()

@end

@implementation ViewControllerX

- (void)viewDidLoad {
[super viewDidLoad];
self.array = [NSMutableArray arrayWithArray:@[@"Lin Sean",@"Lin wade",@"D wade",@"Lin James",@"CB"]];

UIBarButtonItem *left = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemTrash target:self action:@selector(delete)];
self.navigationItem.leftBarButtonItem = left;

UIBarButtonItem *right = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self action:@selector(add)];
self.navigationItem.rightBarButtonItem = right;
isInsert = NO;

// 在navigationBar添加一个搜索栏
UISearchBar *sb = [[UISearchBar alloc]initWithFrame:CGRectMake(0, 0, 60, 20)];
sb.showsCancelButton = YES;
self.navigationItem.titleView = sb;
sb.delegate = self;

self.searchArray = [[NSMutableArray alloc]init];
}

// 点击搜索栏cancel按钮时执行的操作 - (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar { isSearch = NO; [searchBar resignFirstResponder]; //键盘退回 [self.SeanTableView reloadData]; } - (void)searchBar:(UISearchBar *)searchBar textDidChange:(NSString *)searchText { isSearch = YES; if (self.searchArray.count != 0) { [self.searchArray removeAllObjects]; } for (id sean in self.array) { if ([sean containsString:searchText]) { [self.searchArray addObject:sean]; [self.SeanTableView reloadData]; } else { [self.SeanTableView reloadData]; } } }

- (void) delete { isInsert = NO; // 加上标志记录 [self.SeanTableView setEditing:YES animated:YES]; } - (void) add { isInsert = YES; // 加上标志纪录 [self.SeanTableView setEditing:YES animated:YES]; }- (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
if (isInsert == YES) {
return UITableViewCellEditingStyleInsert;
}
else
{
return UITableViewCellEditingStyleDelete;
}
}

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath { if (editingStyle == UITableViewCellEditingStyleDelete) { [self.array removeObjectAtIndex:indexPath.row]; [tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewAutomaticDimension]; } else { UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath]; [self.array insertObject:cell.textLabel.text atIndex:indexPath.row]; [tableView insertRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewAutomaticDimension]; } }

- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { if (isSearch == YES) { return self.searchArray.count; } return self.array.count; } - (UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { NSString *str = nil; if (isSearch == YES) { str = [self.searchArray objectAtIndex:indexPath.row]; } else { str = [self.array objectAtIndex:indexPath.row]; } UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cell"]; if (cell == nil) { cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"cell"]; } cell.textLabel.text = str; return cell; }

- (void) tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)sourceIndexPath toIndexPath:(NSIndexPath *)destinationIndexPath
{

}

@end
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: