iOS 程式碼段收集

weixin_34208283發表於2016-04-10

1、純程式碼建立UI,和XIB建立UI(limitedFree TopicView)

//手寫程式碼例項化物件時呼叫此方法
-(instancetype)initWithFrame:(CGRect)frame
{
    if (self = [super initWithFrame:frame]) {
        [self createUI];
    }
    return self;
}

//使用xib資原始檔初始化時呼叫此方法
-(instancetype)initWithCoder:(NSCoder *)aDecoder
{
    if (self = [super initWithCoder:aDecoder]) {
        [self createUI];
    }
    return self;
}

3、儲存圖片到本地相簿和訊息彈框

-(void)longPressImageView:(UILongPressGestureRecognizer *)sender
{
    UIAlertController *controller = [UIAlertController alertControllerWithTitle:@"操作圖片" message:@"image" preferredStyle:UIAlertControllerStyleActionSheet];
    [controller addAction:[UIAlertAction actionWithTitle:@"儲存" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
        //儲存到相簿
        UIImageView *imgView = (UIImageView *)sender.view;
        //第一個引數是要儲存的圖片物件,第二個引數是操作後由self呼叫第3個引數的方法,第4個引數是傳遞給回撥方法的資訊
        UIImageWriteToSavedPhotosAlbum(imgView.image, self, @selector(image:finishedSaveWithError:contextInfo:), nil);
    }]];
    [controller addAction:[UIAlertAction actionWithTitle:@"取消" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
    }]];
    [self presentViewController:controller animated:YES completion:nil];
}

//儲存圖片到相簿的回撥方法  (UIAlertView iOS8之後就不推薦使用)
-(void)image:(UIImage *)image finishedSaveWithError:(NSError *)error contextInfo:(void *)contextInfo{
    if (error) {
        NSLog(@"儲存失敗:%@",error.localizedDescription);
    }else{
        UIAlertView *alerView = [[UIAlertView alloc]initWithTitle:@"提示" message:@"儲存成功" delegate:nil cancelButtonTitle:nil otherButtonTitles:@"ok", nil];
        [alerView show];
    }
}

4、分欄控制器設定按鈕

for (int i = 0; i < array.count;i++) {
        Class cls = NSClassFromString(array[i]);
        
        UIViewController *viewController = [[cls alloc]init];
        
        UINavigationController *nc = [[UINavigationController alloc]initWithRootViewController:viewController];
        
        UIImage *image1 = [UIImage imageNamed:defaultImages[i]];
        
        UIImage *image2 = [[UIImage imageNamed:selectedImages[i]]imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
        //設定分欄按鈕的選中圖片和常態圖片
        nc.tabBarItem = [[UITabBarItem alloc]initWithTitle:nameArray[i] image:image1 selectedImage:image2];
                    //設定導航欄背景顏色
        [nc.navigationBar setBarTintColor:[UIColor colorWithRed:34 /255.0 green:115 / 255.0 blue:193 / 255.0 alpha:1]];
        
        nc.tabBarItem.imageInsets = UIEdgeInsetsMake(7, 0, -7, 0);

        [controllerArray addObject:nc];
    }

5.設定label特殊的字型(一大一小),每個字的顏色

NSMutableAttributedString *str = [[NSMutableAttributedString alloc]initWithString:[model.ratingFinal stringValue]];
    [str addAttribute:NSFontAttributeName value:[UIFont systemFontOfSize:20] range:NSMakeRange(0, 1)];
    [str addAttribute:NSFontAttributeName value:[UIFont systemFontOfSize:13] range:NSMakeRange(1, 2)];
//設定顏色
[str addAttribute:NSForegroundColorAtrributeName value:[UIFont systemFontOfSize:13] range:NSMakeRange(1, 2)];
    self.rateLabel.attributedText = str;

6.資料名稱與關鍵字重名的時候,

1)重寫setter方法
@property (nonatomic,copy,setter=setDescription:)NSString *myDescription;
2)使用JSON ,對映

+(JSONKeyMapper *)keyMapper{
    return [[JSONKeyMapper alloc] initWithDictionary:@{@"GregorianCalendar":@"gregorianCalendar",@"LunarCalendar":@"lunarCalendar",@"ChineseZodiacYear":@"chineseZodiacYear",@"HeavenlyStemsAndEarthlyBranches":@"heavenlyStemsAndEarthlyBranches",@"SolarTerms":@"solarTerms"}];
}

7.關於資料下載的時候強引用的問題

//弱引用
    __weak ViewController *weakSelf = self;
    
    [manager GET:kLimitUrl parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) {
        
        id result = [NSJSONSerialization JSONObjectWithData:responseObject options:NSJSONReadingMutableContainers error:nil];
        if ([result isKindOfClass:[NSDictionary class]]) {
            NSDictionary *dict = result;
            
            for (NSDictionary *appDict in dict[@"applications"]) {
                
                LimitModel *model = [[LimitModel alloc]init];
                [model setValuesForKeysWithDictionary:appDict];
                [weakSelf.dataArray addObject:model];
            }
        }

8.懶載入

//重新實現了getter方法
//在實際使用這個成員變數的時候,才會給它分配記憶體
-(NSMutableArray *)dataArray{
    if (_dataArray==nil) {
        _dataArray = [NSMutableArray array];
    }
    return _dataArray;
}

9.判斷系統版本(iOS7 中會對selected的圖片進行渲染為藍色)

#define iOS7 [[UIDevice currentDevice].systemVersion doubleValue] >= 7.0

10.當前所有顯示的BarButton

UIBarButtonItem *appearance = [UIBarButtonItem appearance];

11.部分程式碼只需執行一次,例如全域性修改標題的顏色
+(void)initialize; 當第一次使用這個類的時候呼叫1次

12.UITextField 自定義搜尋框

//一定要設定,不然不顯示
    textField.leftViewMode = UITextFieldViewModeAlways;
    textField.clearButtonMode = UITextFieldViewModeAlways;

13.取消選中的按鈕,不用迴圈

//UI的修改
    //1)取消前面選中的按鈕
    UIButton *lastBtn = (UIButton *)[_myTabView viewWithTag:300+self.selectedIndex];
    lastBtn.selected = NO;
    UILabel *lastLabel = (UILabel *)[lastBtn viewWithTag:400];
    lastLabel.textColor = [UIColor whiteColor];
-------------------------------------------

//控制按鈕的狀態(self.selectedButton 屬性)
    self.selectedButton.selected = NO;
    btn.selected = YES;
    self.selectedButton = btn;

15.自動計算文字的寬度

  • 自動計算寬度
    第一個引數顯示:文字顯示的最大範圍
    第二個引數:文字顯示的方式
    第三個引數:文字的屬性
    第四個引數:上下文nil
    NSDictionary *dict = @{NSFontAttributeName:[UIFont systemFontOfSize:14]};
    CGFloat fitW = [hDateModel.alertInfoFitting boundingRectWithSize:CGSizeMake(CGFLOAT_MAX, 20) options:NSStringDrawingUsesLineFragmentOrigin attributes:dict context:nil].size.width;         

16.日期計算

    NSDate *date = [NSDate date];
    
    NSCalendar *cal = [NSCalendar currentCalendar];
    
    unsigned int unit = NSCalendarUnitYear | NSCalendarUnitMonth |NSCalendarUnitDay;
    
    NSDateComponents *dc = [cal components:unit fromDate:date];
    
    NSString *urlString = [NSString stringWithFormat:kHomeInfoUrl,hostIp,[dc year],[dc month],[dc day]];

17.isKindOfClass判斷子檢視是否為某個型別,如果是則刪除

    for (UIView *oldSub in self.subviews) {
        if ([oldSub isKindOfClass:[SearchGridCell class]]) {
            [oldSub removeFromSuperview];
        }
    }

19.提示彈框+儲存圖片到本地

-(void)saveImageToLocal:(UILongPressGestureRecognizer *)sender{
    //建立提示控制器
    UIAlertController *alertController = [UIAlertController alertControllerWithTitle:@"儲存到相簿" message:nil preferredStyle:UIAlertControllerStyleActionSheet];
    [alertController addAction:[UIAlertAction actionWithTitle:@"儲存" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
        //儲存到相簿
        UIImageView *imgView = (UIImageView *)sender.view;
        //第一個引數是要儲存的圖片物件,第二個引數是操作後由self呼叫第3個引數的方法,第4個引數是傳遞給回撥方法的資訊
        UIImageWriteToSavedPhotosAlbum(imgView.image, self, @selector(image:finishedSaveWithError:contextInfo:), nil);
    }]];
    //新增提示動作
    [alertController addAction:[UIAlertAction actionWithTitle:@"取消" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
    }]];
    //讓代理執行展示的方法
    [self.delegate presentAlertCotroller:(alertController)];
}

