iOS10 適配、Xcode8配置總結②

Xcode8 新特性html

Interface Builderios

隨着14年的iPhone6和6P出來以後,iPhone的屏幕尺寸也愈來愈多,屏幕適配是一個須要解決的問題,之後不必定蘋果又出什麼尺寸的iPhone呢。api

在iPhone6和6P發佈的同一年,蘋果推出的Xcode6中在原有的Auto layout的基礎上,添加了Size Classes新特性,經過這個新特性可使用一個XIB或者SB文件,適配不一樣的屏幕以及iPhone和iPad兩種設備。數組

在Xcode8中,蘋果推出了更增強大的可視化編輯工具預覽功能,能夠在不運行App的狀況下,預覽當前XIB或SB在不一樣屏幕尺寸下的顯示。(這個功能我記得以前Xcode就有,只是隱藏的比較深,蘋果如今給拿到外面了)app

選擇一個XIB文件進去,點擊下面紅框的位置,會出現從3.5寸-5.5寸一系列屏幕尺寸的選項。直接點擊不一樣屏幕尺寸,以及橫豎屏選項,切換不一樣的屏幕顯示。在iPad上還能夠選擇是否分屏,功能很是強大。框架

21.png

Interface Builder異步

在右邊有一個Vary for Traits選項,點擊這個選項就能夠同時顯示全部可選的屏幕樣式,功能和上面圖片都同樣,只是顯示上看起來比較多。函數

22.png

Interface Builder工具

還有一點,新建立的XIB控件尺寸,再也不是以前600*600的方塊了,而是默認是6s的長方形XIB文件,看起來舒服多了。字體

Target中General的變化

在Xcode8以前,都須要本身設置證書和描述文件。若是設置出現錯誤的狀況下,還能夠經過點擊Fix issue來修復這個錯誤。但這有個問題就在於,Fix issue選項並非那麼好用,有的時候設置是正確的這裏也提示須要Fix issue。

可能蘋果也意識到這個問題的存在,在Xcode8中能夠經過Automatically manage signing選項,讓蘋果爲咱們管理證書和配置文件,設置也都是由蘋果來完成的。在Xcode8中新建項目,這個選項默認是被勾選的。

23.png

Automatically manage signing

從上面圖中能夠看到,蘋果幫咱們自動管理了證書和配置文件。並且在以前的項目中,若是想要設置安裝後顯示在手機上的App名字,還須要本身到Info.plist文件中,修改Display Name字段,而如今直接在General中就能夠作修改,這個修改和Info.plist是同步的。

可是,若是我想本身管理證書和描述文件呢?只須要去掉Automatically manage signing選項。

24.png

Automatically manage signing

若是本身到Build Settings中手動設置證書和描述文件,能夠發現Provisioning Profile選項已經被標明爲Deprecated,也就是蘋果並不推薦手動設置。

Xcode插件

升級Xcode8以後會發現,在Xcode8中全部第三方插件都失效了,而且連以前菜單欄的插件選項也不存在了。在以前不少iOS開發者,都是經過Alcatraz來管理插件的,如今Alcatraz也是不可用的。可是Xcode8自身也對編譯器進行了升級,將一些比較好的插件功能加入到Xcode中,例如單行高亮顯示等。

在Xcode8中支持了開發插件工程,而且爲咱們提供了一個插件模板,開發的插件能夠上傳到App Store下載。蘋果這麼作有一個緣由在於,以前Xcode和插件是運行在同一個進程的,因此插件的崩潰也會致使Xcode崩潰。蘋果如今將插件做爲一個單獨的應用程序,分開進程運行,不會對Xcode帶來其餘影響。

25.png

Xcode Source Editor Extension

Runtime Issues

在開發過程當中,由於語法或明顯的代碼錯誤(例如Retain Cycle),編譯器能夠發現並報黃色或紅色警告。可是一些由於代碼邏輯致使的錯誤,編譯器並無辦法找到。例以下面的這句代碼,由於代碼邏輯的問題致使兩個數組相互引用,都不能釋放。

26.png

數組循環引用

這時候能夠經過Xcode8提供的Runtime Issues新特性,查找到運行過程當中出現的問題,並經過Graph的方式將問題可視化的展示給開發者。

27.png

Runtime Issues

Debug Memory Graph

在Xcode6中出現了Debug View Hierarchy新特性,能夠經過其調試當前App的視圖層級,查找UI相關的bug很是方便。在Xcode8中蘋果爲開發者提供了Debug Memory Graph特性,經過這個新特性,能夠直接選擇一個對象,查看與其相關的內存關係。

28.png

Debug Memory Graph

Debug Memory Graph和Runtime Issues能夠配合使用,經過Debug Memory Graph分析內存關係完成後,點擊Runtime Issues能夠看到已經發現的內存問題。

Swift 3

