一、UITableViewController
UITableViewController是繼承于UIViewController中的一個類,隻不過比UIViewController中多了一個屬性tableView。
也就是說UITableViewController是自帶table的視圖控制器。
它的self.view 是UITableView而不是UIView。
dataSource和delegate都預設是self。
總而言之,省了不少事情,相當于建立了一個UIViewController并在上面聲明了完整的UITableView。
二、UITableView的編輯
對于UITableView來說,經常需要删除或者添加一條資訊,比如,通訊錄中的滑動删除和添加資訊。
簡單來說就是對單元格進行删除,添加,插入,以及調換順序的操作。
這些操作主要通過各種代理方法來實作
1.讓tableView處于編輯狀态
//系統提供的方法按鈕會調用此方法,讓tableView處于編輯狀态
-(void)setEditing:(BOOL)editing animated:(BOOL)animated
{
//設定父類進入編輯狀态
[super setEditing:editing animated:animated];
//開啟表視圖的編輯狀态
UITableView *tempTableView = [self.view viewWithTag:1000];
[tempTableView setEditing:editing animated:animated];
}
//确定cell是否可以進入編輯狀态,為NO就不能進入編輯狀态
-(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
return YES;
}
2.設定編輯狀态的style,決定插入或删除
//設定編輯的樣式
-(UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
//如果是最後一行,編輯模式為插入
if (indexPath.row == _allDataMutableArray.count-1) {
return UITableViewCellEditingStyleInsert;
}
else
return UITableViewCellEditingStyleDelete;
}
3.編輯狀态的送出,對tableView進行改變
//編輯狀态的送出
-(void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableView *tempTableView = [self.view viewWithTag:1000];
//如果編輯模式為删除
if (editingStyle == UITableViewCellEditingStyleDelete) {
//先删除資料源,也就是數組中的内容
[_allDataMutableArray removeObjectAtIndex:indexPath.row];
//再删除單元格
//這裡要特别注意,必須先操作資料再操作單元格,不然崩的不要不要的
[tempTableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationTop];
}
//如果編輯模式為插入
if (editingStyle == UITableViewCellEditingStyleInsert) {
//先插入到數組
[_allDataMutableArray insertObject:@"新人" atIndex:indexPath.row];
//再建立單元格
[tempTableView insertRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationLeft];
}
}
下面是移動單元格的方法
1.首先還是要進入編輯狀态,與上面第一步相同
2.設定是否可以移動
//實作協定,告訴tableView是否能移動
-(BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath
{
return YES;
}
3.檢測移動的過程,可以對移動的源位置和目的位置進行限制
//監測移動過程,限制最後一行不能移動
-(NSIndexPath *)tableView:(UITableView *)tableView targetIndexPathForMoveFromRowAtIndexPath:(NSIndexPath *)sourceIndexPath toProposedIndexPath:(NSIndexPath *)proposedDestinationIndexPath
{
//設定,如果要移動最後一行或者移動到最後一行,是不允許的
if (sourceIndexPath.row == _allDataMutableArray.count - 1 || proposedDestinationIndexPath.row == _allDataMutableArray.count - 1) {
return sourceIndexPath;
}
else
return proposedDestinationIndexPath;
}
4.進行移動的資料操作,如果不添加這一步,就沒有修改資料源,重新加載後會複原
//移動
-(void)tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)sourceIndexPath toIndexPath:(NSIndexPath *)destinationIndexPath
{
//先得到單元格上的資料
NSString *tempStr = [self.allDataMutableArray objectAtIndex:sourceIndexPath.row];
//把原位置的資料删除
[_allDataMutableArray removeObjectAtIndex:sourceIndexPath.row];
//把新資料添加到數組中對應的位置
[_allDataMutableArray insertObject:tempStr atIndex:destinationIndexPath.row];
}
5.讓tableView重新加載資料
//重新整理資料
-(void)refreshAction:(UIBarButtonItem*)sender
{
UITableView *tempTableView = [self.view viewWithTag:1000];
[tempTableView reloadData];
}
這裡再貼上完整的代碼和效果
//
#import "RootViewController.h"
@interface RootViewController ()<UITableViewDataSource,UITableViewDelegate>
@property (nonatomic,retain)NSMutableArray* allDataMutableArray;
@end
@implementation RootViewController
- (void)viewDidLoad {
[super viewDidLoad];
//标題
self.navigationItem.title = @"表視圖的編輯";
//添加右側按鈕
//添加按鈕
UIBarButtonItem* addBarButton = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self action:@selector(addAction:)];
//編輯按鈕
UIBarButtonItem* editBarButton = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemAction target:self action:@selector(editAction:)];
//添加到右側
self.navigationItem.rightBarButtonItems = @[self.editButtonItem,addBarButton,editBarButton];
//添加左側重新整理按鈕
self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemRefresh target:self action:@selector(refreshAction:)];
//初始化
UITableView *myTableView = [[UITableView alloc]initWithFrame:self.view.bounds style:UITableViewStylePlain];
myTableView.tag = 1000;
//代理
myTableView.delegate = self;
myTableView.dataSource = self;
//添加到父視圖
[self.view addSubview:myTableView];
//顯示相關的屬性
//行高
myTableView.rowHeight = 70;
//分割線
myTableView.separatorColor = [UIColor blueColor];
myTableView.separatorStyle = UITableViewCellSeparatorStyleSingleLine;
//置頂視圖
myTableView.tableHeaderView = [[UIView alloc]init];
//置底視圖
myTableView.tableFooterView = [[UIView alloc]init];
//初始化數組資料
self.allDataMutableArray = [[NSMutableArray alloc]initWithObjects:@"張三",@"李四",@"我擦",@"123",@"",@"111",@"333", nil];
}
//行數
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return _allDataMutableArray.count;
}
//cell填充
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//cell重用機制
//定義重用标示符
static NSString* cellId = @"CELL";
//每次需要使用單元格的是,先根據重用辨別符從重用隊列中擷取單元格,如果隊列中沒有,再進行初始化新的單元格
//每次都會先建立一螢幕的cell,當有cell出螢幕,就會根據重用辨別符添加到對應的重用隊列中,當螢幕外的cell要進入螢幕,先從隊列中擷取,如果沒有,則初始化cell
//當重用cell時,需要對上面的控件程式指派
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellId];
//如果從重用隊列中未擷取cell,也就是Cell為空
if (!cell) {
cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:cellId];
//系統提供的控件要配合不同的樣式來使用
// cell.detailTextLabel.text = [NSString stringWithFormat:@"建立的第%d個單元格",self.index++];
}
//UITableViewCell的屬性
//選中效果
cell.selectionStyle = UITableViewCellSelectionStyleBlue;
//輔助視圖的樣式
cell.accessoryType = UITableViewCellAccessoryCheckmark;
//設定左側圖檔
cell.imageView.image = [UIImage imageNamed:@"ck.jpg"];
//标題視圖
cell.detailTextLabel.text = [NSString stringWithFormat:@"第%ld個cell,%ld個section",indexPath.row,indexPath.section];
//副标題視圖
cell.textLabel.text = _allDataMutableArray[indexPath.row];
//為相應位置傳回定制好的單元格
return cell;
}
#pragma mark -- 按鈕觸發方法
//點選添加觸發的方法
-(void)addAction:(UIBarButtonItem*)sender
{
}
//進入編輯狀态
-(void)editAction:(UIBarButtonItem*)sender
{
[self setEditing:YES animated:NO];
}
//重新整理資料
-(void)refreshAction:(UIBarButtonItem*)sender
{
UITableView *tempTableView = [self.view viewWithTag:1000];
[tempTableView reloadData];
}
#pragma mark -- 編輯相關代理方法
//系統提供的方法按鈕會調用此方法,讓tableView處于編輯狀态
-(void)setEditing:(BOOL)editing animated:(BOOL)animated
{
[super setEditing:editing animated:animated];
//開啟表視圖的編輯狀态
UITableView *tempTableView = [self.view viewWithTag:1000];
[tempTableView setEditing:editing animated:animated];
}
//協定設定
//确定cell是否處于編輯狀态,為NO就不能進入編輯狀态
-(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
return YES;
}
//編輯狀态的送出
-(void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableView *tempTableView = [self.view viewWithTag:1000];
//如果編輯模式為删除
if (editingStyle == UITableViewCellEditingStyleDelete) {
//先删除資料源,也就是數組中的内容
[_allDataMutableArray removeObjectAtIndex:indexPath.row];
//再删除單元格
//這裡要特别注意,必須先操作資料再操作單元格,不然崩的不要不要的
[tempTableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationTop];
}
//如果編輯模式為插入
if (editingStyle == UITableViewCellEditingStyleInsert) {
//先插入到數組
[_allDataMutableArray insertObject:@"新人" atIndex:indexPath.row];
//再建立單元格
[tempTableView insertRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationLeft];
}
}
//設定編輯的樣式
-(UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
//如果是最後一行,編輯模式為插入
if (indexPath.row == _allDataMutableArray.count-1) {
return UITableViewCellEditingStyleInsert;
}
else
return UITableViewCellEditingStyleDelete;
}
//移動相關
//實作協定,告訴tableView是否能移動
-(BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath
{
return YES;
}
//移動
-(void)tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)sourceIndexPath toIndexPath:(NSIndexPath *)destinationIndexPath
{
//先得到單元格上的資料
NSString *tempStr = [self.allDataMutableArray objectAtIndex:sourceIndexPath.row];
//把原位置的資料删除
[_allDataMutableArray removeObjectAtIndex:sourceIndexPath.row];
//把新資料添加到數組中對應的位置
[_allDataMutableArray insertObject:tempStr atIndex:destinationIndexPath.row];
}
//監測移動過程,限制最後一行不能移動
-(NSIndexPath *)tableView:(UITableView *)tableView targetIndexPathForMoveFromRowAtIndexPath:(NSIndexPath *)sourceIndexPath toProposedIndexPath:(NSIndexPath *)proposedDestinationIndexPath
{
if (sourceIndexPath.row == _allDataMutableArray.count - 1 || proposedDestinationIndexPath.row == _allDataMutableArray.count - 1) {
return sourceIndexPath;
}
else
return proposedDestinationIndexPath;
}
@end
效果如下
![](https://img.laitimes.com/img/9ZDMuAjOiMmIsIjOiQnIsICOwADMxITNxEjNyIDM2EDMy8CX0Vmbu4GZzNmLn9Gbi1yZtl2Lc9CX6MHc0RHaiojIsJye.jpg)