20.處理網址中不易識別的中文字元

url = [url stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];

21.EGO重新整理,非arc(上拉載入更多不需要協議方法)

//上拉載入更多
- (void)scrollViewDidScroll:(UIScrollView *)scrollView{
    [self.refreshView egoRefreshScrollViewDidScroll:scrollView];
    if (_tableView.frame.size.height+_tableView.contentOffset.y > _tableView.contentSize.height+44&&self.isLoadMore==NO) {
        self.pageNum++;
        self.isLoadMore = YES;
        [self addData];
    }
}
-(void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate
{
    [self.refreshView egoRefreshScrollViewDidEndDragging:scrollView];
}


#pragma mark - EGORefreshView的協議方法
-(NSDate *)egoRefreshTableHeaderDataSourceLastUpdated:(EGORefreshTableHeaderView *)view{
    return [NSDate date];
}
-(BOOL)egoRefreshTableHeaderDataSourceIsLoading:(EGORefreshTableHeaderView *)view{
   return _isRefresh;
}
//執行重新整理操作
-(void)egoRefreshTableHeaderDidTriggerRefresh:(EGORefreshTableHeaderView *)view{
    _currentPage = 1;
    _isRefresh = YES;
    [self requestDataFromUrl];
}

22.自定義單例類(LimiteFree)

+ (CacheManager *)shareManager{
    static CacheManager *manager = nil;
    @synchronized(self) {
        if (manager==nil) {
            manager = [[CacheManager alloc]init];
        }
    }
    return manager;
}

23.圖片轉二進位制資料(儲存,快取,收藏)

    //圖片物件轉化為二進位制資料
    NSData *data = UIImagePNGRepresentation(model.image);
    if (data==nil) {
        data = UIImageJPEGRepresentation(model.image, 1);
    }

24.列舉型別

#import "BaseViewController.h"
#import "MenuModel.h"
typedef enum{
    SearchTypeCategory,//分類搜尋
    SearchTypeChoose//智慧選菜
}SearchType;
@interface SearchResultController : BaseViewController
//搜尋條件
@property (nonatomic,strong)NSArray *conditionArray;
//第一頁的列表資料
@property (nonatomic,strong)HomeModel *hModel;
//型別
@property (nonatomic,assign)SearchType type;


if (self.type == SearchTypeCategory) {
        title = @"搜尋結果";
    }else{
        title = @"智慧選菜";
    }

25.Label自動適應大小

//自動適應大小
    self.nameLabel.adjustsFontSizeToFitWidth = YES;

26.列舉

typedef enum{
    SearchTypeCategory,//分類搜尋
    SearchTypeChoose//智慧選菜
}SearchType;
@interface SearchResultController : BaseViewController
//搜尋條件
@property (nonatomic,strong)NSArray *conditionArray;
//第一頁的列表資料
@property (nonatomic,strong)HomeModel *hModel;
//型別
@property (nonatomic,assign)SearchType type;

27.自動獲取label的最大高度

 NSDictionary *dict = @{NSFontAttributeName:[UIFont systemFontOfSize:16]};
  CGFloat height = [model.fittingRestriction boundingRectWithSize:CGSizeMake(280, CGFLOAT_MAX) options:NSStringDrawingUsesLineFragmentOrigin attributes:dict context:nil].size.height;
  h = 10 + height +10;

28.QQ摺疊效果,重新整理固定組

//重新整理介面
    //以動畫的形式重新整理某組的資料,第一個引數是組號的集合物件,第二個引數是重新整理的動畫樣式
    //NSIndexSet:索引集合,其中存放的都是索引
    [self.tableView reloadSections:[NSIndexSet indexSetWithIndex:section] withRowAnimation:UITableViewRowAnimationFade];

29.關於導航欄UINavgationController

1)儘量使用系統自帶的,自定義會丟失狀態列隱藏功能
- (BOOL)prefersStatusBarHidden{
    return YES;
}
2) 自定義會丟失左側拖動返回上個頁面的功能


3)關於設定標題
    //無效
   self.navigationController.navigationItem.title = @"首頁";
    //有效
    self.navigationItem.title = @"首頁";
4)攔截所有push進來的Controller

- (void)pushViewController:(UIViewController *)viewController animated:(BOOL)animated{
    if (self.viewControllers.count > 0) { // 如果現在push的不是棧底控制器(最先push進來的那個控制器)
        viewController.hidesBottomBarWhenPushed = YES;
        // 設定導航欄按鈕
        viewController.navigationItem.leftBarButtonItem = [UIBarButtonItem itemWithImageName:@"navigationbar_back" highImageName:@"navigationbar_back_highlighted" target:self action:@selector(back)];
        viewController.navigationItem.rightBarButtonItem = [UIBarButtonItem itemWithImageName:@"navigationbar_more" highImageName:@"navigationbar_more_highlighted" target:self action:@selector(more)];
    }
    [super pushViewController:viewController animated:animated];
}

30.關於super,子類重新父類方法,父類呼叫方法
當子類進行方法的重寫時,父類的方法內容會被覆蓋掉,這時是執行子類重寫的方法。但有時還是要從子類裡使用父類的原來的那個方法,這時可以使用super關鍵字。

31.init內部會呼叫initWithFrame

32.GCD多執行緒操作
總結:
同步(sync)函式,在當前執行緒中執行
(1、併發佇列:不會開執行緒
(2、序列佇列:不會開執行緒
非同步(async)函式,具備開執行緒能力!!但是不一定開(放到主佇列的時候),在另一條執行緒中執行
(1、併發佇列:開多條執行緒
(2、序列佇列:開一條執行緒

1)用得最多的操作

//獲取全域性佇列
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        //非同步執行
        dispatch_async(queue, ^{
            //下載圖片
            dispatch_async(dispatch_get_main_queue(), ^{
                //回到主執行緒更新UI
            });
        });

2)延時執行

1-呼叫NSObject方法
[Self performSelector:@seletor(run) withObject:nil afterDelay:2.0];
2-GCD(更好用,不用重新生成方法)
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        NSLog(@"2222");
    });

3)保證方法在整個程式只執行一次

static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        
        });

單例單例單例單例單例

+(SchoolManager *)sharedInstance  
{  
    static SchoolManager *sharedManager;  
      
    static dispatch_once_t onceToken;  
    dispatch_once(&onceToken, ^{  
        sharedManager = [[SchoolManager alloc] init];  
    });  
      
    return sharedManager;  
}  

