2015年07月21日第13天筆記
一、導航控制器連線
從一個TableView控制器到View控制器
1)兩個控制器要有對應的關聯類
2)TableView的cell要設定id,保證在關聯類裡取到它,負責導航連線無效,因為壓根就沒取到它
3)用cell把View控制器push進來
4)再往TableView的導航條裡拖左右item(注意:如果這個TableView是拖導航控制器自帶的,那麼只能拖右邊的)
5)如果往TableView的導航條裡拖左右item,同時設定它上一個的返回按鈕;那麼這個返回按鈕將被它的左item覆蓋掉
二、導航控制器結構的結論
1)根控制器只會載入一次,消失後,再顯示不在載入
2)其餘子控制器消失後,再顯示將重新載入
三、導航控制器生命週期結論
1)是在各自的控制器裡通過實現父類方法管理的
2)各控制器顯示和消失的過程實質上是交替進行的
3)涉及的相關父類方法
// 控制器view載入完成的時候呼叫
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
NSLog(@"viewDidLoad -- two");
}
// 控制器的view將要顯示
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillDisappear:animated];
NSLog(@"viewWillAppear -- two" );
}
// 控制器的view已經顯示
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
NSLog(@"viewDidAppear -- two");
}
// 控制器view將要消失
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
NSLog(@"viewWillDisappear -- two");
}
// 控制器view已經消失
- (void )viewDidDisappear:(BOOL)animated
{
[super viewDidDisappear:animated];
NSLog(@"viewDidDisappear -- two");
}
四、改變pickerView大小 國旗選擇專案
CGAffineTransform t0 = CGAffineTransformMakeTranslation(0, flag.bounds.size.height / 2);
CGAffineTransform s0 = CGAffineTransformMakeScale(1, 1);//變形範圍
CGAffineTransform t1 = CGAffineTransformMakeTranslation(0, -flag.bounds.size.height / 2);
flag.transform = CGAffineTransformConcat(t0, CGAffineTransformConcat(s0, t1));
問題:CGAffineTransform 結構體的含義???
五、跳轉頁面 資料順傳原理 傳到下一個控制器A–》B
1)時機:本控制器的控制元件的觸發事件
2)原理:在目標控制器B裡設定儲存這個資料的屬性變數,那麼當在源控制器A建立目標控制器B物件的時候,把源控制器A的資料,存在這個變數裡
那麼,這時資料就會到達目標控制器B。關鍵:事先在B定義個接收變數
六、跳轉頁面 資料逆傳原理 傳到上一個控制器B–》A
1)時機:本控制器的控制元件的觸發事件
2)原理:設定一個Block或代理
實現方法一:
用Block:
1)事先準備:在B定義一個帶參無返回的Block
2)在A跳到B之前,A給B的Block一個實現方法C
3)B調回A之前,向它Block傳參
4)跳轉後,會自動執行方法C,A從方法C中得到B傳的引數
用代理
1)事先準備:在定義一個代理協議和代理屬性
2)在A設定代理並實現代理方法C
3)B調回A之前,用代理屬性呼叫代理方法C
4)跳轉後,會自動執行方法C,A從方法C中得到B傳的引數
總結:
關鍵點:
1)是在A-》B之前建立的目標控制器B物件下手,因為在跳轉到B之後,銷燬B之前,B始終是這個B,裡面的資料和方法始終會和A關聯
2)準備使用在- (void)prepareForSegue:(UIStoryboardSegue*)segue sender:(id)sender 中完成
基於關鍵點:
B要做好事先準備
1)順傳:B要定義一個接收變數
2)逆傳:定義一個Block或者定義代理變數
A對建立的B物件下手
1)順傳:賦值
2)逆傳:Block實現並賦值;設定並實現代理
私人通訊錄專案分析
1、功能分析
1)登入
2)新增
3)編輯
4)登出
5)顯示
2.UI分析
2.1、登入介面
1)使用者、密碼輸入框
2)記住密碼、自動登入選擇按鈕
3)登入按鈕 跳到顯示介面
2.2、新增介面
1)介面標題 返回按鈕
2)姓名、電話輸入框
3)新增按鈕
2.3.編輯介面
1)介面標題 編輯按鈕 返回按鈕
2)姓名、電話輸入框
3)儲存按鈕
2.4.顯示介面
1)銷燬按鈕、介面標題、新增按鈕
2)跳到登入介面
3)跳到新增介面
4)跳到編輯介面
3.UI實現
4.程式碼實現
跳轉傳資料要重寫這個方法
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
5.容易忘記的程式碼
1)延遲+載入效果
[SVProgressHUD showWithStatus:@"正在載入...." maskType:SVProgressHUDMaskTypeBlack];
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
[SVProgressHUD dismiss];
if ([name isEqualToString:@"1"]&&[password isEqualToString:@"1"]) {
//跳到聯絡人介面 login2contacts 是在面板上設定的
[self performSegueWithIdentifier:@"login2contacts" sender:nil];
}
else
{
[SVProgressHUD showErrorWithStatus:@"賬號或密碼不正確" maskType:SVProgressHUDMaskTypeBlack];
}
});
2)彈框建立 和 事件觸發
// 登出按鈕的點選事件
- (IBAction)logoutClick:(id)sender
{
UIActionSheet* sheet = [[UIActionSheet alloc] initWithTitle:@"你確定要離開我嘛" delegate:self cancelButtonTitle:@"不要" destructiveButtonTitle:@"我就是要離開你!!!" otherButtonTitles:nil, nil];
[sheet showInView:self.view];
}
- (void)actionSheet:(UIActionSheet*)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex
{
if (buttonIndex)
return;
// 0.25
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.25 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
// pop
[self.navigationController popViewControllerAnimated:YES];
});
}
3)判斷代理是否實現和呼叫代理方法
if ([self.delegate respondsToSelector:@selector(editViewController:withContact:)]) {
[self.delegate editViewController:self withContact:self.contact];
}
4)定義Block(以下兩種寫法完全等同)
@property (nonatomic, copy) void (^editBlock)();
@property (nonatomic, copy) dispatch_block_t editBlock;
5)判斷Block是否實現和呼叫Block
if (self.editBlock) {
self.editBlock();
}
6)手動跳轉介面時 判斷目標控制器的類別 做相應處理
[self performSegueWithIdentifier:@"login2contacts" sender:nil;
- (void)prepareForSegue:(UIStoryboardSegue*)segue sender:(id)sender
{
// 獲取目標控制器(UIViewController)
UIViewController* vc = segue.destinationViewController;
if ([vc isKindOfClass:[AddViewController class]]) {
// 獲取目標控制器(強轉成 addvc)
AddViewController* add = (AddViewController*)vc;
// 給目標控制器設定代理
add.delegate = self;
}
else {
EditViewController* edit = (EditViewController*)vc;
// 設定代理
// edit.delegate = self;
edit.editBlock = ^{
[self.tableView reloadData];
};
// 先獲取到 點選的 indexpath
NSIndexPath* path = [self.tableView indexPathForSelectedRow];
// 通過indexpath 來 獲取 需要傳遞的 物件
edit.contact = self.contacts[path.row];
}
}
7)獲取TableView中選中Cell的索引
NSIndexPath* path = [self.tableView indexPathForSelectedRow];
8)文字框,開關控制元件都繼承自UIControl 都可以addTarget 只對監聽不同狀態
// 監聽文字框的內容的改變
[self.usernameField addTarget:self action:@selector(textChange) forControlEvents:UIControlEventEditingChanged];
[self.passwordField addTarget:self action:@selector(textChange) forControlEvents:UIControlEventEditingChanged];
// 監聽開關的事件
[self.remPwdSwitch addTarget:self action:@selector(remPwdSwitchChange) forControlEvents:UIControlEventValueChanged];
[self.autoLoginSwitch addTarget:self action:@selector(autoLoginSwitchChange) forControlEvents:UIControlEventValueChanged];
9)可以選擇view將要顯示時,重新整理資料
//- (void)viewWillAppear:(BOOL)animated
//{
//
// [super viewWillAppear:animated];
//
// // 重新整理資料
// [self.tableView reloadData];
//}
10) 回到上一個頁面
[self.navigationController popViewControllerAnimated:YES];
11) 從TaleViewController控制器載入cell://顯示樣式在面板設定下
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"contact"];
Person *person = self.persons[indexPath.row];
cell.textLabel.text = person.name;
//顯示樣式在面板設定下
cell.detailTextLabel.text = person.phoneNum;
return cell;
}
12)取消沒有資料的分割線
self.tableView.tableFooterView = [[UIView alloc] init] ;