Xcode8帶來了新版本的Swift3,新版本的Swift變化較大,若是舊版的Swift項目在Xcode8上編譯可能會失敗。對此,蘋果爲開發者提供了Swift遷移工具,據說不太好用(我沒用過這個工具)。

若是不想馬上就遷移到Swift3,能夠在Builder Settings中進行設置,選擇Use Legacy Swift Language Version設置爲YES,就能夠繼續使用舊版本的Swift2.3。

29.png

Use Legacy Swift Language Version

其餘更新

  1. Xcode新版字體,SF Mono Regular字體。更新Xcode以後我比較喜歡這種字體,看起來代碼很是工整。

  2. 被編輯的行高亮顯示。以前Xcode有個插件就是這個功能,Xcode8把高亮功能集成進來了,使用起來很方便。

  3. 最新版的API文檔,展現樣式發生了很大的改變。

  4. 更方便的生成文檔(就是喵神寫的VVDocumenter),在Xcode8中能夠將光標放在方法上面,經過option + command + /快捷鍵生成文檔註釋。

Xcode 8適配

XIB和Storeboard適配

在Xcode8以前,建立一個XIB或SB文件,都是一個600*600的方塊XIB文件。在Xcode8以後,建立的XIB文件默認是6s尺寸的大小。

可是Xcode8打開以前舊項目的XIB或SB文件時,會彈出下面的彈框, 這時候通常直接選擇Choose Device便可。

30.png

Choose an initial device view

可是這樣有個問題,若是Xcode8打開過這個XIB文件,並選擇Choose Device以後。其餘的Xcode8如下版本的編譯器,將沒法再打開這個文件,會報如下錯誤:

The document 「ViewController.xib」 requires Xcode 8.0 or later. This version does not support documents saved in the Xcode 8 format. Open this document with Xcode 8.0 or later.

有兩種方法解決這個問題:

  1. 你同事也升級Xcode8,比較推薦這種方式,應該迎接改變。

  2. 右擊XIB或SB文件 -> Open as -> Source Code,刪除xml文件中下面一行字段。

31.png

編譯錯誤

升級Xcode以後,Xcode8對以前的一些修飾符和語句不兼容,會致使一些編譯錯誤。這種錯誤致使的緣由不少,這裏大體列幾條,各位仍是根據自身遇到的狀況作修改吧。

  1. 以前一些泛型相關的修飾符,nullable之類的有的會報錯。

  2. CAAnimation及其子類,設置代理屬性後,必須在@interface()遵照代理,不然報錯,等等。

權限適配

這應該算iOS10系統適配的範疇,最近這兩個都在弄,因此就直接和Xcode8適配一塊兒寫出來了。

在iOS10以後須要在Info.plist中,添加新的字段獲取權限,不然在iOS10上運行會致使崩潰。下面是一些經常使用的字段,若是有缺乏的麻煩各位評論區補充一下。

222.png

參考資料:developer.apple

推送通知

蘋果的推送在以前iOS8和iOS9的時候就發生過大的更新,推送功能愈來愈強大。在iOS10以後蘋果推出了UserNotifications框架,能夠經過這個框架更好的控制推送通知,能夠更新、修改鎖屏頁面的推送消息,能夠添加圖片等功能。

可是在用Xcode8打包後,而且不對代碼進行修改的狀況下,會發現打包後蘋果發來了一封郵件。這封郵件大概意思是若是須要使用推送通知,須要對代碼作修改,不然將不能使用推送通知。

33.png

Push Notifications

這是由於在Xcode8以後,若是須要使用Push Notifications的功能,須要勾選Capabilities -> Push Notifications爲YES,不然進行遠程推送就會有問題,而且會收到蘋果發來的這封郵件。

刪除系統log

升級Xcode8以後,在調試和運行過程當中,發現控制檯打印了不少不認識的log,這些log是系統打印的,和開發者不要緊。可是這麼多log看着比較亂,怎麼屏蔽掉呢?

subsystem: com.apple.UIKit, category: HIDEventFiltered, enable_level: 0, persist_level: 0, default_ttl: 0, info_ttl: 0, debug_ttl: 0, generate_symptoms: 0, enable_oversize: 1, privacy_setting: 2, enable_private_data: 0

在Target -> Edit Scheme -> Run -> Arguments中,添加OS_ACTIVITY_MODE字段,並設置爲Disable便可。

35.png

OS_ACTIVITY_MODE

順便提一下,這兩天在設置log選項的時候,發現能夠經過在Arguments中設置參數,打印出App加載的時長,包括總體加載時長,動態庫加載時長等。

在Environment Variables中添加DYLD_PRINT_STATISTICS字段,並設置爲YES,在控制檯就會打印加載時長。

38.png

控制檯打印信息

awakeFromNib報警告