4)組操作,多個請求,請求完成後再執行操作

//建立一個組,
    dispatch_group_t group = dispatch_group_create();
    //開啟一個任務下載圖片1
    __block UIImage *image1 = nil;
    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        //image1 = [];
    });
    
    __block UIImage *image2 = nil;
    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        //image2 = [];
    });
    
    dispatch_group_notify(group, dispatch_get_main_queue(), ^{
        //image1
        //image2
    });

33.高效能切圓角

UIImageView *imageView = [[UIImageView alloc]initWithFrame:CGRectMake(100, 100, 100, 100)];
    UIImage *image = [UIImage imageNamed:@"3.jpg"];
    UIGraphicsBeginImageContextWithOptions(imageView.bounds.size, NO, 1.0);
    [[UIBezierPath bezierPathWithRoundedRect:imageView.bounds cornerRadius:50] addClip];
    [image drawInRect:imageView.bounds];
    imageView.image = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    [self.view addSubview:imageView];

34.cocoapods匯入標頭檔案沒有自動提示

選擇Target -> Build Settings 選單,找到\”User Header Search Paths\”設定項
新增一個值"${SRCROOT}",並且選擇\”Recursive\”,這樣xcode就會在專案目錄中遞迴搜尋檔案

35.形變

//縮放比例
        CGFloat navH = [UIScreen mainScreen].bounds.size.height - 2 * 60;
        CGFloat scale = navH / [UIScreen mainScreen].bounds.size.height;
        
        //選單左邊的間距
        CGFloat leftMenuMargin = [UIScreen mainScreen].bounds.size.width * (1 - scale) * 0.5;
        CGFloat translateX = 200 - leftMenuMargin;
        
        CGFloat topMargin = [UIScreen mainScreen].bounds.size.height * (1 - scale)* 0.5;
        CGFloat translateY = topMargin - 60;
        
        //縮放
        CGAffineTransform scaleForm = CGAffineTransformMakeScale(scale, scale);
        
        //平移
        CGAffineTransform translateForm = CGAffineTransformTranslate(scaleForm, translateX/scale, -translateY/scale);

************************************************************************************
取消形變

self.showingNavigationContronller.view.transform = CGAffineTransformIdentity;

36.陰影

//顯示新的控制器
    NavigationController *newNav = self.childViewControllers[toIndex];
    //設定新的控制器和舊的控制器一樣
    newNav.view.transform = oldNav.view.transform;
    //設定陰影
    newNav.view.layer.shadowColor = [UIColor blackColor].CGColor;
    newNav.view.layer.shadowOffset = CGSizeMake(-3, 0);
    newNav.view.layer.shadowOpacity = 0.2;
    [self.view addSubview:newNav.view];

一個導航控制器的view第一次顯示到它的父控制元件上時,如果transform的縮放值被改了,上面的20高度是不會出來

// 0.移除舊控制器的view
    HMNavigationController *oldNav = self.childViewControllers[fromIndex];
    [oldNav.view removeFromSuperview];
    
    // 1.顯示新控制器的view
    HMNavigationController *newNav = self.childViewControllers[toIndex];
    // 設定新控制的transform跟舊控制器一樣
    newNav.view.transform = oldNav.view.transform;

    [self.view addSubview:newNav.view];

//修改
    HMNavigationController *oldNav = self.childViewControllers[fromIndex];
    [oldNav.view removeFromSuperview];
    
    // 1.顯示新控制器的view
    HMNavigationController *newNav = self.childViewControllers[toIndex];
        [self.view addSubview:newNav.view];
    // 設定新控制的transform跟舊控制器一樣
    newNav.view.transform = oldNav.view.transform;

38.啟動廣告頁面
(預設啟動為storyboard的控制器,設定id,新建廣告控制器為啟動控制器),程式碼取出預設的控制器,兩秒後跳轉

 //3.2s後調到下一個控制器
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        UIWindow *window = [UIApplication sharedApplication].keyWindow;
        UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
        window.rootViewController = [storyboard instantiateViewControllerWithIdentifier:@"Main"];
    });

39.UIView與layer的形變
UIView是2D,CG
layer是3D,CA

40.轉場動畫(網易頭像翻轉)

    [UIView transitionWithView:self.iconView duration:1.0 options:UIViewAnimationOptionTransitionFlipFromLeft animations:^{
        self.iconView.image = [UIImage imageNamed:@"user_defaultgift"];
    } completion:^(BOOL finished) {
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            [UIView transitionWithView:self.iconView duration:1.0 options:UIViewAnimationOptionTransitionFlipFromRight animations:^{
                self.iconView.image = [UIImage imageNamed:@"default_avatar"];
            } completion:^(BOOL finished) {
                nil;
            }];
        });
    }];

41.根據顏色生成圖片

+ (UIImage *)imageWithColor:(UIColor *)color{
    CGFloat imageW = 100;
    CGFloat imageH = 100;
    // 1.開啟基於點陣圖的圖形上下文
    UIGraphicsBeginImageContextWithOptions(CGSizeMake(imageW, imageH), NO, 0.0);
    // 2.畫一個color顏色的矩形框
    [color set];
    UIRectFill(CGRectMake(0, 0, imageW, imageH));
    // 3.拿到圖片
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
    // 4.關閉上下文
    UIGraphicsEndImageContext();
    return image;
}
  1. 設定陰影
    newNav.view.layer.shadowColor = [UIColor blackColor].CGColor;
    newNav.view.layer.shadowOffset = CGSizeMake(-3, 0);
    newNav.view.layer.shadowOpacity = 0.2;

43.NSInteger
NSInteger沒有星號,因為NSInteger根據系統是64位還是32位來判斷自身是long還是int型別,並且它也不是一個標準Objective-C物件。

45.tableView優化
tableView 滑動卡的問題主要是因為:從快取中或者是從本地讀取圖片給UIImage的時候耗費的時間。需要把下面的兩句話放到子執行緒裡面:

NSData *imgData = [NSData dataWithContentsOfURL:[NSURL URLWithString:app.icon]]; //得到影像資料  
        UIImage *image = [UIImage imageWithData:imgData];  

把UIImage賦值給圖片的時候在主執行緒。
子執行緒不能更新UI 所有的UI跟新都是主執行緒執行了。手指滑動螢幕了。或者螢幕的某個方法執行了。

46.new和alloc/init區別
概括來說,new和alloc/init在功能上幾乎是一致的,分配記憶體並完成初始化。

差別在於,採用new的方式只能採用預設的init方法完成初始化,

採用alloc的方式可以用其他定製的初始化方法。

47.array與alloc init區別
array這兩個方式都是建立一個空的Array
[NSArray array]不需要release,使用autoreleasepool機制。
[[NSArray alloc] init]需要自己手動release

48.layout中動畫,要宣告約束的屬性

@property (weak, nonatomic) IBOutlet NSLayoutConstraint *redCon;
- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{
    self.redCon.constant += 100;
    [UIView animateWithDuration:1.0 animations:^{
        [self.view layoutIfNeeded];
    }];
}

49.[[[UIDevice currentDevice]systemVersion]floatvalue]為系統版本

50.載入大圖的時候使用,會自動釋放記憶體

NSString *path = [[NSBundle mainBundle]pathForResource:@"3" ofType:@"jpg"];
    imageView.image = [UIImage imageWithContentsOfFile:path];

51.NSTimer放到NSRunloop裡面,相當於放到子執行緒,不會阻塞主執行緒

[[NSRunLoop currentRunLoop]addTimer:self.timer forMode:NSRunLoopCommonModes];

