大多数浏览器和
Developer App 均支持流媒体播放。
-
App Intents 的新功能
了解 App Intents 有哪些改进和提升,并探索这个框架如何帮助你将 App 的功能公开给 Siri 和其他新功能。我们将介绍如何使用 Transferable API、File Representations、Item Providers 以及 Spotlight Indexing 让你的实体在平台中更有意义,从而通过 Siri 和“快捷指令”App 实现强大的功能。使用 URL Representable Entities 和灵活的场景 API 来增强你的意图,帮助用户深入探索你的 App。探索相关的新技术,以通过用于错误处理、延迟属性和关联枚举的新 API 为你的实体和意图建模。
章节
- 0:00 - Introduction
- 1:16 - Spotlight integration
- 5:00 - Entities and files
- 11:41 - Universal links
- 14:24 - Developer improvements
资源
- Accelerating app interactions with App Intents
- App Intents
- Forum: Machine Learning and AI
- Making actions and content discoverable and widely available
相关视频
WWDC24
WWDC23
WWDC22
WWDC21
-
下载
大家好 我叫 Kenny 是 App Intents 团队的工程师
App Intents 让你能够充分利用 “快捷指令”“聚焦”、小组件 以及许多其他功能 包括操作按钮 和新增的 Apple Pencil 轻捏手势 为你的 App 带来诸多精彩体验
今年 App Intents 在 Apple Intelligence 体验 和控件体验的构建中 发挥了核心作用
App Intents 框架 将提供新的方式 来帮助系统理解并使用 你的 App 实体 并让 AppIntents 变得更加简单易用
今天要介绍的内容很多 我们现在就开始吧 我们将介绍如何 将 App 实体索引到“聚焦” 让 Siri 可以充分 理解你的内容
能将你的 App 实体 转换为特定类型的内容 或者直接将你的文稿 作为 App 实体进行公开
也能将 App Intent 类型 作为通用链接进行公开 以便设备根据你的需要 直接带你前往 App 中的相应位置
此外还有开发者体验 方面的一些改进 让你能更轻松地 利用 App Intents 如果你不熟悉 App Intents 建议先观看视频 “利用 App Intents 为用户 奉上 App 的核心功能”
“聚焦”是查找相关内容的好地方 “聚焦”知道我经常使用哪些 App 并且会建议我使用它们 根据这些 App “聚焦”会提供常用操作的快速访问
可能还会显示当前天气状况 或是最近的搜索结果
“聚焦”还提供了 强大的搜索功能 可以帮助你找到所需的内容 比如快速找到特定的备忘录
还有“最佳搜索结果” 中的 App 快捷指令 让你能够通过 AppIntents 轻松公开 App 中的实用功能
今年 我们将添加新的 API 让你能够将 App 实体 索引到“聚焦”中 从而为 App 实体带来强大的 全新语义搜索功能 我们先来了解一下新的 IndexedEntity 协议 借助 CSSearchableIndex 你可以使用 CSSearchableItem 将 App 相关信息索引到“聚焦” 任何 CSSearchableItem 都有一个 属性会设置为扩展所提供的信息
新的 IndexedEntity 让你可以轻而易举地将 App 实体 索引到 CSSearchableIndex 同时让你仍然能够自定属性集 这样一来 你的实体就可以 显示在“聚焦”搜索结果中 并帮助 Siri 理解和找到它们
我和家人都热爱徒步旅行 所以我在开发一个 App 来记录我们喜欢的徒步路线 如果无需打开我的 App 就能在“聚焦”中搜索徒步路线 那真是太好了 为此 我要在 TrailEntity 中 添加对 IndexedEntity 的支持
首先 在 TrailEntity 中添加对新的 IndexedEntity 协议的遵从性
然后 在 App 的 init 方法中 通过在 CSSearchableIndex 上 调用 indexAppEntities 索引来自数据管理器的 所有 Trail 实体 这样就可以了 现在会将我的 TrailEntity 内容提供给“聚焦” 我们来看看它的实际效果 首先 启动我的 App 这样就有机会运行 新的实体索引代码
现在 我要在“聚焦”中 搜索我走过的一条徒步路线 我们可以看到 我的徒步路线内容 显示为搜索结果
因为有一个 OpenTrailIntent 接受了作为参数的 TrailEntity 轻点搜索结果 即可直接前往 这条徒步路线在 App 中的位置 稍后我会详细讨论这一点
默认的 IndexedEntity 实现 只使用 DisplayRepresentation 来填充属性集 但属性集允许你指定 可能会对“聚焦”有用的各种信息 比如位置信息或关键词 我要通过自行实现 attributeSet 向“聚焦”提供更多信息
首先 提供 TrailEntity 上的 一个 attributeSet 实现
自定这个 attributeSet 让它包含一些可能 与我的实体相关的属性 比如我的徒步路线 所在位置所属的城市和州
将关键词设置为 这条徒步路线支持的活动
向“聚焦”提供更多信息 有助于增强搜索和理解 从而返回相关性更高的结果 如果你的应用程序已经 在用 CSSearchableItem API 将内容索引到“聚焦” 则可以使用新的 associateAppEntity 方法 在建立索引之前将 AppEntity 与可搜索的项目关联 这样一来 新的语义搜索就可以 查找有关你的 AppEntity 的信息
你也可以使用任意 IndexedEntity 索引 API 来设置优先级 数值越大 项目就越重要 例如 你可以通过这种方式 赋予收藏项目比未收藏项目 更高的优先级
单凭 CSSearchableItem 就能提供强大的搜索功能 但是它无法对内容执行操作 通过对 App 实体进行索引 你可以利用 适用于这个实体的现有功能 还可以帮助 Siri 找到你的实体并对其执行操作 比如查找包含航班详细信息的 电子邮件并转发给朋友 接下来 我要谈谈如何 让实体对设备来说更有意义
通过 AppEntity 你可以定义 和公开 App 中的概念 比如 Trail
但其他 App 无法理解这些概念 我可以改为用任何 App 都能理解的 标准化格式 比如 PDF 来表示我的实体
同时使用统一类型标识符 来为文件或数据添加类型标签
现在已经有了一个 API 可以帮助我们做到这一点 Transferable 是一种声明式方法 用于描述如何通过模型序列化 和反序列化来实现共享和数据迁移 现在 你能够对 App 实体 采用 Transferable 方法
例如 可以使用 Transferable 将 AppEntity 转换并导出为 PDF、 图像、 和富文本 借助 Transferable Siri 和“快捷指令”可以转换 AppEntity 并将新的值传递给 其他 AppIntents
这样就能允许系统将你的内容 作为附件传递给“邮件” 或者转换为图像并导入照片图库
在“My Trails”App 中 我可以跟踪已完成的活动 并将它们表示为 Activity Statistic Summary 实体 我希望这种做法对其他 App 也是有意义的 因此我要添加 对 Transferable 的支持
我要使用 Transferable 来扩展我的实体 然后实现一个静态 transferRepresentation 方法
我已经有了一个方法 可将 Activity Summary 转换为富文本 所以我要添加 DataRepresentation 将 RTF 或富文本 指定为 exportedContentType
我还有一个可以将摘要 导出为 PNG 文件的方法 所以 我还要添加一个 导出为 PNG 的 FileRepresentation
Transferable 表示的 定义顺序非常重要 请按照保真度从高到低的顺序 来提供这些表示 例如 我的类型的 私有 Codable 表示排在第一位 随后是有损程度更高的格式 比如富文本 然后是纯文本 我们来看看这项功能 在“快捷指令”中的实际效果 我已经有了一个快捷指令 可以接收 Summarize Activities 操作的输出 并将 Calories Burned 属性附加到 我的 Activity Log 备注中
现在 我已经实现了 Transferable 接下来 我们看看如果将输出 更改为实体本身 会发生什么 运行这个快捷指令后 可以看到 它将 Summarize Activities 的结果 转换为文本并 附加到相应的备注中
如果将类型更改为 Image
然后再次运行这个快捷指令 我们可以看到它改为使用 我的 PNG 表示 看看这个效果 说不定我以后 去我们的设计团队也能玩得转 目前对于如何将 Transferable API 与 AppEntity 结合使用 存在一些限制 因为 Xcode 需要在编译时理解你的 Transferable 表示 如果它无法理解 就会提供反馈 此外 如果使用 @Property 属性 来引用 AppEntity 的属性 则只能使用 ProxyRepresentation 因此 在这个示例中 我可以使用 name 属性 因为它具有 @Property 属性
但不能使用 description 因为它没有 @Property 属性
如果你想了解 有关 Transferable 的更多信息 强烈建议观看 Julia 在 WWDC22 上 的精彩讲座“Transferable 简介”
接下来 我们谈谈如何利用 IntentFile 的改进功能来访问内容 我们讨论了如何使用 Transferable 将实体转换为各种类型的内容 接下来 我们看看 如何在接收端实现这项功能 我刚才展示了如何将 Activity Summary 附加到备注中 当 AppendToNote 等 AppIntent 收到 IntentFile 参数时 它会检查哪些 内容类型是可用的 然后请求所需的类型 执行这项操作时 App Intents 会使用 Transferable 表示 将实体转换为 所请求的内容类型 下面的示例将展示 AppendToNote 可能是什么样的 请注意 attachment 参数 会声明它支持的内容类型 这样一来 Siri 和“快捷指令” 就会尽可能自动进行内容转换
要访问 IntentFile 的内容 可以使用新的 API 之一 来提取内容 你可以检查 IntentFile 所代表的内容类型 然后获得相应 URL 的访问权限 以进行转化 在继续介绍之前 我们先来谈谈 另一种表示内容的方式 FileEntity API 非常适合基于文稿 的 App 或是需要管理文件的 App
我们讨论了你可以如何 借助 Transferable 将 AppEntity 转换为 文件或数据 这种方法非常适合 实体用于表示来自数据库 或服务器的对象的情况 但如果实体本身就是文件 比如文本文稿或图像 该怎么办? 在这些情况下 这个文件 就是实体的标准版本 我在另一个 App 中有 PhotoEntity 这个 PhotoEntity 表示 磁盘上的图像文件 虽然我的 App 可以理解 并在 AppIntents 中使用这个实体 比如在我的 SetFavoritePhoto 意图中 但是其他 App 无法理解我的实体 也无法在 AppIntents 中使用它 不过正如我们刚才讨论的 其他 App 可以通过 IntentFile 来理解和访问文件
通过使用 FileEntity Siri 和“快捷指令”可以实现 对其他 App 中文件的安全访问 从而能够直接访问相应的文件 例如 另一个 App 中的 RotateImageIntent 可以 安全地访问 PhotoEntity 的 支持文件 并将它旋转到适当的位置
下面的示例将展示 如何实现 FileEntity 它的实现方式很像其他 AppEntity 还有一项额外的要求是 提供受支持内容类型的列表
同时 将 ID 设为 FileEntityIdentifier
FileEntityIdentifier 可以通过 URL 创建 或者 如果暂时还不存在 作为草稿标识符的文件 FileEntityIdentifier 会使用 URL 的书签数据 因此 如果移动或重命名这个文件 实体仍然有效 我的 App 以网格形式显示了 我的 PhotoEntity 项目 我注意到 我最近添加的两个项目 显示在网格底部 但方向错了 我会使用快捷指令 来解决这个问题 对照片实体运行查询 筛选出添加日期为今天的图像 然后使用“快捷指令”中 内置的旋转操作 对查询结果应用 90 度旋转 当我运行这个快捷指令时 它能够 旋转我的 App 中的图像文件 如果回到这个 App 我们会看到它已经检测到文件更改 并更新了 UI
这些新的 API 功能非常强大 因为它们能让你的实体 对其他 App 也有意义 并让其他 App 的实体 对你的 App 有意义 从而为 Siri 和“快捷指令” 开辟了新的可能性
接下来 我们谈谈通用链接 以及如何使用 App Intent 类型来表示它们 通用链接可以帮助 用户访问你的内容 无论他们是否安装你的 App “My Trails”App 支持通过 通用链接打开特定徒步路线 下面的示例 URL 链接到特定徒步路线的详细信息 1 表示要打开的 徒步路线的标识符
现在 你可以将 AppEntity、 AppEnum 和 AppIntent 表示为 具有 URLRepresentation 这样一来 Siri 和“快捷指令” 就可以将它们视为 特定内容的链接 从而允许执行打开 URL 的操作 或者将它们标记为可共享 我希望能够通过深度链接 从“快捷指令”链接到特定徒步路线 因此 我将扩展 TrailEntity 并添加 对 URLRepresentableEntity 的支持
我将使用通用链接作为模板 提供静态 URLRepresentation
请注意 我用实体的 标识符作为插值 你可以使用实体的 ID 或任何 具有 @Property 属性的实体属性 作为 URL 字符串中的插值
现在 TrailEntity 支持 URLRepresentableEntity 我们来看看如何将这项功能与新的 URLRepresentableIntent 配合使用 创建一个遵从 OpenIntent 且目标为 TrailEntity 的 OpenTrailIntent
还要在 URLRepresentableIntent 中 添加遵从性
这样就可以了 我甚至不必实现 perform App Intents 会负责调用 我现有的 URL 处理代码
我们来看看从“快捷指令”中使用 这个 App Intent 时 会发生什么 我和女儿都热爱骑行 所以我创建了 一个快捷指令来查找某地附近的路线 并为我们随机挑选一条路线供骑行 但是这个快捷指令现在 只能显示路线的名称 要是它能直接带我前往我的 App 中 相应的路线 那就更棒了 因此 我要添加 OpenTrailIntent
我要添加 Open Trail 操作 来替换 Show Result 操作
现在 当我运行这个快捷指令时 会使用 TrailEntity 的 URL 表示 直接深度链接到路线详细信息 还有一种将 URL 与 App Intents 配合使用的方法 是从 perform 返回 新的 OpenURLIntent 当 Siri 和“快捷指令” 执行你的 AppIntent 时 可以打开提供的 URL 链接到相关内容
或者 如果我有一个 “CreateTrail”AppIntent 则可以使用新创建的 TrailEntity 来初始化 OpenURLIntent 从而让“快捷指令”能够打开 App 并直接导航到 新创建的 Trail
通过采用 URLRepresentable 可以轻松提供 适用于 AppIntent 类型的通用链接 从而重复使用现有的 URL 处理代码 并方便用户访问你的内容 今年 我们还将为开发者体验 带来一些改进 让创建 AppIntents 变得更轻松 接下来 我们来讨论一种新的参数类型 以及对 AppIntents 定义方式 和重复使用方式的一些改进
首先来看 UnionValue 有时 你的某个参数或属性 可以用一组类型中的 一个类型来表示 我的 Buy Day Pass AppIntent 可以接受 TrailEntity 但是我希望能够选择 购买一条路线或整个公园的 单日门票 我会使用新的 UnionValue 宏来实现这项功能
首先 创建一个枚举 并定义两个购买选项 一个接受 ParkEntity 另一个接受 TrailEntity
然后将新的 UnionValue 宏 添加到枚举中
现在 我可以更新参数以使用 新的 Day Pass Type 枚举
在 perform 方法中 我可以 对 passType 参数使用开关 就像任何其他枚举一样
务必要注意 枚举中的每个 case 都必须有且仅有一个关联值
没有关联值的 case 是无效的
而且每个关联值必须各不相同 例如已有一个 case 与 TrailEntity 关联 则无法添加另一个这样的 case 如果你想接受现有的类型 请使用 UnionValue 可以把它视为“or”参数
如果你之前使用过 AppIntents 你可能已经注意到 我的一些 AppIntent 示例 在 @Parameter 属性中 缺少标题 使用 Xcode 16.0 进行构建时 无需再为 AppEntity Properties 或 AppIntent Parameters 提供标题
因此我的 SuggestedTrails 意图 可以从这么长
精简成这么短 Xcode 会根据 struct 属性的名称 智能地为你生成 标题字符串
但对于 TrailCollection 我希望标题显示为 “Featured Collection”
因此 我会像以前一样 手动指定标题
最后 我们改进了 AppIntents 在框架中的使用方式 以前 所有 App Intent 类型 都必须位于同一个模块中 你无法让 App 中的 AppIntent 使用在某一个框架中 定义的 AppEntity AppIntent 也必须位于框架中 在 Xcode 16 中 这一限制不复存在 你可以 在框架中定义 App 实体 然后在你的 App 和扩展目标中引用它们
目前仅支持框架 不支持框架之外的库
以上只是 AppIntents 的 部分新功能和改进功能 要深入了解 请查看 AppIntents 文档
温馨提醒 请暂时关闭 2 倍速播放 下面我们来总结一下今天的内容 将 App 实体索引到“聚焦” 可以帮助 Siri 查找和理解 它以前无法查找和理解的内容 为你的 App 实体提供 有意义的表示 可以让其他 App 也能理解你的内容 欢迎试用 URLRepresentable 以及 我们面向开发者新推出的改进功能 然后与我们分享你的看法 AppIntents 正在为设备上的 许多其他功能提供支持 建议大家观看其他精彩视频 了解利用 AppIntents 实现的 另外一些精彩功能
我们迫不及待想要看到大家 充分利用 App Intents 来优化 App 谢谢观看
-
-
正在查找特定内容?在上方输入一个主题,就能直接跳转到相应的精彩内容。
提交你查询的内容时出现错误。请检查互联网连接,然后再试一次。