Widget小组件

目录

技能点

Widget背调

a. 设计定位

b. Widget小组件限制

c. Widget小组件 开发须知

d. 什么是 SwiftUI

App Group 数据共享

a. 配置 App Groups

1、开发者账号配置,并更新pp证书

2、Xcode配置

b. 缓存数据共享-代码实现

1、文件存储

2. 沙盒存储(参考WidgetGroupTool类)

c. pod共享

d. 文件共享(详见WidgetGroupTool)

Widget小组件配置

a. 添加Widget

b. 编写Widget

c. 多Widget组件实现

d. 登录及授权

e. 拉起app

f. 埋点

g. 可配置的Widget组件(详见WidgetStudy项目)

h. 动态项配置(容易出错)

i. 配置页面颜色设置

项目应用示例​​​​​​​

技能点

SwiftUI语言

Widget小组件配置

App组之间的数据共享

Widget背调

a. 设计定位

用户可以通过 Widget 对主屏幕进行个性化定制,但是 iOS 14 的 Widget 跟其他系统上的小组件有很大的区别。在 Widget 的设计上苹果也保持了一贯的克制,定位于轻量化、仅用作关键信息的展示。比如系统自带 Widget 中的股票、天气、电量、运动信息,他们的共同特征是更新频率高、提供的信息重要,让用户不用打开 app 就可以浏览关心的内容。苹果也不希望开发者将 Widget 仅仅当作 app 的一个快捷入口,这样的需求更适合用 contextual menu 来实现。

我们想给经销商app的增加多元的入口体验,于是就有了这个需求。

b. Widget小组件限制

苹果基于上面的设计定位,同时也为了节省系统资源保证续航,对 Widget 的做了一些限制:

1、不支持动画,仅支持静态页面展示

2、更新频率由系统通过机器学习来动态分配

3、不支持拖拽、滚动等复杂的交互,不支持 Switch 等控件

c. Widget小组件 开发须知

1、只能使用SwiftUI进行开发,所以需要SwiftUI和Swift基础

2、Widget只支持3种尺寸systemSmall(2x2)、 systemMedium(4x2)、 systemLarge(4x4)

3、默认点击Widget打开主应用程序

4、需要在项目中进行App Groups的设置才能使其与主程序互通数据 

官方设计文档: Widgets - System experiences - Components - Human Interface Guidelines - Design - Apple Developer

d. 什么是 SwiftUI

SwiftUI 于 2019 年度 WWDC 全球开发者大会上发布,它是基于 Swift 建立的声明式框架。该框架可以用于 watchOS、tvOS、macOS、iOS 等平台的应用开发,等于说统一了苹果生态圈的开发工具。

对于 Swift UI,官方的定义很好找到,也写得非常明确:

SwiftUI is a user interface toolkit that lets us design apps in a declarative way.
可以理解为 SwiftUI 就是⼀种描述式的构建 UI 的⽅式。

SwiftUI官方教程:Apple Developer Documentation

App Group 数据共享

Widget小组件属于一个独立的app,它有着和主项目完全不同的bundleId。

Widget小组件中接口请求需要与主项目相同的账号、dealerId、token等信息,于是就需要从一个app中读取另一个app的信息,但是这是不被苹果允许的,所以就有了APP group的概念,可以将同一个开发者账号下的app数据放到同一个缓存组中,这样这些app就可以共享这些信息。

a. 配置 App Groups

1、开发者账号配置,并更新pp证书

 I. 创建两个APP,并且在Apple Developer中创建两个APP的id创建APPid时,在APP Groups复选框打上对钩,当我们配置完成App ID之后,会发现App Groups是Configurable状态,这是因为咱们还没有配置相应的app groups,别着急,咱们等会再来管它。

II. 在id那一组中又一个App Groups选项,我们新创建一个APP Groups,这里一共有两个选项,第一个是我们这个app group的描述,第二个是我们app group的id。这个id默认是要group.打头,并且是不能去掉的。

III. 现在去配置新创建的两个APP ID,因为再创建的时候勾选了APP Groups,但是并没有配置它,所以它回事黄色的状态,现在点击Edit,进入之后选择新创举的groups。

IV. 点击Edit---勾选上刚创建好的App Group----配置完成,在返回来看一下咱们的App ID,完美~Enabled状态了.

2Xcode配置

主项目和Widget Extension添加App Groups

Capabilities->App Groups

当我们配置完以后,会在文件目录下多出来一个.entitlements的文件

b. 缓存数据共享-代码实现

1、文件存储

主项目写入数据

widget读取数据

2. 沙盒存储(参考WidgetGroupTool类)

写入数据

I. 传统方法 

II. 新方法  (swift属性包装器)

读取数据  

c. pod共享

​​​​​​​