52.tableView右滑刪除

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath {        
    [_dataArray removeObjectAtIndex:indexPath.row];
    [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObjects:indexPath, nil] withRowAnimation:UITableViewRowAnimationTop];
}

53.UITextField:檢測值改變

[_textField addTarget:self action:@selector(valueChange) forControlEvents:UIControlEventEditingChanged];

54.SDWebImage三方庫使用注意點,在AppDelegate中設定

- (void)applicationDidReceiveMemoryWarning:(UIApplication *)application
{
    // 趕緊清除所有的記憶體快取
    [[SDImageCache sharedImageCache] clearMemory];
    
    // 趕緊停止正在進行的圖片下載操作
    [[SDWebImageManager sharedManager] cancelAll];
}

55.監控網路狀態,在AppDelegate中設定

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

// 4.監控網路

    AFNetworkReachabilityManager *mgr = [AFNetworkReachabilityManager sharedManager];
    // 當網路狀態改變了,就會呼叫
    [mgr setReachabilityStatusChangeBlock:^(AFNetworkReachabilityStatus status) {
        switch (status) {
            case AFNetworkReachabilityStatusUnknown: // 未知網路
            case AFNetworkReachabilityStatusNotReachable: // 沒有網路(斷網)
                HMLog(@"沒有網路(斷網)");
                [MBProgressHUD showError:@"網路異常,請檢查網路設定!"];
                break;
            case AFNetworkReachabilityStatusReachableViaWWAN: // 手機自帶網路
                HMLog(@"手機自帶網路");
                break;
            case AFNetworkReachabilityStatusReachableViaWiFi: // WIFI
                HMLog(@"WIFI");
                break;
        }
    }];
    // 開始監控
    [mgr startMonitoring];

56.NSUserDefault儲存到本地,會預設存成一個plist檔案,所有的操作都儲存到這個plist檔案中

57.登陸頁面判斷是否登陸過

    // 3.設定視窗的根控制器
    HMAccount *account = [HMAccountTool account];
    if (account) {
        [HMControllerTool chooseRootViewController];
    } else { // 沒有登入過
        self.window.rootViewController = [[HMOAuthViewController alloc] init];
    }

+ (void)chooseRootViewController
{
    // 如何知道第一次使用這個版本?比較上次的使用情況
    NSString *versionKey = (__bridge NSString *)kCFBundleVersionKey;
    
    // 從沙盒中取出上次儲存的軟體版本號(取出使用者上次的使用記錄)
    NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
    NSString *lastVersion = [defaults objectForKey:versionKey];
    
    // 獲得當前開啟軟體的版本號
    NSString *currentVersion = [NSBundle mainBundle].infoDictionary[versionKey];
    
    UIWindow *window = [UIApplication sharedApplication].keyWindow;
    if ([currentVersion isEqualToString:lastVersion]) {
        // 當前版本號 == 上次使用的版本:顯示HMTabBarViewController
        [UIApplication sharedApplication].statusBarHidden = NO;
        window.rootViewController = [[HMTabBarViewController alloc] init];
    } else { // 當前版本號 != 上次使用的版本:顯示版本新特性
        window.rootViewController = [[HMNewfeatureViewController alloc] init];
        
        // 儲存這次使用的軟體版本
        [defaults setObject:currentVersion forKey:versionKey];
        [defaults synchronize];
    }
}

58.撤銷形變,前提之前的形變也就是採用的transform

self.showingNavigationController.view.transform = CGAffineTransformIdentity;

59.UITextField與UITextView
UITextField:單行,可以有placeholder
UITextView: 多行,沒有placeholder

60.[self setNeedsLayout];重新佈局控制元件,控制元件初始化的時候呼叫一次,後面如果要改變控制元件,自己手動還要再呼叫一次(Neteasy)

61.tableView重新整理具體某行某個cell

//重新整理某一個section  
NSIndexSet *indexSet=[[NSIndexSet alloc] initWithIndex:2];  
[tableview reloadSections:indexSet 
         withRowAnimation:UITableViewRowAnimationNone];  
//重新整理某一個cell 
NSIndexPath *indexPath=[NSIndexPath indexPathForRow:1 inSection:0];  
[tableView reloadRowsAtIndexPaths:[NSArray arrayWithObjects:indexPath,nil]        
                 withRowAnimation:UITableViewRowAnimationNone];

63.列印不要用NSLog

#if DEBUG
#define LLog(fmt, ...) NSLog((@"%s [Line %d] " fmt), __PRETTY_FUNCTION__, __LINE__, ##__VA_ARGS__);
#else
#define LLog(fmt, ...)
#endif

64.tableView分割線距離

if ([self.tableView respondsToSelector:@selector(setSeparatorInset:)]) {
        [self.tableView setSeparatorInset:UIEdgeInsetsMake(0, 15, 0, 15)];
    };

65.tabelView刪除cell動畫

//自定義cell的代理方法,點選cell上的按鈕
- (void)tableViewDeleteCell:(ContactCell *)cell{
    //通過cell拿到索引
    NSIndexPath *indexPath = [self.tableView indexPathForCell:cell];
    [self.dataArray[indexPath.section] removeObjectAtIndex:indexPath.row];
    //通過組數和行數建立array
    NSArray *array = @[[NSIndexPath indexPathForRow:indexPath.row inSection:indexPath.section]];
    //刪除動畫
    [self.tableView deleteRowsAtIndexPaths:array withRowAnimation:UITableViewRowAnimationFade];
}

66.UIView的半透明優化效能
往每個cell中新增了6個subView,而且每個subView都是半透明(UIView預設是半透明的),這個時候滑動起來明顯就可以感覺到有點顫抖,不是很流暢。當把每一個subView的opaque屬性設定成YES的時候,滑動會比之前流暢一些,不過還是有點兒卡。

67.常量指標,指標常量
常量指標:就是指向常量的指標,關鍵字 const 出現在 * 左邊,表示指標所指向的地址的內容是不可修改的,但指標自身可變。
指標常量:指標自身是一個常量,關鍵字 const 出現在 * 右邊,表示指標自身不可變,但其指向的地址的內容是可以被修改的。

68.UIView與Layer關係
“平行的層級關係
每一個UIview都有一個CALayer例項的圖層屬性,也就是所謂的backing layer,檢視的職責就是建立並管理這個圖層,以確保當子檢視在層級關係中新增或者被移除的時候,他們關聯的圖層也同樣對應在層級關係樹當中有相同的操作”
“CALayer是UIView內部實現細節”

Excerpt From: 鐘聲. “ios核心動畫高階技巧.” iBooks.

69.iOS圖片佔記憶體過大的問題完美解決
func useImage(image: UIImage) -> NSData {
//實現等比例縮放
let hfactor = image.size.width / screnWidth;
let vfactor = image.size.height / screnHeight;
let factor = fmax(hfactor, vfactor);
//畫布大小
let newWith: CGFloat = image.size.width / factor
let newHeigth: CGFloat = image.size.height / factor
let newSize = CGSize(width: newWith, height: newHeigth)

    UIGraphicsBeginImageContext(newSize)  
    image.drawInRect(CGRect(x: 0, y: 0, width: newWith, height: newHeigth))  
    let newImage = UIGraphicsGetImageFromCurrentImageContext()  
    UIGraphicsEndImageContext()  
    //影像壓縮  
    let newImageData = UIImageJPEGRepresentation(newImage, 0.5)  
    return newImageData!  
} 
  1. iOS6 不推薦你將 view 置為 nil 的原因
    iOS6 不推薦你將 view 置為 nil 的原因(連結開啟需要翻牆), 翻譯過來如下:
    UIView 有一個 CALayer 的成員變數,CALayer 是具體用於將自己畫到螢幕上的。如下圖所示:

