Apple 未有任何公告便發佈了 iOS 14,讓整個開發者社群都十分驚喜。無論如何,這就是需要配合最新的 OS 來更新 App 的時候了。
首先,以下是一些 iOS 14 中你應該注意的重大改變:
- 在首頁引進 Widget 及 App Clips。
- 以新的 AppTrackingTransparency 框架來取代 IDFA,以作廣告追蹤之用(在撰寫本文的時候,Apple 將此功能延後至 2021 年 1 月推出)。
- 引入了新的 Vision 請求,來處理輪廓 (contour)、軌跡 (trajectory) 檢測、以及手與身體姿勢估算。
- ARKit 為 LiDAR 掃瞄器及位置錨點 (Location Anchors) 帶來新的 Depth API,為特定場所帶來 AR 體驗。
- Apple 的 PencileKit 框架引入了在
PKCanvas
上追蹤手勢速度和壓力的功能。另外,也有新的 ScribbleUITextField
,可以在裝置上的機器學習中識別手寫文字。
現在,讓我們來探究不同 Apple 框架的重要更新和 API 的變動,讓你準備好在 iOS 14 更新 App 了。
更完善的 Pasteboard API
Apple 是資料隱私領域的領導者,而隨著最新的 iOS 更新,他們再次顯現這個地位。
iOS 14 引入一個浮動通知 (floating notification),在 App 讀取剪貼簿裡的內容時出現。為了避免 App 在不必要的情況下存取剪貼簿,現在添加了一個更完善的 UIPasteboard
API,讓你在實際讀取資料前,決定 UIPasteboard
裡呈現的內容種類。
你可以利用 detectPatternsForPatterns:completionHandler
與 detectPatterns(for:inItemSet:completionHandler:)
方法,無需觸發通知,就可以找出特定的模式 (Pattern)。
同時,你可以利用 UIPasteboard.DetectionPattern
結構,來確認剪貼簿是否包含 probableWebUrl
(它可能與 Deep Link 有關)或是 number
。
Picture in Picture 模式
雖然 iPadOS 之前已經支援 Picture in Picture 模式,不過,iOS 14 終於把它帶進 iPhone 的世界裡。
你可以使用 AVPictureInPictureController.isPictureInPictureSupported()
,來確認是否支援在背景播放影片功能:
AVPictureInPictureController(playerLayer: playerView.playerLayer)
但如果你像我一樣,在一個基於 AVPlayer
的 iOS 14 App 中調用 PiP 模式,可能會出現些奇怪的錯誤:當 App 進入背景時,Picture in Picture 無法自動執行。幸運地,在 Stack Overflow 上的這篇文章 提供了解決方法,就是在 AVPictureInPictureController
之前初始化 AVAudioSession.sharedInstance().setActive(true)
。
有限的 Photos Library 讀取權限
在 iOS 13 或更早前的版本中,如果我們允許 App 讀取 Photos Library,就會讓 App 讀取所有相簿及多媒體內容。但這很容易洩漏隱私資料,因為開發者可以上傳裡面的內容到雲端伺服器。
隨著 iOS 14 釋出,Apple 引入有限的相片讀取權限,讓使用者選擇給予特定相片或是整個 Photo Library 的權限,以此保護隱私資料。這也意味著 iOS 開發者們的能做的事又變少了。
因此,我們有一個新的 PHAccessLevel
列舉屬性,來定義權限是 readWrite
還是 addOnly
:
let accessLevel: PHAccessLevel = .readWrite
為了查詢 Photos Library 的授權狀態,將上面的列舉送到下列的函式裡:
let authorizationStatus = PHPhotoLibrary.authorizationStatus(for: accessLevel)
從 iOS 14 開始,authorizationStatus
會回傳一個新 limited
列舉屬性,也就是說,只有使用者選擇的照片才會讓開發者看見。要請求有限的照片讀取權限,我們需要調用下列函式:
PHPhotoLibrary.requestAuthorization(for: .readWrite) { status in
switch status {
case .limited:
print("limited access granted")
default:
print("not implemented")
}
}
輸入下面的程式碼片段,以顯示圖像選取器 UI:
PHPhotoLibrary.shared().presentLimitedLibraryPicker(from: self)
我們可以讓 photoLibraryDidChange
函式符合並且註冊的 PHPhotoLibraryChangeObserver
協定,來監視使用者選擇/取消選擇的圖像。
現在,為了避免每次都會自動跳出相片讀取權限的提示,讓我們在 Info.plist
裡設定 PHPhotoLibraryPreventAutomaticLimitedAccessAlert
的值為 true
。
SwiftUI 帶來新屬性包裝器 (Property Wrappers)、視圖、修飾符 (Modifiers) 及 App 生命週期 (Lifecycle)
SwiftUI 是 Apple 新的宣告式 UI 框架,它在 WWDC 2019 期間獲得極大迴響,即使到了今年仍是如此。隨著 iOS 14 推出 SwiftUI 的第二版,SwiftUI 引進了更多的新 UI 元件,包括 VideoPlayer
、Maps
、Labels
、Links
、ColorPicker
、及 ProgressView
等等。
更重要的是,iOS 14 引進 LazyHStack
以及 LazyVStack
,來支援 VStack
與 HStack
的延遲讀取 (Lazy Loading)。也就是說,你不需擔心 NavigationLinks
會立即讀取目標視圖 (destination view)。
另外,還有一個新的 Grid
元件,它在一定程度上可以取代 UICollectionView
。而新的 matchedGeometryEffect
修飾符就可以建立絢麗的過場與動畫效果。
除了透過全新屬性包裝器與協定來引進SwiftUI 自己的 App 生命週期 外,iOS 14 也添加了 WidgetKit
框架,讓你使用純 SwiftUI 來構建出漂亮而功能強大的 Widget。
更強大的 CollectionView
雖然 SwiftUI 的 CollectionView 沒有在 WWDC 2020 中亮相,但它還是混加了一些強大的新功能。
以下是CollectionView 的一些大改變,可以讓你在 iOS 14 的 App 中使用:
UICollectionViewCompositionalLayout.list
讓你在UITableView
裡建立像UITableView
的外觀,進而加強客製化合成佈局的能力。我相信這表示TableViews
在未來可能會過時。UICollectionView.CellRegistration
結構為我們帶來了新的方法,來配置UICollectionView
的 Cell。所以你不再需要再定義 Cell Identifiers,因為新結構在傳送到dequeueConfiguredReusableCell
內時,會自動處理 Cell 的註冊。- 在 iOS 13 推出的
DiffableDataSources
,現在也帶來了SectionSnapshots
,在每個 Section 上客製及更新資料。
CoreLocation 更好地保護隱私
雖然 iOS 13 引入了延遲的 “Always allow” 與新的 “Allow once” 權限,不過,iOS 14 可以讓使用者授權大概位置的存取權限,來進一步加強隱私。
也就是說,iOS 14 新增了 CLAccuracyAuthorization
型別的屬性。新屬性擁有兩個列舉情況 fullAccuracy
及 reducedAccuracy
(回傳大概位置,而非確實位置)。
此外,現在已不推薦使用 authorizationStatus()
函式,你應該使用 locationManagerDidChangeAuthorization
來查找位置權限狀態。
Core ML 模型加密
Core ML 是 Apple 的機器學習框架,它讓你初始化模型、執行分析、甚至在裝置上進行訓練。到了 iOS 14,Apple 引入了 Model Deployment 讓 Core ML 大躍進。也就是說,你可以遠端更新機器學習模型,而不需更新整個 App。
另外,Xcode 也改善了 Core ML 模型檢視器,可以顯示更下層的東西。不過這次更新最出色的,是模型加密。機器學習模型不容易建置,而且有時會包含敏感資料。之前,你可以很容易擷取嵌入在 App 裡的 .mlmodelc
Core ML 模型檔案。
現在,你在 Xcode 12 裡加密模型後,就不能擷取模型了。如此一來,Core ML 會自動解密,並在App 的記憶體裡讀取。
為了處理加密模型,iOS 14 帶來了新的 Core ML 模型非同步初始器函式:
MyModel.apply{
switch result {
case .success(let model):
currentModel = model
case .failure(let error):
handleFailure(for: error)
}
}
模型只在解密成功時讀取一次。值得注意的是,Apple將不再建議使用初始化 Core ML 模型的舊init()
方法。
總結
這篇文章提及的更新,是你的 App 需要變更的部分。但是,iOS 14 還有其他重要的變更,例如 Natural Language 框架中包含語句嵌入功能,以及支援使用 Create ML 來訓練樣式轉換模型等。
以上總結了開發者需要知道的 iOS 14 主要更新。謝謝你的閱讀。