[英]Is it possible to dynamicly update / change they layout (e.g. number of views) in an iOS 14 Widget?
I am working on my very first iOS 14 widget.我正在开发我的第一个 iOS 14 小部件。 I know that widgets are mostly static and cannot show dynamic content like animations or.
我知道小部件大多是静态的,不能显示动态内容,如动画或。 But is it possible to change the layout of / number of views in a widget?
但是是否可以更改小部件中视图的布局/数量?
Since I am new to SwiftUI I don't see any way to change the view content.由于我是 SwiftUI 的新手,我看不到任何更改视图内容的方法。
Context:语境:
Assume an ToDo app where the widget should show the buttons/links for up to 5 entries.假设有一个 ToDo 应用程序,其中小部件应显示最多 5 个条目的按钮/链接。 However, if there are currently only 3 entries in the app, the widget should of course show only 3 links.
但是,如果应用程序中当前只有 3 个条目,那么小部件当然应该只显示 3 个链接。
The app already offers a Today Widget.该应用程序已经提供了今日小工具。 Here I have solved the problem by simply adding controls (buttons) for fixed number of entries (eg 5) to the widget view.
在这里,我通过简单地将固定数量的条目(例如 5 个)的控件(按钮)添加到小部件视图来解决了这个问题。 If less entries should be shown, the unused controls are simply hidden when the widget updates its view.
如果应该显示较少的条目,则当小部件更新其视图时,未使用的控件将被简单地隐藏。
Creating a widget view with a fixed number of entries (links) in SwiftUI is no problem.在 SwiftUI 中使用固定数量的条目(链接)创建小部件视图是没有问题的。 But how do I hide/remove the unused views?
但是如何隐藏/删除未使用的视图?
In SwiftUI the view is a some View
variable I don't see a way to dynamically change its content:在 SwiftUI 中,视图是
some View
变量,我看不到动态更改其内容的方法:
struct MyEntryView: View {
var body: some View {
Hstrack {
// Item 1
// Item 2
...
// Item n
}
}
}
Widget views are static but they are redrawn whenever a new entry is passed to them.小部件视图是静态的,但只要有新条目传递给它们,它们就会重绘。
It is not possible to create a Widget view which will update itself when the collection changes.不可能创建一个 Widget 视图,它会在集合更改时自行更新。
You can either:您可以:
In both cases you need to create an Entry:在这两种情况下,您都需要创建一个条目:
struct SimpleEntry: TimelineEntry {
let date: Date
let items: [String]
}
and display its items in a view:并在视图中显示其项目:
struct SimpleWidgetEntryView: View {
var entry: SimpleProvider.Entry
var body: some View {
VStack {
ForEach(entry.items, id: \.self) {
Text($0)
}
}
}
}
The only difference is how you create Entries:唯一的区别是您创建条目的方式:
You can:你可以:
items
may vary):items
大小可能会有所不同):func getTimeline(in context: Context, completion: @escaping (Timeline<SimpleEntry>) -> Void) {
var entries = [SimpleEntry]()
let currentDate = Date()
for offset in 0 ..< 5 {
let entryDate = Calendar.current.date(byAdding: .minute, value: offset, to: currentDate)!
entries.append(SimpleEntry(date: entryDate, items: Array(repeating: "Test", count: offset + 1)))
}
let timeline = Timeline(entries: entries, policy: .atEnd)
completion(timeline)
}
WidgetCenter.shared.reloadAllTimelines()
(There likely is a limit to how often you can reload the timeline). (重新加载时间线的频率可能有限制)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.