CALayer 是一個 bitmap 圖象的容器類,當 UIView 呼叫自身的 drawRect 時,CALayer 才會建立這個 bitmap 圖象類。
具體佔記憶體的其實是一個 bitmap 圖象類,CALayer 只佔 48bytes, UIView 只佔 96bytes。而一個 iPad 的全屏 UIView 的 bitmap 類會佔到 12M 的大小!
在 iOS6 時,當系統發出 MemoryWarning 時,系統會自動回收 bitmap 類。但是不回收 UIView 和 CALayer 類。這樣即回收了大部分記憶體,又能在需要 bitmap 類時,通過呼叫 UIView 的 drawRect: 方法重建。
63.自定義了leftBarbuttonItem左滑返回手勢失效了怎麼辦?

self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc]  
              initWithImage:img  
              style:UIBarButtonItemStylePlain  
              target:self  
              action:@selector(onBack:)];  
self.navigationController.interactivePopGestureRecognizer.delegate = (id<UI

64.怎麼像Safari一樣滑動的時候隱藏navigationbar?

navigationController.hidesBarsOnSwipe = Yes

65.多用型別常量,少用#define預處理

如果只在本類使用的常量,使用static const關鍵字來定義常量。

如果多個類都需使用到某一常量,則需將常量定義成公開的,具體方式是在類的宣告檔案中使用extern const關鍵字宣告常量,在類的實現檔案中使用const關鍵字定義常量,這樣任何類只要匯入了宣告常量的標頭檔案就可以直接使用定義好的常量了。

在.h檔案中宣告

extern NSString *const XFExternalConst;
在.m檔案中描述

NSString *const XFExternalConst = @"ko";
為避免衝突,一般都用類名做字首。

50.禁止橫屏方法

- (NSUInteger)application:(UIApplication *)application supportedInterfaceOrientationsForWindow:(UIWindow *)window  
{  
    return UIInterfaceOrientationMaskPortrait;  
}

49.一行程式碼解決改變展點陣圖文字顏色程式碼

[_userName setValue:[UIColor whiteColor] forKeyPath:@"_placeholderLabel.textColor"];

48.修改狀態列顏色

iOS7預設狀態列文字顏色為黑色,專案需要修改為白色。
1在Info.plist中設定UIViewControllerBasedStatusBarAppearance 為NO
2 在需要改變狀態列顏色的 AppDelegate中在 didFinishLaunchingWithOptions 方法中增加:
[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
如果需要在單個ViewController中新增,在ViewDidLoad方法中增加:
[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];

47.判斷程式是否第一次啟動

if(![[NSUserDefaults standardUserDefaults] boolForKey:@"firstLaunch"]){
    [[NSUserDefaults standardUserDefaults] setBool:YES forKey:@"firstLaunch"];
    NSLog(@"第一次啟動");
    [[NSUserDefaults standardUserDefaults] setBool:NO forKey:@"isLogin"];

}else{
    NSLog(@"已經不是第一次啟動了");
}

46.iPhone尺寸規格

iPhone尺寸規格.png
45.模糊效果

// 模糊效果
//    UIBlurEffect *effect = [UIBlurEffect effectWithStyle:UIBlurEffectStyleLight];
//    UIVisualEffectView *test = [[UIVisualEffectView alloc] initWithEffect:effect];
//    test.frame = self.view.bounds;
//    test.alpha = 0.5;
//    [self.view addSubview:test];

43.新增每個cell出現時的3D動畫

-(void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath{

    // 動畫1
    //    CATransform3D rotation;//3D旋轉
    //    rotation = CATransform3DMakeRotation( (90.0*M_PI)/180, 0.0, 0.7, 0.4);
    //    //逆時針旋轉
    //    rotation.m34 = 1.0/ -600;
    //
    //    cell.layer.shadowColor = [[UIColor blackColor]CGColor];
    //    cell.layer.shadowOffset = CGSizeMake(10, 10);
    //    cell.alpha = 0;
    //
    //    cell.layer.transform = rotation;
    //
    //    [UIView beginAnimations:@"rotation" context:NULL];
    //    //旋轉時間
    //    [UIView setAnimationDuration:0.8];
    //    cell.layer.transform = CATransform3DIdentity;
    //    cell.alpha = 1;
    //    cell.layer.shadowOffset = CGSizeMake(0, 0);
    //    [UIView commitAnimations];

    // 動畫2
    cell.alpha = 0.5;

    CGAffineTransform transformScale = CGAffineTransformMakeScale(0.3,0.8);
    CGAffineTransform transformTranslate = CGAffineTransformMakeTranslation(0.5, 0.6);

    cell.transform = CGAffineTransformConcat(transformScale, transformTranslate);

    [tableView bringSubviewToFront:cell];
    [UIView animateWithDuration:.4f
                          delay:0
                        options:UIViewAnimationOptionAllowUserInteraction
                     animations:^{

                         cell.alpha = 1;
                         //清空 transform
                         cell.transform = CGAffineTransformIdentity;

                     } completion:nil];

    // 動畫3
    /*
     // 從錨點位置出發,逆時針繞 Y 和 Z 座標軸旋轉90度
     CATransform3D transform3D = CATransform3DMakeRotation(M_PI_2, 0.0, 1.0, 1.0);

     // 定義 cell 的初始狀態
     cell.alpha = 0.0;
     cell.layer.transform = transform3D;
     cell.layer.anchorPoint = CGPointMake(0.0, 0.5); // 設定錨點位置;預設為中心點(0.5, 0.5)

     // 定義 cell 的最終狀態,執行動畫效果
     // 方式一:普通操作設定動畫
     [UIView beginAnimations:@"transform" context:NULL];
     [UIView setAnimationDuration:0.5];
     cell.alpha = 1.0;
     cell.layer.transform = CATransform3DIdentity;
     CGRect rect = cell.frame;
     rect.origin.x = 0.0;
     cell.frame = rect;
     [UIView commitAnimations];

     // 方式二:程式碼塊設定動畫
     //        [UIView animateWithDuration:0.5 animations:^{
     //                cell.alpha = 1.0;
     //                 cell.layer.transform = CATransform3DIdentity;
     //                CGRect rect = cell.frame;
     //                 rect.origin.x = 0.0;
     //            cell.frame = rect;
     //             }];

     */
}

42.強制橫屏程式碼

#pragma mark - 強制橫屏程式碼
- (BOOL)shouldAutorotate
{
    //是否支援轉屏
    return NO;
}

- (UIInterfaceOrientationMask)supportedInterfaceOrientations
{
    //支援哪些轉屏方向
    return UIInterfaceOrientationMaskLandscape;
}

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
    return UIInterfaceOrientationLandscapeRight;
}

- (BOOL)prefersStatusBarHidden
{
    return NO;
}

41.將window上的顯示在最外層

[[[[UIApplication sharedApplication] delegate] window] addSubview:topImgView];

40.監測網路狀態

只要網路狀態發生了變化,在任何一個檢視控制器都會給出相應的提示
說明: 這裡需要匯入第三方庫,1. MBProgressHUD 2. AFNetworking
匯入標頭檔案 MBProgressHUD.h, AFNetworking.h

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    // 應用程式載入完成

    UIWindow *window = ((AppDelegate *) [UIApplication sharedApplication].delegate).window;

    AFNetworkReachabilityManager *manager = [AFNetworkReachabilityManager sharedManager];
    [manager setReachabilityStatusChangeBlock:^(AFNetworkReachabilityStatus status) {
        // 使用MBProgressHUD三方庫建立彈框,給出相應的提示
        MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:window animated:YES];
        hud.mode = MBProgressHUDModeText;
        switch (status) {
            case AFNetworkReachabilityStatusNotReachable:
                // 彈框提示的內容
                hud.labelText = @"世界上最遙遠的距離就是沒網";
                break;
            case AFNetworkReachabilityStatusReachableViaWWAN:
                hud.labelText = @"2G/3G/4G";
                break;
            case AFNetworkReachabilityStatusReachableViaWiFi:
                hud.labelText = @"WiFi線上";
            default:
                break;
        }
        dispatch_async(dispatch_get_global_queue(0, 0), ^{
            // 顯示時間2s
            sleep(2);
            dispatch_async(dispatch_get_main_queue(), ^{
                // 讓彈框消失
                [MBProgressHUD hideHUDForView:window animated:YES];
            });
        });
    }];
    [manager startMonitoring];

    return YES;
}

