大多数浏览器和
Developer App 均支持流媒体播放。
-
将实时活动功能引入 Apple Watch
从 iPadOS 18 和 watchOS 11 开始,将实时活动引入 Apple Watch 上的智能叠放。我们将介绍实时活动会如何显示在 Apple Watch 上,以及如何提升实时活动在智能叠放中的显示效果。我们还将探索一些其他注意事项,以确保 Apple Watch 上的实时活动能够始终显示最新的信息。
章节
- 0:00 - Introduction
- 1:07 - Review your Live Activity
- 3:22 - Customize for Apple Watch
- 6:02 - Keep it live
资源
-
下载
大家好 我叫 Anne 是一名框架工程师 从事 watchOS 的开发 很高兴能为大家介绍 如何让现有的 iOS 实时活动 在 Apple Watch 上提供出色体验 通过实时活动 你可以 在多个一目了然的位置 比如锁定屏幕、待机显示和灵动岛 显示有关你的 App 的 活动或事件的最新信息 现在 在 iOS 18 和 watchOS 11 中 iOS 实时活动会自动显示在 Apple Watch 上的智能叠放中 首先谈谈更新到 watchOS 11 后 实时活动在 Apple Watch 上的 显示方式
然后 我将介绍如何为智能叠放 自定实时活动视图 我还将详细介绍一下 watchOS 的活动更新 以及如何让实时活动 保持最新状态
我们首先来了解一下现有的 iOS 实时活动在运行 watchOS 11 的 Apple Watch 上如何显示
对于带有灵动岛的 iPhone 在手机保持锁定屏幕状态时 实时活动会转为在灵动岛中 显示紧凑的前边缘视图 和后边缘视图 灵动岛中的视图 来自“compact leading” 和“compact trailing”视图构建器 在 Apple Watch 上 同样的视图 会自动显示在智能叠放中 一同显示的还有一个标题 说明这些视图由你的 App 提供 不妨借着这次绝佳的机会 思考一下你的紧凑视图 是否充分利用了可用空间 来帮助用户及时获取最新信息 在这里 我的 App 在前边缘视图中 显示的是预计多久送达 并在后边缘视图中显示订单当前状态
iOS 上实时活动的更新 会自动发送到 Apple Watch 在 iOS 上 提醒更新 会以动画效果显示 灵动岛扩展视图 在 Apple Watch 上收到提醒更新时 如果提醒目前位于表盘上 则系统会自动启动智能叠放 显示提醒 然后显示实时活动
如果某个 App 位于前台 则屏幕底部会显示一个横幅 同时显示灵动岛紧凑视图
轻点实时活动可全屏显示 并提供 在 iPhone 上打开 App 的选项
iOS 实时活动的灵动岛紧凑视图 将自动显示在智能叠放中 查看一下当前的视图 确保显示动态更新的信息 以便让用户及时了解活动的状态 这项更新功能的受益者包括已更新到 iOS 18 和 watchOS 11 的用户 以及你的现有 iPhone 顾客
到目前为止 我已经介绍了用户 更新到 iOS 18 和 watchOS 11 之后 会自动经历哪些事情 此外 你还有机会 为 Apple Watch 提供 自定实时活动视图 我的 App 为用户提供本地农产品 订购送货上门服务 用户可以通过实时活动 查看订单配送状态 我们来修改这个实时活动 以自定 用于 Apple Watch 的实时活动视图
我的实时活动目前在智能叠放中 采用默认显示方式 显示紧凑的灵动岛视图 可以在 Xcode 中通过预览 查看显示效果
在 Canvas Device Settings 中 选择 All Variants 后 可以在 Canvas 中一并查看 所有视图样式 或者 也可以进入 Select 模式并将 Canvas Device Settings 更新为 显示 Content Smart Stack 以便专注于我的智能叠放视图
为了针对 watchOS 智能叠放 进行自定 我要为我的实时活动 在 WidgetConfiguration 中添加 supplementalActivityFamilies 修饰符 我将使用 .small 来 表明支持智能叠放 现在 智能叠放中会显示 来自活动内容的 iOS 锁定屏幕视图 而不是紧凑视图 由于我采用了适用于较大视图的 锁定屏幕内容设计 因此在 Apple Watch 上 文本会被截断 我要针对智能叠放进行自定
我将获取 activityFamily 环境值 然后在 activityFamily 为 small 时 为我的内容提供新的布局
当 activityFamily 为 medium 时 对于 iOS 锁定屏幕 将使用原始内容视图布局
我可以对实时活动 使用 Xcode 预览 来预览我的视图 在智能叠放中的显示效果
通过添加 supplementalActivityFamilies 修饰符 我的实时活动现在可以 在 Apple Watch 上显示自定视图
即使你没有安装“Watch”App 实时活动也适用于 Apple Watch 但如果你安装了“Watch”App 也可以通过 轻点智能叠放中的实时活动 选择打开“Watch”App
在“Watch”App 目标的 Build Settings 中 为 Info.plist 部分中的 Supports Launch for Live Activity Attribute Types 键 添加一个值 要想为你的所有实时活动 启动“Watch”App 请将这个值留空 要想只为特定的实时活动启动 请为每个应该启动“Watch”App 的 ActivityAttributes 遵从类型 添加一个项目
只需编写几行代码 我已经能够更新 实时活动的显示方式了 还能预览显示效果 在 Apple Watch 上 为了确保 实时活动显示尽可能最新的信息 并按照你设想的方式发挥作用 你还应该了解 一些其他的事项 我要介绍一下更新频率和预算、 如何处理连接受限的问题 以及如何针对全天候显示模式 调整实时活动视图
iPhone 和 Apple Watch 在更新频率和预算方面 存在一些差异
实时活动更新会 自动同步到 Apple Watch 你不必管理单独的推送令牌 也不必添加任何代码 为了避免影响电池续航时间 对更新同步设置了预算 预算阈值与 iOS 类似 如果现在将推送更新用于实时活动 这些更新应该会在 Apple Watch 的 预算范围内 并且无需额外的操作 Apple Watch 还支持 在需要时提供高频更新
在 iOS App 中 请考虑 实时活动通过 ActivityKit 在本地更新的情况 现在 这些更新还会 同步到 Apple Watch 并计入设备更新预算 如果更新超出预算 则可能不会在用户垂下手腕时 立即显示出来 但是 当用户抬起手腕时 实时活动就会显示 可用的最新信息
可能导致 Apple Watch 不及时接收活动更新的另一个原因 是连接状态 如果 Apple Watch 与附近 搭配使用的 iPhone 连接良好 或者位于同一无线局域网中 则更新一般会发送到 Apple Watch 在连接受限的情况下 会在 Apple Watch 上优先显示 开始、结束和提醒更新
系统会通过在智能叠放中 显示一条有关上次连接的信息 让用户知道自己可能 无法看到最新信息 还可以思考一下你的活动可能需要 针对全天候显示模式进行哪些调整 当手表处于全天候显示模式时 如果用户手腕下垂 系统会自动将配色方案切换到深色 并降低亮度
如果视图颜色鲜艳 可以使用 isLuminanceReduced 环境值来移除鲜艳的元素 或降低其亮度
在我的视图中 我要让仪表 在亮度降低后换一个色调 从而在降低亮度的同时仍然便于阅读
如果你希望实时活动具有浅色外观 可以将 preferredColorScheme 设置为 light 在全天候模式下 实时活动 会自动采用深色外观 并降低亮度 诸如 primary 之类的语义色会 根据配色方案 自动采用相应的颜色 现在 我的活动视觉效果很棒 并且始终尽可能显示 最佳信息
从 iOS 18 和 watchOS 11 开始 iOS 实时活动会自动显示在 Apple Watch 上的智能叠放中 确保灵动岛紧凑视图 显示及时、相关且丰富的信息 使用 supplementalActivityFamilies 为 Apple Watch 自定实时活动 如需进一步了解出色的实时活动设计 请观看视频 “为 Apple Watch 设计实时活动” 如果你没有 watchOS 开发经验 那么实时活动可能会成为 你针对 watchOS 自定 App 内容的 首次尝试 我们很高兴大家能够 加入我们这个平台 我们也希望大家进一步探索 让你们的 App 也能登陆 Apple Watch 谢谢
-
-
1:28 - Existing Live Activity views
struct DeliveryLiveActivity: Widget { var body: some WidgetConfiguration { ActivityConfiguration( for: DeliveryActivityAttributes.self ) { context in DeliveryActivityContent(context: context) } dynamicIsland: { context in DynamicIsland { DynamicIslandExpandedRegion(.leading) { DeliveryExpandedLeadingView(context: context) } DynamicIslandExpandedRegion(.trailing) { DeliveryExpandedTrailingView(context: context) } DynamicIslandExpandedRegion(.bottom) { DeliveryExpandedBottomView(context: context) } } compactLeading: { DeliveryCompactLeading(context: context) } compactTrailing: { DeliveryCompactTrailing(context: context) } minimal: { DeliveryMinimal(context: context) } } } }
-
3:43 - Preview Live Activities with Xcode Previews
extension DeliveryActivityAttributes.ContentState { static var shippedOrder: DeliveryActivityAttributes.ContentState { .init( status: .shipped, courierName: "Johnny" ) } static var packedOrder: DeliveryActivityAttributes.ContentState { .init( status: .packed, courierName: "Contacting Courier...") } } #Preview( "Dynamic Island Compact", as: .dynamicIsland(.compact), using: DeliveryActivityAttributes.preview ) { DeliveryLiveActivity() } contentStates: { DeliveryActivityAttributes.ContentState.packedOrder DeliveryActivityAttributes.ContentState.shippedOrder }
-
4:15 - Add .supplementalActivityFamilies to indicate support for the Smart Stack
struct DeliveryLiveActivity: Widget { var body: some WidgetConfiguration { ActivityConfiguration( for: DeliveryActivityAttributes.self ) { context in DeliveryActivityContent(context: context) } dynamicIsland: { context in DynamicIsland { DynamicIslandExpandedRegion(.leading) { DeliveryExpandedLeadingView(context: context) } DynamicIslandExpandedRegion(.trailing) { DeliveryExpandedTrailingView(context: context) } DynamicIslandExpandedRegion(.bottom) { DeliveryExpandedBottomView(context: context) } } compactLeading: { DeliveryCompactLeading(context: context) } compactTrailing: { DeliveryCompactTrailing(context: context) } minimal: { DeliveryMinimal(context: context) } } .supplementalActivityFamilies([.small]) } }
-
4:49 - Customize view layout for the small activity family
struct DeliveryActivityContent: View { @Environment(\.activityFamily) var activityFamily var context: ActivityViewContext<DeliveryActivityAttributes> var body: some View { switch activityFamily { case .small: DeliverySmallContent(context: context) case .medium: DeliveryMediumContent(context: context) @unknown default: DeliveryMediumContent(context: context) } } }
-
5:06 - Preview customized layouts for the Smart Stack
#Preview("Content", as: .content, using: DeliveryActivityAttributes.preview) { DeliveryLiveActivity() } contentStates: { DeliveryActivityAttributes.ContentState.packedOrder DeliveryActivityAttributes.ContentState.shippedOrder }
-
8:37 - Use isLuminanceReduced to remove bright elements with Always On Display
struct DeliveryGauge: View { @Environment(\.isLuminanceReduced) private var isLuminanceReduced var context: ActivityViewContext<DeliveryActivityAttributes> var body: some View { Gauge(value: context.state.progressPercent) { GaugeLabel(context: context) } .tint(isLuminanceReduced ? .gaugeDim : .gauge) } }
-
8:57 - For Live Activities with a light appearance, use a light preferredColorScheme
struct DeliveryActivityContent: View { @Environment(\.activityFamily) var activityFamily var context: ActivityViewContext<DeliveryActivityAttributes> var body: some View { switch activityFamily { case .small: DeliverySmallContent(context: context) .preferredColorScheme(.light) case .medium: DeliveryMediumContent(context: context) @unknown default: DeliveryMediumContent(context: context) } } }
-
-
正在查找特定内容?在上方输入一个主题,就能直接跳转到相应的精彩内容。
提交你查询的内容时出现错误。请检查互联网连接,然后再试一次。