d. 文件共享(详见WidgetGroupTool

Widget小组件配置

a. 添加Widget

File -> New -> Target -> Widget Extension

Include Configuration Intent如果你所创建的Widget需要支持用户自定义配置属性,则需要勾选这个(例如天气组件,用户可以选择城市;记事本组件,用户记录信息等),不支持的话则不用勾选

会生成一个新文件夹,包含以下内容

  • 扩展名.swift
  •  扩展名.intentdefinition(勾选Include Configuration Intent)
  • Assets.xcassets
  • Info.plist

b. 编写Widget

1、原理:开发者通过 SwiftUI 构建 Views,定义Timelines为 Views 提供对应时间所需的数据,当数据变化时,通过reload更新数据。TimelineProvider提供一组TimelineEntry和ReloadPolicy,用来后续刷新页面。

2、实现 Widget 的代码相对比较模版,可以从 Widget 的入口开始,缺什么补什么。

I. 入口:@main

  •  @main:代表着Widget的主入口,系统从这里加载,可用于多Widget实现
  •  kind:字符串,唯一标识 Widget。
  • WidgetConfiguration:有两类配置,分别为
    •  StaticConfiguration : 可以在不需要用户任何输入的情况下自行解析,可以在 Widget 的 App 中获取相关数据并发送给 Widget。
    •  IntentConfiguration:依赖于 App 的 Siri Intent,会自动接收这些 Intent 并用于更新 Widget,用于构建动态 Widget。
  • .supportedFamilies:支持不同尺寸。
  •  description:添加编辑界面展示的描述内容
  • configurationDisplayName:添加编辑界面展示的标题

II. Entry

渲染 Widget 所需的数据模型,需要遵守TimelineEntry协议。

III. Provider

遵守TimelineProvider协议,告诉 WidgetKit 何时渲染与刷新 Widget。需要实现以下 3 个方法

placeholdergetSnapshotgetTimeline

  1.  getTimeline 是最重要的方法,后面的数据刷新都会在其中完成,所以可能会在其中完成最新的网络数据和本地数据的获取,然后转成 Model 以供使用。
  2.  getTimeline 的方法里有一个 policy 参数,表示刷新的时机,可以选择.never(不刷新),.atEnd(Entry 显示完毕之后自动刷新) 或 .after(date)(到达某个特定时间后自动刷新)。
  3.  Widget 刷新的时间由系统统一决定(有时候设置了也不会自己刷新),如果需要强制刷新 Widget,可以在 App 中使用 WidgetCenter 来重新加载所有时间线:WidgetCenter.shared.reloadAllTimelines()

IV. EntryView

屏幕上 Widget 显示的内容,可以针对不同尺寸的 Widget 设置不同的 View。

  1.  Widget 能且只能使用 SwiftUI 构建界面。
  2.  Widget 本质:一个随着时间线而更新的 SwiftUI View。

c. 多Widget组件实现

一个Widget只能实现大中小三个不同尺寸的组件形式,如果现有需求要做不同功能并且相同尺寸规格的组件则需要实现多组件。

通过修改原Widget入口文件方法添加更多配置来支持多个Widget

每个bundle body子属性上限为5个

d. 登录及授权

加载数据之前首先要解决的是授权问题。

1、主 app 在登录后将 token 等数据写入 app group 中

2、Widget 通过 HTTPS 接口加上 token 来访问用户数据。其中 token 通过 UserDefaults 来共享到 Widget,因为开发过程中不同的证书打包的 bundle id 不同,因此我们将 group name 设置成 group.[bundle id] 的形式,保证能正确读取 token。

Token 的同步有几个时机:

  1.  App 启动后,更新token
  2.  登录成功,更新token
  3.  退出登录时,删除 token

e. 拉起app

苹果提供了两种 API 给到开发者,第一种是SwiftUI 的 WidgetURL API,它的可点击区域是在整个widget页面。

对于 systemSmall 类型来说,只支持 widgetURL 的方式,但是对于 systemMedium 和 systemLarge 还可以使用 SwiftUI Link API,而 Link 的可点击区域是这样的: 

f. 埋点

Widget 的曝光事件我们是无法感知的,由于点击 Widget 会直接跳转到主 app,所以我们可以在跳转到主 app 的 URL 上增加埋点参数,主 app 解析 URL 中的参数来埋点。

触发网络请求的时候,也可以考虑添加埋点。

g. 可配置的Widget组件(详见WidgetStudy项目)

前面我们所介绍的构建小组件的方式,虽然可以通过时间线做部分更新逻辑,但对用户来说,依然是静态的。用户不能够根据自己的偏好对组件进行配置,还以天气类组件为例,有些用户可能关心的是空气质量,湿度等信息,有些用户可能只关心阴天雨天的信息,由于小组件的显示空间有限,有时候你无法将所有的信息都展示在组件内,因此让用户选择他感兴趣的信息进行小组件的配置非常重要。

首先,如果要让我们开发的Widget可以支持用户配置,需要在Widget的target工程中添加一个配置属性表文件,使用Xcode新建一个SiriKit Intent Definition File的文件,如下图所示:

之后,需要创建一个新的Intent配置,添加一系列的用户配置项,系统提供了各种类型的配置项,如让用户传入字符串信息的配置项,开关配置项,日期配置项等等,如下图所示:

重新运行Widget,我们的小组件就已支持用户配置功能,用户可以编辑小组件进行设置,当用户修改了配置项后,组件会重新请求Timeline时间线,在timeline回调方法中,会传入configuration对象,用来存储用户的配置信息

(添加枚举属性,修改display name)

需要注意以下几点:

  •  Intent 的 Category 选择为 View(即用于展示/配置 UI)
  •  选中 Intent is eligible for widgets
  •  取消选中 Siri can ask value for run(除非该 Intent 也用于 Siri Shortcuts)

同时需要修改Provider,改为遵循IntentTimelineProvider(详见Widget2)

h. 动态项配置(容易出错)

上面演示的这种配置方式,适用于当配置项固定的场景,更多时候,可能连配置项都是动态的,比如我们的应用会根据服务端的状态来提供不同的服务,这时可提供给用户开启的服务项目就是动态的。Widget的配置项也支持动态进行配置,这需要使用到Intents Extension的相关功能,下图为动态项配置

添加Intents Extension官方文档

IntentHandler类遵循对应的IntentHandling协议,并实现provideCardOptionsCollection,defaultCard协议方法

  •  provideCardOptionsCollection(for:with:)在用户点击 Widget 中 Card 配置项的时候,WidgetKit 会展示上图右侧中的列表 UI,其中的数据由这个方法异步返回。
  •  defaultCard(for:)我们可以通过实现该方法,在用户首次添加我们的 Widget 时,对于该 Widget 的某一个可配置项返回一个默认的参数值。例如在图示的实现中,我们返回了用户的主要信用卡(Primary Card)。

Tips:

  •  通过使用 INObjectCollection(sections:) 构造器,传入 INObjectSection 数组,可以分区展示待选项列表。
  •  自定义 Intent 类型继承自 INObject,通过重载/设置 displayString、 subtitleString 等属性,可以定制自定义类型在待选项列表中的显示内容。
  •  Intent Handling 协议中定义的 defaultXXX(for:) 方法被标记为 optional,但是依然推荐实现,因为一个好的默认视图对我们的 Widget 来说是十分重要的。

你可能注意到了待选项列表上方的搜索框。默认情况下,搜索框会对我们所返回的全部内容进行搜索过滤。但是,当待选数据较多,或者说待选数据取决于用户具体输入时,我们可以打开 Intent handler provides search results as the user types 选项,实现对待选项列表的实时更新。

在打开该选项后,Xcode 会为生成的 IntentHandling 协议的 provideCardOptionsCollection(for:with:) 方法添加一个 searchTerm 参数:

当用户在搜索框中输入字符时,WidgetKit 会调用该方法对待选项列表进行更新。首次显示待选项列表时,该参数值为 nil。

i. 配置页面颜色设置

背景色设置

文本按钮颜色配置

项目应用示例

上图为小组件的示例图

上图为添加小组件的步骤演示

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
【课程特点】1、231节大容量课程:包含了SwiftUI的大部分知识点,详细讲解SwiftUI的方方面面;2、15个超级精彩的实例:包含美食、理财、健身、教育、电子商务等各行业的App实例;3、创新的教学模式:手把手教您SwiftUI用户界面开发技术,一看就懂,一学就会;4、贴心的操作提示:让您的眼睛始终处于操作的焦点位置,不用再满屏找光标;5、语言简洁精练:瞄准问题的核心所在,减少对思维的干扰,并节省您宝贵的时间;6、视频短小精悍:即方便于您的学习和记忆,也方便日后对功能的检索;7、齐全的学习资料:提供所有课程的源码,在Xcode 11 + iOS 13环境下测试通过; 更好的应用,更少的代码!SwiftUI是苹果主推的下一代用户界面搭建技术,具有声明式语法、实时生成界面预览等特性,可以为苹果手机、苹果平板、苹果电脑、苹果电视、苹果手表五个平台搭建统一的用户界面。SwiftUI是一种创新、简单的iOS开发中的界面布局方案,可以通过Swift语言的强大功能,在所有的Apple平台上快速构建用户界面。 仅使用一组工具和API为任何Apple设备构建用户界面。SwiftUI具有易于阅读和自然编写的声明式Swift语法,可与新的Xcode设计工具无缝协作,使您的代码和设计**同步。自动支持动态类型、暗黑模式、本地化和可访问性,意味着您的**行SwiftUI代码已经是您编写过的非常强大的UI代码了。 

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值