老項目在Xcode8中,有些重寫awakeFromNib方法的地方,會報下面的錯誤。這是由於沒有調用super的方法致使的,還好我平時都是調用super的,我代碼目前還沒出問題。

1

Method possibly missing a [super awakeFromNib] call

 

 

蘋果在iOS 2中引入了openURL:方法來進行APP間的跳轉。不過在iOS 9中,隱私控制已禁止開發者經過openURL:方法查詢設備上是否安裝了哪些APP應用。蘋果禁止開發者查詢設備上是否安裝了某款APP。在iOS 10中,蘋果棄用了openURL,轉而用openURL:options:completionHandler:替代。簡單介紹如何在iOS 10中進行APP之間的跳轉。

iOS 10中的新功能

蘋果在What's New in iOS文檔的UIKit部分中指出:

新的UIApplication方法openURL:options:completionHandler:能夠異步執行並在主隊列中執行完成後進行回調(此方法替換原來的openURL:)。

如今被廢棄的方法必須傳入啓動APP的URL並返回布爾值來標識成功或是失敗。

 

1

2

3

4

5

// Objective-C

- (BOOL)openURL:(NSURL*)url

 

// Swift

open func canOpenURL(_ url: URL) -> Bool

iOS 10中的新方法:

 

1

2

3

4

5

6

7

// Objective-C

- (void)openURL:(NSURL*)url options:(NSDictionary *)options

  completionHandler:(void (^ __nullable)(BOOL success))completion

   

// Swift

open func open(_ url: URL, options: [String : Any] = [:],

  completionHandler completion: (@escaping (Bool) -> Swift.Void)? = nil)

如今變爲三個參數

  • 打開APP的URL

  • 可選字典參數(請參見如下有效條目)。傳入一個空字典能夠達到openURL:同樣的行爲。

  • 執行成功後completionhandler在主隊列中回調。若是你並不關心它的返回狀態也能夠傳空。

在iOS10中打開URL

若是你有一個iOS 10應用程序也就意味着你不須要關心它的可選參數及完成回調函數返回的狀態並中止對Xcode的抱怨。

 

1

2

3

4

5

6

// Objective-C

UIApplication *application = [UIApplication sharedApplication];

[application openURL:URL options:@{} completionHandler:nil];

 

// Swift

UIApplication.shared.open(url, options: [:], completionHandler: nil)

在項目實踐中,若是你仍然兼容iOS9及更早的版本,你確定會想用回之前的openURL 老方法。下面來看一段代碼是如何使用completionHandler來檢查APP打開狀態。先上一段Object-C代碼:

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

- (void)openScheme:(NSString *)scheme {

  UIApplication *application = [UIApplication sharedApplication];

  NSURL *URL = [NSURL URLWithString:scheme];

 

  if ([application respondsToSelector:@selector(openURL:options:completionHandler:)]) {

    [application openURL:URL options:@{}

       completionHandler:^(BOOL success) {

      NSLog(@"Open %@: %d",scheme,success);

    }];

  else {

    BOOL success = [application openURL:URL];

    NSLog(@"Open %@: %d",scheme,success);

  }

}

 

// Typical usage

[self openScheme:@"tweetbot://timeline"];

我爲option參數傳入一個空的字典,除了只是在成功回調方法裏只是打印了一下日誌之外,並無寫任何有用的代碼。如下是Swift版本:

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

func open(scheme: String) {

  if let url = URL(string: scheme) {

    if #available(iOS 10, *) {

      UIApplication.shared.open(url, options: [:],

        completionHandler: {

          (success) in

           print("Open \(scheme): \(success)")

       })

    else {

      let success = UIApplication.shared.openURL(url)

      print("Open \(scheme): \(success)")

    }

  }

}

 

// Typical usage

open(scheme: "tweetbot://timeline")

Options 參數

UIApplication 頭文件爲options字典列出了一個key:

  • UIApplicationOpenURLOptionUniversalLinksOnly:若是這個要打開的URL有效,而且在應用中配置它布爾值爲true(YES)時才能夠打開,不然打不開。

爲了覆蓋默認行爲,建立一個設置key值了True的字典做爲參數傳入:

 

1

2

3

4

5

6

7

// Objective-C

NSDictionary *options = @{UIApplicationOpenURLOptionUniversalLinksOnly : @YES};

[application openURL:URL options:options completionHandler:nil];

 

// Swift

let options = [UIApplicationOpenURLOptionUniversalLinksOnly : true]

UIApplication.shared.open(url, options: options, completionHandler: nil)

以上面示例,若是我設置它爲true並打開URL:https://twitter.com/kharrison 時, 若是我並無安裝Twitter app那它就會失敗,同時會調用safari來打開這個連接。

 

 

原文:http://www.cocoachina.com/ios/20161024/17830.html

原文:http://www.cocoachina.com/ios/20161024/17824.html

相關文章
相關標籤/搜索