ハイライト
Apple は、WWDC 2021 で Xcode Cloud、Swift Concurrency、新しい SwiftUI コンポーネント、RealityKit 2、Focus API、Screen Time API、ウィジェットの提案、SharePlay を発表しました。これにより、開発者は Xcode 内で配信を完了し、Swift で同時コードを記述し、AR コンテンツを作成し、アプリケーションをシステムレベルのコラボレーションと集中的なエクスペリエンスに接続できるようになります。
主な内容
Apple プラットフォーム アプリケーションを作成する場合、コードの作成には時間の一部しかかかりません。チームはまた、テストを実行し、プル リクエストを読み取り、署名し、TestFlight を送信し、クラッシュ フィードバックを受信する必要があります。以前は、これらの手順がローカル スクリプト、Web ページ、サードパーティ CI、App Store Connect の間に分散されており、開発者は常に環境を切り替える必要がありました。
Apple は今回、配信リンクを Xcode に戻します。 Xcode Cloud は、Xcode 13 に組み込まれた継続的インテグレーションおよび継続的配信サービスです。Git ソース リポジトリに接続し、ビルドとテストを実行し、署名を処理し、TestFlight にビルドを渡し、Xcode のレポート ナビゲーターにレポートを表示します。
言語レベルでは、Swift 5.5 には同時実行モデルが導入されています。開発者が使用できるのは、asyncそしてawait非同期関数を作成するには、次を使用します。async let同時サブタスクを作成するには、次を使用します。actor可変状態を保護するには、次を使用します。@MainActorメインスレッドで実行する必要がある API を宣言します。以前は完了ハンドラー、DispatchQueue、および人間の慣例によって実現されていたものは、現在では言語ルールによって実現されています。
UI レベルでは、SwiftUI はアプリケーション開発の一般的な機能を補完し続けます。リストはスライド操作、プルダウンの更新と検索をサポートし、macOS ではTable、ローターと標準コントロールの継承を通じてアクセシビリティを向上させることができます。 Swift Playgrounds 4 を使用すると、iPad で SwiftUI アプリを作成し、App Store Connect にアップロードできるようになります。
グラフィックスと AR も参入障壁を下げます。 RealityKit 2 では、開発者が iPhone または iPad で一連の写真を撮影し、Mac 上で USDZ、USD、または OBJ モデルを生成できるようにするオブジェクト キャプチャが導入されています。 RealityKit は、カスタム サーフェス シェーダー、プロシージャル ジオメトリ API、後処理、コンピューティング シェーダー、およびジオメトリ モディファイアーも公開します。
最後の部分はユーザー関係を対象としています。通知には中断レベルと関連性スコアがあり、通信アプリケーションはフォーカス ステータスにアクセスできます。 Screen Time API は、管理対象設定、ファミリー コントロール、およびデバイス アクティビティをペアレンタル コントロール アプリケーションに提供します。ウィジェットは、インテントの寄付を通じてシステムの提案を受け取ることができます。 SharePlay は、GroupActivities フレームワークを通じて、FaceTime グループをアプリケーション内でアクティビティを共有できるようにします。
##詳細
Xcode Cloud: ビルド、テスト、TestFlight を Xcode に組み込む
(02:47) Xcode Cloud は、Apple の新しい CI/CD (継続的インテグレーションおよび継続的デリバリー) サービスです。 Xcode に組み込まれており、すべての Apple プラットフォームをサポートし、ビルド、テスト、署名、TestFlight 配布をクラウドに配置できます。
この講演ではコマンドライン API については説明しません。ワークフロー構成が表示されます。製品の選択、ワークフローの確認、ソース コード ウェアハウスの認証、App Store Connect への接続です。その後、プル リクエスト ワークフローを追加して、それぞれを許可できます。mainPR は iOS テスト計画を自動的に実行し、結果を Slack に通知します。
name: Pull Requests
startCondition:
type: pullRequest
targetBranch: main
environment:
xcode: public-beta
macOS: public-beta
actions:
- type: test
testPlan: iOS
simulators: recommended-iPhone-and-iPad
postActions:
- type: notify
destination: team-slack-channel
キーポイント:
name講義で作成したプルリクエストのワークフローに対応します。 -startConditionワークフローが送信されることを示しますmainブランチのプルリクエストを開始します。 -environmentプレゼンテーション用に Xcode と macOS のパブリック ベータ バージョンを選択します。 -actionsそれに応じてテスト アクションを追加し、プロジェクト内の既存の iOS テスト計画を選択します。 -simulatorsXcode Cloud が推奨する iPhone および iPad シミュレーターのセットに対応します。 -postActionsビルドの成功または失敗をチームに通知する、通知ポストアクションに対応します。
(08:21) Xcode Cloud は、プラットフォーム、デバイス シミュレーター、OS バージョン間で複数のテスト計画を並行して実行できます。 Xcode 13 には、UI テストのスクリーンショットを表示するためのギャラリー ビューも追加されています。また、不定期に失敗するテストの処理に役立つ、テストを繰り返し実行する API および予想失敗 API も提供します。
import XCTest
final class SmoothieTests: XCTestCase {
func testFavoriteButtonIsUnreliable() throws {
XCTExpectFailure("Favorite button can fail before sign-in is fixed")
let app = XCUIApplication()
app.launch()
app.buttons["Favorite"].tap()
XCTAssertTrue(app.staticTexts["Added to Favorites"].exists)
}
}
キーポイント:
import XCTestテストフレームワークの導入。 -SmoothieTestsXCTest テスト ケースを定義します。 -XCTExpectFailure既知の失敗にフラグを立てて、その理由をチームに残します。 -XCUIApplication()テスト対象のアプリケーションを作成します。 -app.launch()アプリケーションを起動します。 -app.buttons["Favorite"].tap()ユーザーがお気に入りボタンをクリックする様子をシミュレートします。 -XCTAssertTrue問題が修正された後もテストで動作を検証できるように、アサーションを保持します。
Swift Concurrency: 非同期プロセスを直線で記述する
(21:22) Swift 5.5async/await言語を追加します。非同期関数の場合asyncコールポイントに使用されるマーカーawaitマーク。スピーチ用prepareForShow注: 完了ハンドラーは、プロセスをネストされたコールバックに変換します。async/await制御フローは上から下に読むことができます。
enum StageError: Error {
case missingScenery
}
struct Dancer {}
struct Scenery {}
struct Stage {}
func warmUpCompany() async throws -> [Dancer] {
[Dancer()]
}
func fetchStageScenery() async throws -> Scenery {
Scenery()
}
func setStage(with scenery: Scenery) async throws -> Stage {
Stage()
}
func moveToOpeningPositions(_ dancers: [Dancer], on stage: Stage) async throws {
print("Ready")
}
func prepareForShow() async throws {
let dancers = try await warmUpCompany()
let scenery = try await fetchStageScenery()
let stage = try await setStage(with: scenery)
try await moveToOpeningPositions(dancers, on: stage)
}
キーポイント:
enum StageError非同期関数が引き続き Swift のエラー メカニズムを使用することを示すエラー タイプを定義します。 -warmUpCompany()、fetchStageScenery()、setStage(with:)両方を使用するasync throws非同期を表し、失敗する可能性があります。 -prepareForShow()これは、他の非同期関数を呼び出すため、非同期関数でもあります。 -try await warmUpCompany()ダンスグループがウォーミングアップしてバグを広めるのを待ちます。 -try await fetchStageScenery()シーンがロードされるまで待ちます。 -try await setStage(with:)風景で舞台を設定します。 -try await moveToOpeningPositions最初のいくつかの手順が完了したら、アクターの位置を移動します。
(23:05) 構造化同時実行により、同時タスクは引き続き現在のスコープに属することができます。スピーチで示されたのは、async let: ウォームアップとシーンの取得は並行して実行でき、結果が本当に必要なときに実行できます。await。
func prepareForShowInParallel() async throws {
async let dancers = warmUpCompany()
async let scenery = fetchStageScenery()
let stage = try await setStage(with: scenery)
try await moveToOpeningPositions(dancers, on: stage)
}
キーポイント:
async let dancersサブタスクを作成して実行を開始するwarmUpCompany()。async let scenery別のサブタスクを作成して実行を開始するfetchStageScenery()。- 2 つのサブタスクは親タスクと同じファミリーに属します。
prepareForShowInParallel()構造化されたスコープ。 -try await setStage(with: scenery)シーンを設定する必要がある場合は結果を待っています。 -try await moveToOpeningPositions(dancers, on: stage)ダンサーが必要な場合は結果を待っています。
(24:31) Swift も追加しますactor。アクターはオブジェクトと同様に状態を保持しますが、外部アクセスは通過します。async/await相互排除を調整します。講演では、これを以前の手書きのシリアルディスパッチキューモデルと比較し、アクターがロックの忘れによって引き起こされるデータ競合を削減できると指摘しました。
actor SmoothieInventory {
private var stock: [String: Int] = [:]
func add(_ name: String, count: Int) {
stock[name, default: 0] += count
}
func take(_ name: String) -> Bool {
guard let count = stock[name], count > 0 else {
return false
}
stock[name] = count - 1
return true
}
}
let inventory = SmoothieInventory()
await inventory.add("Berry Blue", count: 10)
let success = await inventory.take("Berry Blue")
print(success)
キーポイント:
actor SmoothieInventoryアクターのタイプを宣言します。 -private var stockこれは、アクター自体によって保護される可変の状態です。 -add手書きのキューを必要とせずに、アクター内で状態を直接変更します。 -takeインベントリは読み取られて更新され、操作全体はアクター分離によって保護されます。 -await inventory.addアクターの外部からメソッドを呼び出すには、非同期待機が必要です。 -await inventory.take外部アクセスが同時に破壊されないようにするstock。
(26:30) UI については、Swift が提供します@MainActor。講演では、これまでは、メインスレッドで実行する必要がある API への呼び出しはすべて、手動でメインキューにディスパッチする必要があったと説明しました。宣言にメインアクターに注釈を付けることができるようになりました。
import SwiftUI
@MainActor
final class SmoothieViewModel: ObservableObject {
@Published var title = "Loading"
func updateTitle(_ value: String) {
title = value
}
}
キーポイント:
@MainActorこのビュー モデルの API をメイン アクター上で実行するように宣言します。 -ObservableObjectSwiftUI でオブジェクトの変更を観察させます。 -@Published var titleビューが変更されたときに更新するように通知します。 -updateTitleUIステータスを手書きなしで直接更新可能DispatchQueue.main.async。
SwiftUI と Swift Playgrounds: 一般的なインタラクションが修飾子になる
(30:14) SwiftUI は今年、リスト、検索、テーブル、マテリアルを完成させました。講演内の Fruta の例では、コレクションのスライディング操作、プルダウンの更新、検索ボックス、および検索候補を数行のコードにまとめています。
import SwiftUI
struct Smoothie: Identifiable {
let id = UUID()
let name: String
let subtitle: String
}
struct SmoothieList: View {
@State private var searchText = ""
@State private var smoothies = [
Smoothie(name: "Berry Blue", subtitle: "Blueberry and banana"),
Smoothie(name: "Green Garden", subtitle: "Kale and apple")
]
var body: some View {
List(filteredSmoothies) { smoothie in
VStack(alignment: .leading) {
Text(smoothie.name)
Text(smoothie.subtitle)
.foregroundStyle(.secondary)
}
.swipeActions {
Button("Favorite") {
print("Favorite \(smoothie.name)")
}
}
}
.refreshable {
await reloadSmoothies()
}
.searchable(text: $searchText) {
Text("Berry").searchCompletion("Berry")
Text("Green").searchCompletion("Green")
}
}
private var filteredSmoothies: [Smoothie] {
guard !searchText.isEmpty else { return smoothies }
return smoothies.filter { $0.name.localizedCaseInsensitiveContains(searchText) }
}
private func reloadSmoothies() async {
smoothies = smoothies
}
}
キーポイント:
@State private var searchText検索入力を保存します。 -List(filteredSmoothies)フィルタリングされたデータをレンダリングします。 -.swipeActionsリスト行にスライド操作を追加します。 -Button("Favorite")スライド後に表示されるお気に入りボタンを定義します。 -.refreshableプルダウン更新を追加し、非同期関数の実行を許可します。 -.searchable(text:)システム検索ボックスを追加すると、プラットフォームによって検索ボックスの場所が決定されます。 -.searchCompletion検索ボックスに提案された用語を入力します。 -filteredSmoothies入力に基づいてリストをフィルターします。
(31:40) macOS では、SwiftUI が増加しますTable。プレゼンテーションでは、新しいファイルを使用して複数列のテーブルを追加し、検索結果もテーブルに表示する方法を示しました。
import SwiftUI
struct SmoothieTable: View {
let smoothies: [Smoothie]
var body: some View {
Table(smoothies) {
TableColumn("Name", value: \.name)
TableColumn("Description", value: \.subtitle)
}
}
}
キーポイント:
Table(smoothies)一連のデータから macOS の複数列テーブルを作成します。 -TableColumn("Name", value: \.name)バンドルname最初の列に表示されます。 -TableColumn("Description", value: \.subtitle)バンドルsubtitle2列目に表示されます。- 表形式のデータは同じモデルのセットから取得されており、検索結果で再利用できます。
(33:56) Swift Playgrounds 4 は、iPad での SwiftUI アプリの作成をサポートしています。スピーチでは、左側にコード、右側にライブ プレビュー、挿入ポイントの下にコード補完が表示され、リアルタイムのコンソール表示が表示されます。print出力。アプリは、アプリ設定から App Store Connect にアップロードすることもできます。
import SwiftUI
struct PlaygroundContentView: View {
var body: some View {
Button {
print("Hello from Swift Playgrounds")
} label: {
Label("Say Hello", systemImage: "swift")
}
}
}
キーポイント:
Button音声内の静的テキストをボタンに置き換えるクリック可能なコントロールを作成します。 -print出力は、Swift Playground のメッセージ バブルとコンソールに表示されます。 -LabelテキストとSFシンボルを組み合わせます。 -systemImage: "swift"システムシンボルを使用します。
RealityKit 2: 写真を使用して 3D モデルを生成し、そのモデルを AR に配置します
(40:23) RealityKit 2 にはオブジェクト キャプチャが追加されています。このプロセスでは、まず iPhone または iPad を使用して複数の角度から写真を撮影し、次に Mac の Object Capture API を使用して写真フォルダーを AR に最適化された 3D モデルに変換します。
import Foundation
import RealityKit
@main
struct ObjectCaptureTool {
static func main() async throws {
let inputFolder = URL(fileURLWithPath: "/Users/me/CroissantPhotos")
let outputFile = URL(fileURLWithPath: "/Users/me/croissant.usdz")
let session = try PhotogrammetrySession(input: inputFolder)
try session.process(requests: [
.modelFile(url: outputFile, detail: .preview)
])
}
}
キーポイント:
import RealityKitObject Capture が配置されているフレームワークを紹介します。 -inputFolder写真が撮影されたフォルダーをポイントします。 -outputFile生成された USDZ ファイルをポイントします。 -PhotogrammetrySession(input:)講義中の「撮影した画像のフォルダを指す」に相当する写真計測セッションを作成します。 -process(requests:)音声の「処理関数の呼び出し」に相当するモデル生成を開始します。 -.modelFile(url:detail:)モデルファイルの生成を要求します。 -.previewこれは、プレビューレベルの詳細モデルを生成することを意味します。スピーチの中で、必要な詳細レベルを選択できると述べられました。
(42:58) モデルを生成した後、それを Xcode プロジェクトにドラッグし、ARKit を使用してそれを App Clip コードに固定し、次に使用します。ModelEntityアセットを初期化します。 RealityKit 2 は、カスタム サーフェス シェーダー、プロシージャル ジオメトリ API、後処理、コンピューティング シェーダー、およびジオメトリ モディファイアーもサポートしています。
import ARKit
import RealityKit
import SwiftUI
struct CroissantARView: UIViewRepresentable {
func makeUIView(context: Context) -> ARView {
let view = ARView(frame: .zero)
let anchor = AnchorEntity(.plane(.horizontal, classification: .any, minimumBounds: [0.2, 0.2]))
if let croissant = try? ModelEntity.loadModel(named: "croissant") {
anchor.addChild(croissant)
}
view.scene.addAnchor(anchor)
return view
}
func updateUIView(_ uiView: ARView, context: Context) {}
}
キーポイント:
ARViewRealityKitのARレンダリングビューです。 -AnchorEntity(.plane(...))水平面上にアンカーポイントを作成します。 -ModelEntity.loadModel(named:)3D モデル リソースをプロジェクトに読み込みます。 -anchor.addChild(croissant)モデルをアンカーポイントに吊り下げます。 -view.scene.addAnchor(anchor)ARシーンにアンカーポイントを追加します。 -UIViewRepresentableSwiftUI をホストにするARView。
フォーカス、スクリーンタイム、ウィジェット、および SharePlay: アプリケーション アクセスのシステム レベルの関係
(52:21) 新しい割り込みレベル API の取得に関する通知。開発者は、通知をパッシブ、アクティブ、時間重視、クリティカルの 4 つのカテゴリに分類できます。通知の概要では、サムネイルと関連性スコアに基づいて、概要の上部にあるマーキー スロットも選択されます。
import UserNotifications
func scheduleOrderReadyNotification() async throws {
let content = UNMutableNotificationContent()
content.title = "Smoothie ready"
content.body = "Your Berry Blue smoothie is ready for pickup."
content.interruptionLevel = .timeSensitive
content.relevanceScore = 0.9
let request = UNNotificationRequest(
identifier: "smoothie-ready",
content: content,
trigger: nil
)
try await UNUserNotificationCenter.current().add(request)
}
キーポイント:
UNMutableNotificationContent通知コンテンツを作成します。 -titleそしてbodyユーザーに表示されるテキストです。 -.timeSensitive通知は直ちに配信する必要があり、音声リクエストは現時点で関連し、即時対応が必要なコンテンツにのみ使用されることを示します。 -relevanceScoreシステムがスニペット内のプレゼンテーションの優先順位を決定するのに役立ちます。 -UNNotificationRequestコンテンツを通知リクエストにラップします。 -UNUserNotificationCenter.current().add通知を送信します。
(58:09) Screen Time API はペアレンタル コントロール アプリケーション用であり、管理対象設定、ファミリー コントロール、デバイス アクティビティという 3 つの Swift フレームワークが含まれています。 Family Controls のピッカーは不透明なトークン (不透明なトークン) を返し、アプリケーションは特定のアプリや Web サイトを制限または監視できますが、元のバンドル ID と URL を取得することはできません。
import DeviceActivity
import FamilyControls
import ManagedSettings
struct HomeworkSchedule {
let center = DeviceActivityCenter()
let activity = DeviceActivityName("homework")
func start() throws {
let schedule = DeviceActivitySchedule(
intervalStart: DateComponents(hour: 16),
intervalEnd: DateComponents(hour: 18),
repeats: true
)
try center.startMonitoring(activity, during: schedule)
}
}
キーポイント:
DeviceActivityCenterデバイスのアクティビティ監視に登録するために使用されます。 -DeviceActivityName("homework")アクティブなウィンドウに名前を付けます。 -DeviceActivitySchedule毎日 16:00 から 18:00 までの時間枠を定義します。 -repeats: true繰り返し実行することを示します。 -startMonitoringこのアクティブなウィンドウの監視を開始します。- 音声の説明: アプリケーションは警告イベントと完了イベントを受信した後、制限を調整したり、子供たちに宿題を完了するよう促したりすることができます。
(01:04:48) ウィジェットに提案機能が追加されました。システムは、ユーザーによるアプリケーションとの対話や、インテントを通じてアプリケーションから提供された新しい関連情報に基づいて、スマート スタックへのウィジェットを推奨できます。プレゼンテーションの例は、朝に青汁を注文することが多いユーザーにウィジェットを推奨する Fruta アプリでした。
import Intents
func donateMorningSmoothieInteraction() {
let intent = INIntent()
let interaction = INInteraction(intent: intent, response: nil)
interaction.identifier = "morning-green-juice"
interaction.donate { error in
if let error {
print("Donation failed: \(error)")
}
}
}
キーポイント:
INIntentシステムに寄付できるインテントを表します。 -INInteractionインテントをユーザー関連のインタラクションにラップします。 -identifierこの寄付に安定フラグを付けてください。 -donateウィジェットの提案などのシナリオについては、対話をシステムに任せます。- 講演では、過去の使用行動と新しい関連インテントの寄付の両方が、システムがウィジェットを提案するのに役立つ可能性があると指摘しました。
(01:06:38) SharePlay は GroupActivities フレームワークによって駆動されます。開発者は、GroupActivity、ユーザーが FaceTime 通話中にアクティビティを開始した後、システムは同じグループの人々をアプリに取り込みます。メディア アプリケーションは AVPlayer の再生コーディネーターを使用して同期再生を実現でき、カスタム アプリケーションはGroupSessionMessengerリアルタイムデータを送信します。
import AVFoundation
import GroupActivities
struct WatchSmoothieShow: GroupActivity {
let url: URL
var metadata: GroupActivityMetadata {
var metadata = GroupActivityMetadata()
metadata.title = "Watch Smoothie Show"
metadata.type = .watchTogether
return metadata
}
}
func startSharedPlayback(url: URL, player: AVPlayer) async throws {
let activity = WatchSmoothieShow(url: url)
let activation = try await activity.prepareForActivation()
guard activation == .activationPreferred else {
player.play()
return
}
_ = try await activity.activate()
}
キーポイント:
WatchSmoothieShow従うGroupActivity、共有できるアクティビティを定義します。 -url各参加者がロードするコンテンツ アドレスです。音声記述にすでにディープリンクがあるアプリケーションは、それを再利用できます。 -metadataシステム UI で必要なタイトルとアクティビティ タイプを指定します。 -prepareForActivation()システムに確認ダイアログを表示させます。ユーザーが FaceTime 通話中でない場合は、すぐに戻ります。 -.activationPreferredシステムが共有アクティビティの開始を推奨することを示します。 -activate()実際に SharePlay アクティビティを開始します。 -player.play()共有アクティビティが開始されていないときのローカル再生パスです。
import AVFoundation
import GroupActivities
func coordinatePlayback(player: AVPlayer, session: GroupSession<WatchSmoothieShow>) {
player.playbackCoordinator.coordinateWithSession(session)
session.join()
}
キーポイント:
GroupSession<WatchSmoothieShow>現在の SharePlay セッションを表します。 -playbackCoordinatorAVPlayerの再生連携入口です。 -coordinateWithSession(session)プレーヤーをグループ アクティビティ セッションに接続して、フレーム レベルの同期を実現します。 -session.join()このデバイスを共有アクティビティに参加させます。
重要なポイント
-
やるべきこと: チーム アプリケーションを Xcode Cloud の PR テスト プロセスに接続します。 実行する価値がある理由: この講演では、プル リクエストのワークフロー、並行テスト、ビルド レポート、チームのフィードバックを Xcode に戻すための Slack 通知について紹介します。 開始方法: Xcode 13 の Xcode Cloud メニューでワークフローを作成し、プル リクエストを
main開始時に、テスト アクションを追加し、テスト計画を選択して、通知後のアクションを追加します。 -
何をすべきか: ネットワーク リクエストが集中するページを Swift Concurrency に移行します。 実行する価値がある理由:
async/await、async letアクターはコールバックのネストを減らし、共有状態の保護を言語モデルに任せることができます。 開始方法: まず、完了ハンドラーをカプセル化します。async throws機能、再利用async let独立したデータは並列にプルされます。共有キャッシュはアクターに入れられます。 -
何をすべきか: プルダウンの更新、検索候補、およびスライド コレクションをリスト ページに追加します。 実行する価値がある理由: SwiftUI は、これらの一般的なインタラクションを次のようなものに変えます。
.refreshable、.searchable、.swipeActions、カスタム UIKit のラッピングを減らすことができます。 開始方法: データモデルを作成するIdentifiable、存在するListオンラインで追加.swipeActions、リストの外側に追加します.refreshableそして.searchable(text:)。 -
やるべきこと: 電子商取引またはメニュー アプリケーション用の AR 製品プレビューを生成します。 実行する価値がある理由: Object Capture は実際のオブジェクトの写真を USDZ に変換でき、RealityKit 2 は App Clip または完全なアプリケーションでモデルを表示できます。 開始方法: iPhone であらゆる角度からオブジェクトの写真を撮り、Mac で使用します。
PhotogrammetrySessionUSDZを生成して使用しますModelEntity.loadModel(named:)ARシーンに入れます。 -
対処方法: SharePlay をビデオ、ホワイトボード、または読書アプリに追加します。 実行する価値がある理由: GroupActivities は、FaceTime グループ、同期再生、エンドツーエンドの暗号化されたデータ チャネルを提供するため、アプリケーションは独自のリアルタイム コラボレーション インフラストラクチャを構築する必要がありません。 開始方法: コンプライアンスの定義
GroupActivityアクティビティの種類。メディア再生用AVPlayer.playbackCoordinator.coordinateWithSession、カスタムコラボレーション用GroupSessionMessenger動作データを送信します。
関連セッション
- Xcode Cloud の紹介 — Xcode Cloud のビルド、テスト、署名、配布プロセスを製品の観点から紹介します。
- Swift での async/await について — 詳しい説明
async、await、非同期プロパティ、および完了ハンドラーから移行する方法。 - SwiftUI の新機能 — このシステムは、リスト、検索、テーブル、マテリアル、キャンバスなどの SwiftUI の新機能を拡張します。
- Object Capture を使用して 3D モデルを作成する — RealityKit を使用して写真を撮影し 3D モデルを生成する方法の詳細な手順。
- グループ アクティビティの紹介 — SharePlay の GroupActivity、セッション管理、共有エクスペリエンス アーキテクチャについて説明します。
コメント
GitHub Issues · utterances