效果如圖:
可以根據輸入的關鍵字,在TableView中顯示符合的數據。
圖中分組顯示和索引效果,前面的博文已經記錄,不再贅述。下面的例子是基於前文的基礎上修改的,所以文件名啥的,請參考前文。
第一步是在TableView上方添加一個Search Bar,這里有一點需要注意,必須先把TableView拖下來,留下空間放Search Bar,不要在Table View占滿屏幕的情況下把Search Bar拖到Table View頂部。區別在於,使用后面的方法,Search Bar是作為Table View的Header部分添加的,而前面的方法,Search Bar是獨立的。在添加索引功能時,如果作為Table View的Header添加,右側的索引會遮住Search Bar的右邊部分。Search Bar幾個常用屬性:
Placeholder是提示,就是hint屬性,Corretion是自動修正,一般設為NO,即不修正,Show Cancel Button是顯示取消按鈕,我這里勾選。選中Search Bar的情況下切換到Connections Inspector面板,delegate與File’s Owner建立連接(我們會在ViewController中支持UISearchBarDelegate協議)。與前面幾篇文章的例子相 同,ViewController文件名為PDViewController.h和PDViewController.m。
第二步,添加Table View和Search Bar的Outlet.按住Control鍵,分別拖動Table View和Search Bar到PDViewController.h,添加Outlet
第三步,就是PDViewController代碼:
PDViewController.h:
#import <UIKit/UIKit.h>
@interface PDViewController : UIViewController<UITableViewDelegate,UITableViewDataSource,UISearchBarDelegate>
@property (strong,nonatomic) NSDictionary *names;
@property (strong,nonatomic) NSMutableDictionary *mutableNames;
@property (strong,nonatomic)NSMutableArray *mutableKeys;
//可變字典和可變數組,用於存儲顯示的數據,而不可變的字典用於存儲從文件中讀取的數據
@property (strong, nonatomic) IBOutlet UITableView *table;
@property (strong, nonatomic) IBOutlet UISearchBar *search;
-(void)resetSearch;
//重置搜索,即恢復到沒有輸入關鍵字的狀態
-(void)handleSearchForTerm:(NSString *)searchTerm;
//處理搜索,即把不包含searchTerm的值從可變數組中刪除
@end
#import "PDViewController.h"
#import "NSDictionary+MutableDeepCopy.h"
@implementation PDViewController
@synthesize names=_names;
@synthesize mutableKeys=_mutableKeys;
@synthesize table = _table;
@synthesize search = _search;
@synthesize mutableNames=_mutableNames;
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Release any cached data, images, etc that aren't in use.
}
#pragma mark - View lifecycle
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
NSString *path=[[NSBundle mainBundle] pathForResource:@"sortednames" ofType:@"plist"];
//取得sortednames.plist絕對路徑
//sortednames.plist本身是一個NSDictionary,以鍵-值的形式存儲字符串數組
NSDictionary *dict=[[NSDictionary alloc] initWithContentsOfFile:path];
//轉換成NSDictionary對象
self.names=dict;
[self resetSearch];
//重置
[_table reloadData];
//重新載入數據
}
- (void)viewDidUnload
{
[self setTable:nil];
[self setSearch:nil];
[super viewDidUnload];
self.names=nil;
self.mutableKeys=nil;
self.mutableNames=nil;
// Release any retained subviews of the main view.
// e.g. self.myOutlet = nil;
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
// Return YES for supported orientations
return (interfaceOrientation != UIInterfaceOrientationPortraitUpsideDown);
}
-(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
//返回分組數量,即Array的數量
return [_mutableKeys count];
//
}
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
if ([_mutableKeys count]==0) {
return 0;
}
NSString *key=[_mutableKeys objectAtIndex:section];
NSArray *nameSection=[_mutableNames objectForKey:key];
return [nameSection count];
//返回Array的大小
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSUInteger section=[indexPath section];
//分組號
NSUInteger rowNumber=[indexPath row];
//行號
//即返回第section組,rowNumber行的UITableViewCell
NSString *key=[_mutableKeys objectAtIndex:section];
//取得第section組array的key
NSArray *nameSection=[_mutableNames objectForKey:key];
//通過key,取得Array
static NSString * tableIdentifier=@"CellFromNib";
UITableViewCell *cell=[tableView dequeueReusableCellWithIdentifier:tableIdentifier];
if(cell==nil)
{
cell=[[UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:tableIdentifier];
}
cell.textLabel.text=[nameSection objectAtIndex:rowNumber];
//從數組中讀取字符串,設置text
return cell;
}
-(NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section
{
if ([_mutableKeys count]==0) {
return 0;
}
NSString *key=[_mutableKeys objectAtIndex:section];
return key;
}
-(NSArray *)sectionIndexTitlesForTableView:(UITableView *)tableView
{
return _mutableKeys;
//通過key來索引
}
-(void)resetSearch
{//重置搜索
_mutableNames=[_names mutableDeepCopy];
//使用mutableDeepCopy方法深復制
NSMutableArray *keyarr=[NSMutableArray new];
[keyarr addObjectsFromArray:[[_names allKeys] sortedArrayUsingSelector:@selector(compare:)]];
//讀取鍵,排序后存放可變數組
_mutableKeys=keyarr;
}
-(void)handleSearchForTerm:(NSString *)searchTerm
{//處理搜索
NSMutableArray *sectionToRemove=[NSMutableArray new];
//分組待刪除列表
[self resetSearch];
//先重置
for(NSString *key in _mutableKeys)
{//循環讀取所有的數組
NSMutableArray *array=[_mutableNames valueForKey:key];
NSMutableArray *toRemove=[NSMutableArray new];
//待刪除列表
for(NSString *name in array)
{//數組內的元素循環對比
if([name rangeOfString:searchTerm options:NSCaseInsensitiveSearch].location==NSNotFound)
{
//rangeOfString方法是返回NSRange對象(包含位置索引和長度信息)
//NSCaseInsensitiveSearch是忽略大小寫
//這里的代碼會在name中找不到searchTerm時執行
[toRemove addObject:name];
//找不到,把name添加到待刪除列表
}
}
if ([array count]==[toRemove count]) {
[sectionToRemove addObject:key];
//如果待刪除的總數和數組元素總數相同,把該分組的key加入待刪除列表,即不顯示該分組
}
[array removeObjectsInArray:toRemove];
//刪除數組待刪除元素
}
[_mutableKeys removeObjectsInArray:sectionToRemove];
//能過待刪除的key數組刪除數組
[_table reloadData];
//重載數據
}
-(NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath
{//TableView的項被選擇前觸發
[_search resignFirstResponder];
//搜索條釋放焦點,隱藏軟鍵盤
return indexPath;
}
-(void)searchBarSearchButtonClicked:(UISearchBar *)searchBar
{//按軟鍵盤右下角的搜索按鈕時觸發
NSString *searchTerm=[searchBar text];
//讀取被輸入的關鍵字
[self handleSearchForTerm:searchTerm];
//根據關鍵字,進行處理
[_search resignFirstResponder];
//隱藏軟鍵盤
}
-(void)searchBar:(UISearchBar *)searchBar textDidChange:(NSString *)searchText
{//搜索條輸入文字修改時觸發
if([searchText length]==0)
{//如果無文字輸入
[self resetSearch];
[_table reloadData];
return;
}
[self handleSearchForTerm:searchText];
//有文字輸入就把關鍵字傳給handleSearchForTerm處理
}
-(void)searchBarCancelButtonClicked:(UISearchBar *)searchBar
{//取消按鈕被按下時觸發
[self resetSearch];
//重置
searchBar.text=@"";
//輸入框清空
[_table reloadData];
[_search resignFirstResponder];
//重新載入數據,隱藏軟鍵盤
}
@end