UITableView表視圖,是實用的數據展示的基礎控制項,是繼承於UIScrollView,所以也可以滾動。但不同於UIScrollView,UITableView只可以上下滾動,而不能左右滾動。 因為是數據展示,必然少不了數據的存在,嗯,使用plist文件來獲取想要的數據。通過模型來獲取。 說到這
UITableView表視圖,是實用的數據展示的基礎控制項,是繼承於UIScrollView,所以也可以滾動。但不同於UIScrollView,UITableView只可以上下滾動,而不能左右滾動。
因為是數據展示,必然少不了數據的存在,嗯,使用plist文件來獲取想要的數據。通過模型來獲取。
說到這樣就必須要變到MVC了,MVC是設計模塊的核心
M是指模型,用來獲取數據
V是指視圖,用來展示各種數據,各種控制項
C是指視圖控制器,能來維持M和V之間的通信
創建一個類,將相要展示的數據聲明成屬性
@interface Student : NSObject @property (nonatomic, copy)NSString *name; @property (nonatomic, copy)NSString *age; @property (nonatomic, copy)NSString *number; @property (nonatomic, copy)NSString *gender; @property (nonatomic, copy)NSString *hobby;
一定要記得重寫處理異常的方法,因為有可能有些數據沒有使用到,或者數據拼寫錯誤都不會 產生異常處理。
- (void)setValue:(id)value forUndefinedKey:(NSString *)key{ }
因為要使用模型,所以 用類似於懶載入的方式,來載入數據
因為 是在MRC環境下,所以操作完之後要記得釋放
在延展中創建一個保存數據的可變數組dataArrary;
@implementation ListViewController - (void)dealloc{ [_dataArrary release]; [_tableView release]; [super dealloc]; } //載入數據的方法 - (void)reloadData{ //獲取文件路徑 NSString *filePath = [[NSBundle mainBundle] pathForResource:@"Student" ofType:@"plist"]; //從文件路徑中提取數組 NSArray *arrary = [NSArray arrayWithContentsOfFile:filePath]; //初始化數組 _dataArrary = [[NSMutableArray alloc] initWithCapacity:0]; //遍曆數組,進行添加模型 for (NSDictionary *dic in arrary) { Student *student = [[Student alloc] init]; [student setValuesForKeysWithDictionary:dic]; [_dataArrary addObject:student]; [student release]; //一定要釋放! } }
創建UITableView.
//執行載入的方法 [self reloadData]; _tableView = [[UITableView alloc] initWithFrame:[[UIScreen mainScreen]bounds] style:UITableViewStylePlain]; self.navigationItem.leftBarButtonItem = self.editButtonItem; //代理 _tableView.dataSource = self; _tableView.delegate = self; [self.view addSubview:_tableView];
因為要展示數據,所以必須要使用系統內部提供的兩個協議,數據源協議UITableDataSource,代理協議UITableDelegate
因為簽訂了UITableDataSource協議,所以有兩個必須要實現的方法
//每個分區多少行 - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section; //每行顯示的內容,也就cell的內容 - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath;
#pragma mark ------數據源協議的方法-------- //返回分區多少行 - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{ return [_dataArrary count]; } //每行顯示的內容 - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{ //標識符 static NSString *reuseIdentifier = @"reuse"; //通過重用標識符找cell UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:reuseIdentifier]; //判斷是否為空,是的話重新創建 if (cell == nil) { cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:reuseIdentifier]autorelease]; } //選中的一行不會有格式顯示,預設選中的為灰色 cell.selectionStyle = UITableViewCellSelectionStyleNone; cell.textLabel.text = [[_dataArrary objectAtIndex:indexPath.row] name]; cell.detailTextLabel.text = [[_dataArrary objectAtIndex:indexPath.row] age]; return cell; }
因為 要註意重用池的使用,如果 cell每次使用都要重新創建的話,那會造成很大的記憶體負擔,如果使用重用池,當cell滑出屏幕之外,被滑出的cell會放入重用池中,當下次使用,根據重用標識符來判斷,如果為空,則重新創建,否則則使用已有的cell。
每個cell都相當於button的作用,都可以點擊,都可以選定,所以系統內部也規定了,cell有專門的點擊方法
//點擊單元格觸發的方法 - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{ //push操作,傳值 DetailViewController *detailVC = [[DetailViewController alloc] init]; detailVC.student = _dataArrary[indexPath.row]; [self.navigationController pushViewController:detailVC animated:YES]; [detailVC release]; }
對錶視圖也可以 進行一些操作,比如刪除,添加和移動。
如果想刪除和添加的話有四步可以 實現 這兩個功能
//增加刪除功能顯示 並不能執行刪除操作 [_tableView setEditing:YES animated:YES];
每一個視圖控制器都有一個編輯按鈕,因為項目中編輯的應用場景非常多,所以系統預留了一個編輯按鈕供我們使用。
#pragma mark -------刪除,添加數據---------- //1.讓將要執行刪除,添加操作的表視圖處於編輯狀態 - (void)setEditing:(BOOL)editing animated:(BOOL)animated{ //先執行父類中的這個方法 [super setEditing:editing animated:animated]; //表視圖執行此方法 [self.tableView setEditing:editing animated:animated]; } //2.指定表視圖中哪些行可以處於編輯狀態 - (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath{ //前五行可以處於編輯狀態 // if (indexPath.row < 5) { // return YES; // } // return NO; //這個方法預設的是全部行都可以進行編輯 return YES; } //3.指定編輯樣式,到底是刪除還是添加 - (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath{ //這個方法預設的是刪除樣式,即UITableViewCellEditingStyleDelete //添加樣式 //return UITableViewCellEditingStyleInsert; //前六行是刪除樣式,之後的全部行是添加樣式 // if (indexPath.row < 6) { // return UITableViewCellEditingStyleDelete; // }else{ // return UITableViewCellEditingStyleInsert; // } } //4.不管是刪除還是添加,這個方法才是操作的核心方法,當點擊刪除或者添加按鈕時,需要做什麼事情,怎麼樣才能完成刪除還是添加操作,全部在這個方法內部指定。 - (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath{ //表視圖開始更新 [tableView beginUpdates]; if (editingStyle == UITableViewCellEditingStyleDelete) { //將該位置下的單元格刪除 [tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationFade]; //刪除數據數組中,與該單元格綁定的數據‘ [_dataArrary removeObjectAtIndex:indexPath.row]; }else if (editingStyle == UITableViewCellEditingStyleInsert){ Student *student = _dataArrary[indexPath.row]; //構建一個位置信息 NSIndexPath *index = [NSIndexPath indexPathForRow:0 inSection:0]; [tableView insertRowsAtIndexPaths:@[index] withRowAnimation:UITableViewRowAnimationTop]; [_dataArrary insertObject:student atIndex:index.row]; } //表視圖結束更新 [tableView endUpdates]; }
同樣的 ,移動也是相同的步驟,不同於刪除和添加的方法就是核心處理方式的不同,也就是第四步
#pragma mark ------表視圖移動的操作--------- //1.移動的第一步也是需要將表視圖的編輯狀態打開 //2.指定哪些行可以進行移動 - (BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath{ //預設都可以移動 return YES; } //3.移動完成之後要做什麼事,怎麼完成移動 //sourceIndexPath原位置 //destinationIndexPath新位置 - (void)tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)sourceIndexPath toIndexPath:(NSIndexPath *)destinationIndexPath{ //先記錄原有位置下的模型數據 Student *student = _dataArrary[sourceIndexPath.row]; [student retain]; //刪除原位置下的模型數據 [_dataArrary removeObjectAtIndex:sourceIndexPath.row]; //在新位置將記錄的模型數據添加到數據數組中 [_dataArrary insertObject:student atIndex:destinationIndexPath.row]; [student release]; }
移動呢,就是先記錄好原有位置的數據,再刪除原位置的數據,然後在新位置上,把記錄的數據添加到模型數組中。
註意:
UITableView,是展示數據的基礎,對於新手來說,還是很容易上手的,數據源協議有除了兩個必要的方法之外,還可以通過方法來顯示有多少個分區,並顯示分區標題,根據分區顯示索引。