39.在狀態列顯示有網路請求的提示器

//- (void)webViewDidStartLoad:(UIWebView *)webView {
//    [UIApplication sharedApplication].networkActivityIndicatorVisible = YES;
//}
//- (void)webViewDidFishLoad:(UIWebView *)webView {
//    [UIApplication sharedApplication].networkActivityIndicatorVisible = NO;
//}
//接收響應
// 在狀態列顯示有網路請求的提示器
//- (void)connection:(NSURLConnection*)connection didReceiveResponse:(NSURLResponse*)response{
//    
//    //網路活動指示器
//    
//    [UIApplication sharedApplication].networkActivityIndicatorVisible=YES;
//    
//}

//隱藏狀態列

//- (BOOL)prefersStatusBarHidden
//
//{
//    
//    return YES;
//    
//}

38.模糊效果

    // 模糊效果
    UIBlurEffect *effect = [UIBlurEffect effectWithStyle:UIBlurEffectStyleLight];
    UIVisualEffectView *test = [[UIVisualEffectView alloc] initWithEffect:effect];
    test.frame = self.view.bounds;
    test.alpha = 0.5;
    [self.view addSubview:test];

35.相對路徑

$(SRCROOT)/
34.在storyboard上新增ScrollView

32.返回cell高度

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
    NSString *string = self.lrcArr[indexPath.row];

    CGRect frame = [string boundingRectWithSize:CGSizeMake([UIScreen mainScreen].bounds.size.width, 10000) options:(NSStringDrawingUsesLineFragmentOrigin) attributes:[NSDictionary dictionaryWithObject:[UIFont systemFontOfSize:17] forKey:NSFontAttributeName] context:nil];

    return frame.size.height;
}
  1. UIImageView
NSArray *animationImages; // 把圖片賦值給動畫陣列【幀動畫】
NSInteger animationRepeatCount; // 預設是0,無限迴圈
NSTimeInterval animationDuration; // 執行一輪圖片的時間

26.檢視是否自動(只是把第一個自動)向下挪64

self.automaticallyAdjustsScrollViewInsets = NO; // 不讓系統幫我們們把scrollView及其子類的檢視向下調整64

25.問題處理:有時候self是加在parentViewController(父ViewController)上的,self上面是沒有navigationController的,但是這時還想使用self父類的navigationController,那麼,此時需要第二種方法push過去

[self.navigationController pushViewController:detailViewController animated:YES];
[self.parentViewController.navigationController pushViewController:detailViewController animated:YES];

24.問題處理:cell是有重用機制的,但有時候,我們的cell是自適應高度,但是所有cell的標識都是一個,那麼,在重用的時候會出現 有的單元格高,有的單元格矮的情況,和本身想要的frame不匹配,這個時候,只需要給cell上面的檢視在懶載入的時候,重新賦frame值就好了。也就是在if判斷外,再賦值一次frame。(例如,豆瓣專案電影院列表)

  1. 容器檢視控制器

把一個檢視控制器作為容器檢視控制器,在這個容器檢視控制器上新增多個其他檢視控制器,並把其他控制器的檢視新增上來

TableViewController *tableViewController = [[TableViewController alloc] init];
[self addChildViewController:tableViewController]; // self在這裡就是容器檢視控制器
[self.view addSubView:tableViewController.tableView];

使用場景:當我們某個檢視控制器要使用多個子介面,並且多個子介面的處理事務的邏輯比較複雜,我們就可以通過這種方式將不同的邏輯處理拆分開,在各自的檢視控制器中處理自己的邏輯,而不是所有邏輯都在當前檢視控制器中處理。

.22. 程式的退出【瞭解】

【特別注意】iOS的應用程式在應用程式內部是不允許被退出的,只能通過連擊兩次HOME鍵的時候進入程式管理介面 通過上滑退出。如果在應用程式中寫了下面的程式碼,那麼在提交程式的時候是不能被稽核通過的。所以下面的程式碼是不允許寫的。在這裡只是作了解。
exit(0); // 只要執行這個語句,程式就會直接退出

.21. 隱藏手機的狀態列

-(BOOL)prefersStatusBarHidden {
    return YES;
}

.20. 代理的安全保護【斷是否有代理,和代理是否執行了代理方法】

if (self.delegate && [self.delegate respondsToSelector:@selector(passValueWithArray:)]) {
}

19.按照文字計算高度

- (void)descHeightWithDesc:(NSString *)desc{

    CGRect rect = [desc boundingRectWithSize:CGSizeMake(240, MAXFLOAT) options:NSStringDrawingUsesLineFragmentOrigin|NSStringDrawingUsesFontLeading attributes:@{NSFontAttributeName:self.descLabel.font} context:nil];
    //按照文字計算高度
    float textHeight = rect.size.height;

    CGRect frame = self.descLabel.frame;
    frame.size.height = textHeight;
    self.descLabel.frame = frame;
}

18.網路請求圖片

//    NSURL *url = [NSURL URLWithString:urlString];
//    NSURLRequest *request = [NSURLRequest requestWithURL:url];
//    NSData *data = [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
//    UIImage *image = [UIImage imageWithData:data];
//此種寫法和上面的操作是一致的,都是同步請求資料。
UIImage *image = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:urlString]]];
return image;

17.substringWithRange: 專門擷取字串的一塊肉

NSMakeRange(4,2) 從第4個字元開始擷取,長度為2個字元,(字串都是從第0個字元開始數的哦~!)

        self.begin_time = dic[@"begin_time"];
        self.end_time = dic[@"end_time"];
        NSRange range = NSMakeRange(5, 11);

        self.time = [[self.begin_time substringWithRange:range] stringByAppendingString:[@" -- "stringByAppendingString:[self.end_time substringWithRange:range]]];

13.UITextField的字數限制

