1 /* 登陸按鈕監聽賬號、密碼輸入框的通知 2 * 只有當兩者都有內容的時候才能激活登陸按鈕 3 */ 4 - (void) loginButtonListening{ 5 // 監聽賬號輸入 6 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(textChange) name:UITextFieldTextDidChangeNotification object:self.accountText]; 7 8 // 監聽密碼輸入 9 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(textChange) name:UITextFieldTextDidChangeNotification object:self.pwdText];10 }11 12 // 記得要在自身被銷毀的時候取消消息訂閱13 - (void)dealloc {14 [[NSNotificationCenter defaultCenter] removeObserver:self];15 }16 17 // 登陸按鈕監聽的觸發事件18 - (void) textChange {19 // 只有當賬號、密碼不為空的時候,才能使用登陸按鈕20 self.loginButton.enabled = self.accountText.text.length && self.pwdText.text.length;21 }
/** 點擊登陸 */- (IBAction)login { // 檢測賬號 if (![self.accountText.text isEqualToString:@"hw"]) { NSLog(@"賬號不存在"); return; } // 檢測密碼 if (![self.pwdText.text isEqualToString:@"123"]) { NSLog(@"密碼不正確"); return; } // 根據Segue ID 執行跳轉 [self performSegueWithIdentifier:@"contactList" sender:nil];}
1 /** 點擊登陸 */ 2 - (IBAction)login { 3 // 檢測賬號 4 if (![self.accountText.text isEqualToString:@"hw"]) { 5 [MBPRogressHUD showError:@"賬號不存在"]; 6 return; 7 } 8 9 // 檢測密碼10 if (![self.pwdText.text isEqualToString:@"123"]) {11 [MBProgressHUD showError:@"密碼錯誤"];12 return;13 }14 15 // 登陸中,遮蓋屏幕,禁止用戶進行其他操作16 [MBProgressHUD showMessage:@"正在使勁登錄中..."];17 18 // 模擬登陸過程,延遲跳轉19 dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{20 // 移除遮蓋21 [MBProgressHUD hideHUD];22 23 // 根據Segue ID 執行跳轉24 [self performSegueWithIdentifier:@"contactList" sender:nil];25 });26 }
1 // 根據Segue ID 執行跳轉2 [self performSegueWithIdentifier:@"contactList" sender:nil];
1 /** 點擊記住密碼 */ 2 - (IBAction)keepPwdSwitch { 3 if (!self.keepPwd.isOn) { 4 [self.autoLogin setOn:NO]; 5 } 6 } 7 8 /** 點擊自動登陸 */ 9 - (IBAction)autoLoginSwitch {10 if (self.autoLogin.isOn) {11 [self.keepPwd setOn:YES];12 }13 }
1 /** 點擊注銷 */ 2 - (IBAction)logout:(UIBarButtonItem *)sender { 3 UIActionSheet *sheet = [[UIActionSheet alloc] initWithTitle:@"確定要注銷?" delegate:self cancelButtonTitle:@"取消" destructiveButtonTitle:@"確定" otherButtonTitles:nil, nil]; 4 5 [sheet showInView:self.view]; 6 } 7 8 #pragma mark - ActionSheet delegate function 9 - (void)actionSheet:(UIActionSheet *)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex {10 if (buttonIndex != 0) return;11 12 // 彈出一個棧頂控制器,即本控制器,回到上一頁13 [self.navigationController popViewControllerAnimated:YES];14 }
1 - (void)viewDidLoad { 2 [super viewDidLoad]; 3 // Do any additional setup after loading the view. 4 5 // 設置“添加”按鈕的激活狀態 6 self.addButton.enabled = NO; 7 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(textChange) name:UITextFieldTextDidChangeNotification object:self.nameText]; 8 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(textChange) name:UITextFieldTextDidChangeNotification object:self.phoneText]; 9 }10 11 - (void)dealloc {12 // 取消訂閱消息監聽13 [[NSNotificationCenter defaultCenter] removeObserver:self];14 }15 16 /** 姓名、電話文本編輯消息處理 17 * 只有當姓名、電話不為空的時候才能使用“添加”按鈕18 */19 - (void) textChange {20 self.addButton.enabled = self.nameText.text.length && self.phoneText.text.length;21 }
1 // 等界面完全顯示完畢,再彈出鍵盤2 - (void)viewDidAppear:(BOOL)animated {3 [super viewDidAppear:animated];4 5 // 將焦點放在“姓名”輸入框6 [self.nameText becomeFirstResponder];7 }
1 /** 點擊添加按鈕 */ 2 - (IBAction)add { 3 // 1.關閉當前控制器 4 [self.navigationController popViewControllerAnimated:YES]; 5 6 // 2.使用模型傳遞數據給上一個控制器(ContactListViewController),使用代理通知數據更新 7 Contact *contact = [[Contact alloc] init]; 8 contact.name = self.nameText.text; 9 contact.phone = self.phoneText.text;10 [self.delegate addViewController:self didAddedContact:contact];11 }
1 #pragma mark - AddViewController delegate function2 /** 添加聯系人后,更新聯系人列表數據 */3 - (void)addViewController:(AddViewController *)addViewController didAddedContact:(Contact *)contact {4 NSMutableArray *mcontacts = [NSMutableArray arrayWithArray:self.contacts];5 [mcontacts addObject:contact];6 self.contacts = mcontacts;7 [self.tableView reloadData];8 }
1 + (instancetype) cellWithTableView:(UITableView *) tableView {2 // cell ID 要在storyboard中設置好3 static NSString *ID = @"contactCell";4 // 先從緩存池尋找,如果找不到就從storyboard中創建一個5 return [tableView dequeueReusableCellWithIdentifier:ID];6 }
1 #pragma mark - Segue相關 2 - (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender { 3 // 取得目標控制器 4 id controller = segue.destinationViewController; 5 6 // 判斷跳轉目標 7 if ([controller isKindOfClass:[AddViewController class]]) { 8 // 如果是“添加聯系人” 9 AddViewController *addViewController = controller;10 addViewController.delegate = self;11 }12 13 if ([controller isKindOfClass:[EditViewController class]]) {14 // 如果是“查看/編輯聯系人”15 EditViewController *editViewController = controller;16 17 // 取出數據18 NSIndexPath *indexPath = [self.tableView indexPathForSelectedRow];19 editViewController.contact = self.contacts[indexPath.row];20 21 // 設置代理22 editViewController.delegate = self;23 }24 25 }
1 - (void)viewDidLoad { 2 [super viewDidLoad]; 3 // Do any additional setup after loading the view. 4 5 // 加載數據 6 self.nameText.text = self.contact.name; 7 self.phoneText.text = self.contact.phone; 8 9 // 設置輸入監聽10 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(textChange) name:UITextFieldTextDidChangeNotification object:self.nameText];11 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(textChange) name:UITextFieldTextDidChangeNotification object:self.phoneText];12 }
1 /** 點擊“編輯”或"取消” */ 2 - (IBAction)editOrCancel:(UIBarButtonItem *)sender { 3 // 轉變后的狀態 4 BOOL isChangedToEditMode = [sender.title isEqualToString:@"編輯"]? YES:NO; 5 6 if (isChangedToEditMode) { 7 // 點擊"編輯" 8 // 1.轉變title 9 sender.title = @"取消";10 11 // 2.轉變編輯狀態12 self.nameText.enabled = YES;13 self.phoneText.enabled = YES;14 self.saveButton.hidden = NO;15 16 // 獲得輸入焦點17 [self.nameText becomeFirstResponder];18 } else {19 // 點擊“取消”20 // 1.轉變title21 sender.title = @"編輯";22 23 // 2.轉變編輯狀態24 self.nameText.enabled = NO;25 self.phoneText.enabled = NO;26 self.saveButton.hidden = YES;27 28 // 3.還原數據29 self.nameText.text = self.contact.name;30 self.phoneText.text = self.contact.phone;31 32 // 4.退出鍵盤33 [self.view endEditing:YES];34 }35 36 }37 38 /** 消息監聽事件 */39 - (void) textChange {40 self.saveButton.enabled = self.nameText.text.length && self.phoneText.text.length;41 }
1 #pragma mark - EditViewController delegate function2 /** “編輯聯系人”的“保存”代理方法, 刷新數據 */3 - (void)editViewController:(EditViewController *)editViewController didSavedContact:(Contact *)contact {4 [self.tableView reloadData];5 }
1 + (instancetype) cellWithTableView:(UITableView *) tableView {2 // cell ID 要在storyboard中設置好3 static NSString *ID = @"contactCell";4 // 先從緩存池尋找,如果找不到就從storyboard中創建一個5 return [tableView dequeueReusableCellWithIdentifier:ID];6 }
1 /**2 * 如果cell是通過storyboard或者xib創建,不會調用此方法3 * 如果使用代碼創建cell,才會調用這個方法來初始化cell4 */5 - (instancetype) initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier {6 NSLog(@"initWithStyle");7 self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];8 return self;9 }
1 /** 2 * 如果cell是通過storyboard或者xib創建,創建完畢會調用這個方法 3 * 可以在這里初始化cell 4 */ 5 - (void) awakeFromNib { 6 // 自定義一個分割線 7 UIView *divideLine = [[UIView alloc] init]; 8 [divideLine setBackgroundColor:[UIColor blackColor]]; 9 [divideLine setAlpha:0.2];10 [self.contentView addSubview:divideLine];11 self.divideLine = divideLine;12 }13 14 /**15 * 在此方法中,cell的frame確定被初始化完成,可以再這里初始化其子控件的frame16 */17 - (void)layoutSubviews {18 // 切記調用父類方法!19 [super layoutSubviews];20 21 CGFloat lineHeight = 1;22 CGFloat lineWidth = self.frame.size.width;23 CGFloat lineX = 0;24 CGFloat lineY = self.frame.size.height - 1;25 26 self.divideLine.frame = CGRectMake(lineX, lineY, lineWidth, lineHeight);27 }
1 #pragma mark - AddViewController delegate function 2 /** 添加聯系人后,更新聯系人列表數據 */ 3 - (void)addViewController:(AddViewController *)addViewController didAddedContact:(Contact *)contact { 4 NSMutableArray *mcontacts = [NSMutableArray arrayWithArray:self.contacts]; 5 [mcontacts addObject:contact]; 6 self.contacts = mcontacts; 7 8 // 保存數據到plist文件 9 [self saveContactsDataToFile];10 11 // 刷新界面數據12 [self.tableView reloadData];13 }14 15 #pragma mark - EditViewController delegate function16 /** “編輯聯系人”的“保存”代理方法, 刷新數據 */17 - (void)editViewController:(EditViewController *)editViewController didSavedContact:(Contact *)contact {18 // 保存數據19 [self saveContactsDataToFile];20 // 刷新數據21 [self.tableView reloadData];22 }23 24 #pragma mark - 加載、保存、讀取數據25 /** 保存聯系人數據到plist */26 - (void) saveContactsDataToFile {27 // 沙盒路徑28 NSString *path = NSHomeDirectory();29 // Documents路徑30 NSString *docPath = [path stringByAppendingPathComponent:@"Documents"];31 // plist文件路徑32 NSString *filePath = [docPath stringByAppendingPathComponent:@"contacts.plist"];33 34 NSMutableArray *dictArray = [NSMutableArray array];35 for (Contact *contact in self.contacts) {36 // 將模型轉換成字典進行存儲37 NSDictionary *dict = [Contact dictionaryWithContact:contact];38 [dictArray addObject:dict];39 }40 [dictArray writeToFile:filePath atomically:YES];41 NSLog(@"save to : %@", filePath);42 }
1 /** 加載數據 */ 2 - (NSArray *) contacts { 3 if (nil == _contacts) { 4 // 沙盒路徑 5 NSString *path = NSHomeDirectory(); 6 // Documents路徑 7 NSString *docPath = [path stringByAppendingPathComponent:@"Documents"]; 8 // plist文件路徑 9 NSString *filePath = [docPath stringByAppendingPathComponent:@"contacts.plist"];10 11 // 如果plist文件不存在12 NSFileManager *fileManager = [NSFileManager defaultManager];13 if (![fileManager fileExistsAtPath:filePath]) {14 _contacts = [NSArray array];15 return _contacts;16 }17 18 // 如果plist文件存在,開始讀取19 NSArray *contacts = [NSArray arrayWithContentsOfFile:filePath];20 NSMutableArray *mcontacts = [NSMutableArray array];21 for (NSDictionary *dict in contacts) {22 Contact *contact = [Contact contactWithDictionary:dict];23 [mcontacts addObject:contact];24 }25 26 _contacts = mcontacts;27 }28 29 return _contacts;30 }
1 /** 2 * 把初始化代碼放在viewDidAppear 3 * 讓view完全呈現之后才進行自動登陸,否則拿不到view,hideHUD的時候會失效 4 */ 5 - (void)viewDidAppear:(BOOL)animated { 6 // 設置登陸狀態 7 [self readLoginStatus]; 8 9 // 初始化登陸按鈕狀態10 if (!self.accountText.text.length || !self.pwdText.text.length) {11 self.loginButton.enabled = NO;12 }13 14 // 登陸按鈕開始監聽賬號、密碼輸入框15 [self loginButtonListening];16 }17 18 /** 讀取登陸狀態 */19 - (void) readLoginStatus {20 // 記住密碼、自動登錄開關狀態21 NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];22 self.keepPwd.on = [defaults boolForKey:@"keepPwd"]? YES:NO; // 防止鍵值對為nil23 self.autoLogin.on = [defaults boolForKey:@"autoLogin"]? YES:NO;24 25 // 賬號、密碼26 if (self.keepPwd.isOn) {27 self.accountText.text = [defaults objectForKey:@"account"];28 self.pwdText.text = [defaults objectForKey:@"pwd"];29 }30 31 // 自動登陸32 if (self.autoLogin.isOn) {33 [self login];34 }35 }
1 /** 點擊登陸 */ 2 - (IBAction)login { 3 // 檢測賬號 4 if (![self.accountText.text isEqualToString:@"hw"]) { 5 [MBProgressHUD showError:@"賬號不存在"]; 6 return; 7 } 8 9 // 檢測密碼10 if (![self.pwdText.text isEqualToString:@"123"]) {11 [MBProgressHUD showError:@"密碼錯誤"];12 return;13 }14 15 // 登陸中,遮蓋屏幕,禁止用戶進行其他操作16 [MBProgressHUD showMessage:@"正在使勁登錄中..."];17 18 // 模擬登陸過程,延遲跳轉19 dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{20 // 移除遮蓋21 [MBProgressHUD hideHUD];22 23 // 根據Segue ID 執行跳轉24 [self performSegueWithIdentifier:@"contactList" sender:nil];25 });26 27 // 保存登陸狀態28 NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];29 [defaults setBool:self.keepPwd.isOn forKey:@"keepPwd"];30 [defaults setBool:self.autoLogin.isOn forKey:@"autoLogin"];31 32 // 保存賬號、密碼信息33 if (self.keepPwd.isOn) {34 [defaults setObject:self.accountText.text forKey:@"account"];35 [defaults setObject:self.pwdText.text forKey:@"pwd"];36 }37 }
1 /** 自動登陸標識 */ 2 @property(nonatomic, assign) BOOL stopAutoLogin; 3 4 - (void)viewDidDisappear:(BOOL)animated { 5 // 當不是初次出現在屏幕上,禁止自動登陸 6 self.stopAutoLogin = YES; 7 } 8 9 /** 讀取登陸狀態 */10 - (void) readLoginStatus {11 // 記住密碼、自動登錄開關狀態12 NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];13 self.keepPwd.on = [defaults boolForKey:@"keepPwd"]? YES:NO; // 防止鍵值對為nil14 self.autoLogin.on = [defaults boolForKey:@"autoLogin"]? YES:NO;15 16 // 賬號、密碼17 if (self.keepPwd.isOn) {18 self.accountText.text = [defaults objectForKey:@"account"];19 self.pwdText.text = [defaults objectForKey:@"pwd"];20 }21 22 // 自動登陸23 if (!self.stopAutoLogin && self.autoLogin.isOn) {24 [self login];25 }26 }
1 /** 2 * 如果實現了這個方法,就自動實現了滑動刪除功能 3 * 點擊了“刪除”按鈕就會調用 4 * 實質是提交了一個編輯操作導致調用(刪除/添加/編輯) 5 * @param editingStyle 編輯行為 6 * @param indexPath 操作行號 7 */ 8 - (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath { 9 // 如果是刪除操作10 if (editingStyle == UITableViewCellEditingStyleDelete) {11 // 1.刪除數據12 NSMutableArray *marray = [NSMutableArray arrayWithArray:self.contacts];13 [marray removeObjectAtIndex:indexPath.row];14 self.contacts = marray;15 16 // 2.刷新界面17 // [self.tableView reloadData];18 // 只刪掉需要刪除的一行,不必刷新所有數據19 // 使用這個方法,必須刪除對應的模型數據,數量要對應20 [self.tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationLeft];21 22 // 3.更改plist數據23 [self saveContactsDataToFile];24 }25 }
1 - (void)viewDidLoad { 2 [super viewDidLoad]; 3 4 // 設置無系統自帶分割線 5 [self.tableView setSeparatorStyle:UITableViewCellSeparatorStyleNone]; 6 7 // 取出原來在storyboard中創建的“+”按鈕 8 UIBarButtonItem *addItem = self.navigationItem.rightBarButtonItem; 9 10 // 創建一個“垃圾桶”按鈕11 UIBarButtonItem *deleteItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemTrash target:self action:@selector(deleteCheck)];12 13 // 都放入到右邊的狀態欄14 self.navigationItem.rightBarButtonItems = @[deleteItem, addItem];15 }
1 // 點擊狀態欄按鈕“垃圾桶”,使所有cell進入編輯狀態或者退出編輯狀態2 - (void) deleteCheck {3 // self.tableView.editing = !self.tableView.editing;4 [self.tableView setEditing:!self.tableView.editing animated:YES];5 }
1 // 改變編輯狀態下的編輯按鈕 2 - (UITableViewCellEditingStyle) tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath { 3 if (indexPath.row == 0) { 4 // 這里改為“添加”符號,需要自定義事件 5 return UITableViewCellEditingStyleInsert; 6 } else if (indexPath.row == 1) { 7 // none就是什么都沒有,沒有作用 8 return UITableViewCellEditingStyleNone; 9 } else {10 // 默認就是“刪除”11 return UITableViewCellEditingStyleDelete;12 }13 }
新聞熱點
疑難解答