// viewDidLoad中
[[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(textFiledEditChanged:) 
          name:@"UITextFieldTextDidChangeNotification" object:myTextField];
-(void)textFiledEditChanged:(NSNotification *)obj
{
    UITextField *textField = (UITextField *)obj.object;
    NSString *toBeString = textField.text;

    //獲取高亮部分
    UITextRange *selectedRange = [textField markedTextRange];
    UITextPosition *position = [textField positionFromPosition:selectedRange.start offset:0];

    // 沒有高亮選擇的字,則對已輸入的文字進行字數統計和限制
    if (!position)
    {
        if (toBeString.length > MAX_STARWORDS_LENGTH)
        {
            NSRange rangeIndex = [toBeString rangeOfComposedCharacterSequenceAtIndex:MAX_STARWORDS_LENGTH];
            if (rangeIndex.length == 1)
            {
                textField.text = [toBeString substringToIndex:MAX_STARWORDS_LENGTH];
            }
            else
            {
                NSRange rangeRange = [toBeString rangeOfComposedCharacterSequencesForRange:NSMakeRange(0, MAX_STARWORDS_LENGTH)];
                textField.text = [toBeString substringWithRange:rangeRange];
            }
        }
    }
 }

12.處理標籤字串中的空格,換行,/t(製表符)等

- (NSString *)replaceStringWithString :(NSMutableString *)string
{
    NSString *string1 = [string stringByReplacingOccurrencesOfString:@"\n" withString:@""] ;
    NSString *string2 = [string1 stringByReplacingOccurrencesOfString:@" " withString:@""] ;
    NSString *string3 = [string2 stringByReplacingOccurrencesOfString:@"\r" withString:@""] ;
    NSString *string4 = [string3 stringByReplacingOccurrencesOfString:@"\t" withString:@""] ;
    return string4 ;
}

11.通過2D仿射函式實現小的動畫效果(變大縮小) --可用於自定義pageControl中.

   [UIView animateWithDuration:0.3 animations:^{
   imageView.transform = CGAffineTransformMakeScale(2, 2);
   } completion:^(BOOL finished) {
   imageView.transform = CGAffineTransformMakeScale(1.0, 1.0);
   }];

10.當有多個導航控制器時,一次設定多個導航控制器

   UINavigationBar *navBar = [UINavigationBar appearance] ;
    // 所有導航條顏色都會改變 -- 一鍵設定
    //navBar.barTintColor = [UIColor yellowColor] ;
    [navBar setBackgroundImage:[UIImage imageNamed:@"bg_nav.png"] forBarMetrics:UIBarMetricsDefault] ;

9.UIImage與字串互轉

//圖片轉字串  
-(NSString *)UIImageToBase64Str:(UIImage *) image  
{  
    NSData *data = UIImageJPEGRepresentation(image, 1.0f);  
    NSString *encodedImageStr = [data base64EncodedStringWithOptions:NSDataBase64Encoding64CharacterLineLength];  
    return encodedImageStr;  
}

//字串轉圖片  
-(UIImage *)Base64StrToUIImage:(NSString *)_encodedImageStr  
{  
    NSData *_decodedImageData   = [[NSData alloc] initWithBase64Encoding:_encodedImageStr];  
    UIImage *_decodedImage      = [UIImage imageWithData:_decodedImageData];  
    return _decodedImage;  
}

8.UITableViewCell可移動,需要開啟的代理方法以及移動過程中呼叫的代理方法

// tableView可移動  移動完成之後會呼叫此代理方法
- (void)tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)sourceIndexPath toIndexPath:(NSIndexPath *)destinationIndexPath
{

}

// 移動過程中呼叫的代理方法 -- 示例為不能跨區移動
/**
 *  <#Description#>
 *
 *  @param tableView
 *  @param sourceIndexPath              所要移動單元格的原始位置
 *  @param proposedDestinationIndexPath 將要移動到的位置
 *
 *  @return return value description
 */
- (NSIndexPath *)tableView:(UITableView *)tableView targetIndexPathForMoveFromRowAtIndexPath:(NSIndexPath *)sourceIndexPath toProposedIndexPath:(NSIndexPath *)proposedDestinationIndexPath
{
    // 移動位置在同一分割槽
    if (sourceIndexPath.section == proposedDestinationIndexPath.section)
    {
        // 這時允許單元格移動
        return proposedDestinationIndexPath ;
    }
    // 不在同一分割槽 不讓單元格移動,返回原始的indexPath
    else
    {
        return sourceIndexPath ;
    }
}

8.隱藏狀態列 修改狀態列風格

-(UIStatusBarStyle)preferredStatusBarStyle 
{ 
    return UIStatusBarStyleLightContent;  // 暗背景色時使用
} 

- (BOOL)prefersStatusBarHidden 
{ 
    return YES; // 是否隱藏狀態列
}

6.取消圖片的渲染

[button setImage:[[UIImage imageNamed:@"1.jpg" ] imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal]  forState:UIControlStateNormal] ;
  1. NSNumber

a.是數字的NS物件的表達形式,如果要把數字新增到陣列或者字典中,必須要進行轉換,同時要使用陣列中的數字,還需要轉換成對應的數字。
b.要轉換數字可以使用OC提供的包裝方法:@(int)
c.要把NSNumber轉換成字串,需要使用stringValue方法

  1. NSTimer計時器

使用例項程式碼如下:
// 第一個引數:多長時間會觸發一次,以秒為單位
// 第二個引數:如果看到函式的引數有target,一般情況下,都用self
// 第三個引數:SEL,需要呼叫其他的方法,就是每次時鐘被觸發的時候,去執行的方法
// 最多可以帶一個引數,就是時鐘本身
// 第四個引數,暫時不用考慮,設定成nil
// 第五個引數:是否重複,通常會設定YES

_gameTimer = [NSTimer scheduledTimerWithTimeInterval:1.0f target:self selector:@selector(updateTimer:) userInfo:nil repeats:YES];

a.在時鐘觸發方法中,可以使用sender.fireDate獲取到時鐘被觸發的時間
b.注意:使用NSTimer的時候,千萬不要忘記呼叫invalidate方法關閉時鐘。
c.NSTimer可能不會是及時相應觸發時間的,它的執行優先順序相對較低,因此,不要使用NSTimer去做實時響應需求較高的週期性操作。

2.根據UILabel裡的內容自適應高度

NSString *contentString = [dic objectForKey:@"content"] ; //從字典中提取字串
CGRect rect = [contentString boundingRectWithSize:CGSizeMake(tableView.bounds.size.width, MAXFLOAT) options:NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingUsesFontLeading attributes:@{NSFontAttributeName :[UIFont systemFontOfSize:15]} context:nil] ;
    // 內容的自適應高度方法
     *  @param CGSize 規定文字顯示的最大範圍
        @param options 按照何種設定來計算範圍
        @param attributes 文字內容的一些屬性,例如字型大小,字型型別等  (字型不一樣,高度也不一樣)
        @parma context 上下文 可以規定一些其他的設定 但是一般都是nil
     */    
    // 列舉值中的 " | "  意思是要滿足所有的列舉值設定.

1.根據漢字字串獲取該字串的拼音然後取得首字母

分享資源    漢字轉換為 拼音 獲取首字母
//獲取拼音首字母(傳入漢字字串, 返回大寫拼音首字母)
/*
- (NSString *)firstCharactor:(NSString *)aString
{
    //轉成了可變字串
    NSMutableString *str = [NSMutableString stringWithString:aString];
    //先轉換為帶聲調的拼音
    CFStringTransform((CFMutableStringRef)str,NULL, kCFStringTransformMandarinLatin,NO);
    //再轉換為不帶聲調的拼音
    CFStringTransform((CFMutableStringRef)str,NULL, kCFStringTransformStripDiacritics,NO);
    //轉化為大寫拼音
    NSString *pinYin = [str capitalizedString];
    //獲取並返回首字母
    return [pinYin substringToIndex:1];
}
*/
        NSString *string = @"簡書" ;
        if ([string length])
        {
            NSMutableString *mutableString = [NSMutableString stringWithString:string] ;
            /**
             *  由於此方法是在coreFoundation框架下,我們們平時所使用的型別都是Foundation框架下的,所以需要轉換型別.
             *
             *  @param string#>    string 所需要轉換的原字元#>
             *  @param range#>     range 所需要轉換字元的範圍.如果為0或者是NULL意思是所有字元都轉換#>
             *  @param transform#> transform 轉換方式#>
             *  @param reverse#>   reverse 如果為YES,返回原字串;如果為NO,返回轉換之後的字串#>
             *
             *  @return return value description
             */
            // 將所有非英文的字元轉換為拉丁字母,並且帶聲調和重音標識
            // __bridge :只改變當前物件的型別,但是不改變物件記憶體的管理許可權
            CFStringTransform((__bridge CFMutableStringRef)mutableString , 0,kCFStringTransformToLatin , NO) ;

            // 去掉聲調
            CFStringTransform((__bridge CFMutableStringRef)mutableString , 0,kCFStringTransformStripDiacritics , NO) ;

            // 每個單詞的首字母大寫 後再擷取字串
            NSString *str = [[mutableString capitalizedString] substringToIndex:1];
        }

100.afnetworking上傳圖片

[manager POST:url parameters:param constructingBodyWithBlock:^(id<AFMultipartFormData>  _Nonnull formData) {

        for (int i = 0; i < data_arr.count; i++) {

            //拿當前時間拼接字串做檔名

            NSDateFormatter *formatter = [[NSDateFormatter alloc] init];

            [formatter setTimeZone:[NSTimeZone systemTimeZone]];

            [formatter setDateFormat:@"yyyyMMddHHmmss"];

            NSString* dateString = [formatter stringFromDate:[NSDate date]];

            dateString = [NSString stringWithFormat:@"%@_%du.png",dateString,(int)data_arr.count + 1];

            // data 轉檔案流

            NSData* data = [[data_arr objectAtIndex:i] objectForKey:@"picData"];

            //            data = [data_arr objectAtIndex:i];

            //            NSString  *path = NSHomeDirectory();

            //            DEF_DEBUG(@"path:%@",path);

            //            NSArray* paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask,YES);

            //            NSString* documentsDirectory = [paths objectAtIndex:0];

            //            NSString* fullPathToFile = [documentsDirectory stringByAppendingPathComponent:dateString];

            //寫入檔案

            //[data writeToFile:fullPathToFile atomically:NO];

            //            NSString* name = [NSString stringWithFormat:@"file_%d",i + 1];

            

            [formData appendPartWithFileData:data name:@"contract_photo_list[]" fileName:dateString mimeType:@"image/png"];

        }

    } progress:^(NSProgress * _Nonnull uploadProgress) {

101.強弱引用

/**
 Synthsize a weak or strong reference.
 Example:
    @weakify(self)
    [self doSomething^{
        @strongify(self)
        if (!self) return;
        ...
    }];
 */

#ifndef weakify
    #if DEBUG
        #if __has_feature(objc_arc)
        #define weakify(object) autoreleasepool{} __weak __typeof__(object) weak##_##object = object;
        #else
        #define weakify(object) autoreleasepool{} __block __typeof__(object) block##_##object = object;
        #endif
    #else
        #if __has_feature(objc_arc)
        #define weakify(object) try{} @finally{} {} __weak __typeof__(object) weak##_##object = object;
        #else
        #define weakify(object) try{} @finally{} {} __block __typeof__(object) block##_##object = object;
        #endif
    #endif
#endif

#ifndef strongify
    #if DEBUG
        #if __has_feature(objc_arc)
        #define strongify(object) autoreleasepool{} __typeof__(object) object = weak##_##object;
        #else
        #define strongify(object) autoreleasepool{} __typeof__(object) object = block##_##object;
        #endif
    #else
        #if __has_feature(objc_arc)
        #define strongify(object) try{} @finally{} __typeof__(object) object = weak##_##object;
        #else
        #define strongify(object) try{} @finally{} __typeof__(object) object = block##_##object;
        #endif
    #endif
#endif

102.關於屬性非空的判斷
我們通常用nonnull來限定屬性的非空狀態:

@property (strong, nonatomic, nonnull) NSString *str;

然而很多個屬性的情況下,每次都寫比較坑爹,所以可以用蘋果給我們準備好的巨集:

NS_ASSUME_NONNULL_BEGIN
@property (strong, nonatomic) NSString *str1;
@property (strong, nonatomic) NSString *str2;
@property (strong, nonatomic, nullable) NSString *str3;
NS_ASSUME_NONNULL_END

其中nullable設定該引數可以賦值為空

103.UUID

+ (NSString *)UUID {
    //MARK:此處的 @"5CKSJSE23P.com.haodf.mainGroup" 字串不能動,否則會導致獲取的值錯誤或者 nil
    KeychainItemWrapper *wrapper = [[KeychainItemWrapper alloc] initWithIdentifier:@"HuangyibiaoAppID" accessGroup:@"com.huangyibiao.test.group"];
    NSString *UUID = [wrapper objectForKey:(__bridge id)kSecValueData];
    
    if (UUID.length == 0) {
      UUID = [[[UIDevice currentDevice] identifierForVendor] UUIDString];
      [wrapper setObject:UUID forKey:(__bridge id)kSecValueData];
    }
  
  return UUID;
}

104、消除tableView組之間的細線

 UIView * headview =[[UIViewalloc]initWithFrame:CGRectMake(0, 0, 0, CGFLOAT_MIN)];
    tableView.tableHeaderView = headview;

self.tableView.contentInset = UIEdgeInsetsMake(0.0f, 0.0f, 0.0f, 0.0f);

- (CGFloat) tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
{
    return 0.0f;
}

UIView * headview =[[UIView alloc]initWithFrame:CGRectMake(0, 0, 0, CGFLOAT_MIN)];
    _tableview.tableHeaderView = headview;

1000、UIScrollView 滾動收起鍵盤
keyboardDismissMode設定為:UIScrollViewKeyboardDismissModeOnDrag

1001、導航欄設定(透明)

//全透明,一般在viewWillAppear
+ (void)createCompletelyTransparentNavigationBar:(UIViewController *)sender
{
    [sender.navigationController.navigationBar setBackgroundImage:[UIImage new]
                                                  forBarMetrics:UIBarMetricsDefault];
    sender.navigationController.navigationBar.shadowImage = [UIImage new];
    sender.navigationController.navigationBar.translucent = YES;
    sender.navigationController.view.backgroundColor = [UIColor clearColor];
    sender.navigationController.navigationBar.backgroundColor = [UIColor clearColor];
}

//恢復成預設,一般在viewWillDisappear
+ (void)createDefaultNavigationBar:(UIViewController *)sender
{
    [sender.navigationController.navigationBar setBackgroundImage:nil
                                                  forBarMetrics:UIBarMetricsDefault];
}
#pragma mark - 
#pragma mark - 自定義導航欄按鈕 返回按鈕 或者其他按鈕
- (void)createCustomNavigationBackOrOtherButton
{
    UIButton *backBtn = [UIButton buttonWithType:UIButtonTypeCustom];
    backBtn.frame = CGRectMake(0, 0, 32, 32);
    [backBtn addTarget:self action:@selector(navCustomBackButtonPressed) forControlEvents:UIControlEventTouchUpInside];
    [backBtn setImage:[UIImage imageNamed:@"NavBackCustomImg"] forState:UIControlStateNormal];
    self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:backBtn];
   // self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithImage:[UIImage imageNamed:@"NavBackCustomImg"] style:UIBarButtonItemStyleBordered target:self action:@selector(navCustomBackButtonPressed)];
    //解決自定義了leftBarbuttonItem左滑返回手勢失效了的問題
    self.navigationController.interactivePopGestureRecognizer.delegate = (id<UIGestureRecognizerDelegate>)self;
}

- (void)navCustomBackButtonPressed
{
    [self.navigationController popViewControllerAnimated:YES];
}

相關文章