我知道我们可以像这样在垂直SwiftUI中创建一个List,
struct ContentView : View { var body: some View { NavigationView { List { Text("Hello") } } } }
但是我们有没有办法把列表分成2个或3个,或者更多的跨度,像在UICollectionView中那样覆盖屏幕
UICollectionView
wqsoz72f1#
checkout 基于ZStack的示例here
Grid(0...100) { _ in Rectangle() .foregroundColor(.blue) }
k7fdbhmy2#
您可以使用两个新的本机View:
View
LazyHGrid
LazyVGrid
使用代码或直接从库中:
该库包含一个完全工作的示例代码,您可以自己测试。
4uqofj5v3#
你可以像这样创建你的customView来实现UICollectionView行为:
struct ContentView : View { var body: some View { VStack(alignment: .leading, spacing: 10) { ScrollView(showsHorizontalIndicator: true) { HStack { ForEach(0...10) {_ in GridView() } } } List { ForEach(0...5) {_ in ListView() } } Spacer() } } } struct ListView : View { var body: some View { Text(/*@START_MENU_TOKEN@*/"Hello World!"/*@END_MENU_TOKEN@*/) .color(.red) } } struct GridView : View { var body: some View { VStack(alignment: .leading, spacing: 10) { Image("marker") .renderingMode(.original) .cornerRadius(5) .frame(height: 200) .border(Color.red) Text("test") } } }
8e2ybdfx4#
适用于Xcode 12上的iOS/iPadOS 14。您可以使用LazyVGrid将用户看到的内容加载到屏幕上,而不是整个列表,List默认为lazy。
import SwiftUI //MARK: - Adaptive struct ContentView: View { var body: some View { ScrollView { LazyVGrid(columns: [GridItem(.adaptive(minimum:100))]) { ForEach(yourObjects) { object in YourObjectView(item: object) } } } } } //MARK: - Custom Columns struct ContentView: View { var body: some View { ScrollView { LazyVGrid(columns: Array(repeating: GridItem(), count: 4)) { ForEach(yourObjects) { object in YourObjectView(item: object) } } } } }
不要忘记将infoobjects替换为您的info,将YourObjectView替换为您的customView。
dfddblmv5#
🔴 SwiftUI的LazyVGrid和LazyHGrid为我们提供了相当灵活的网格布局。最简单的网格是由三件事组成的:您的原始数据,描述您想要的布局的GridItem数组,以及将数据和布局结合在一起的LazyVGrid或LazyHGrid。例如,这将使用大小为80点的单元格创建垂直网格布局:
struct ContentView: View { let data = (1...100).map { "Item \($0)" } let columns = [ GridItem(.adaptive(minimum: 80)) ] var body: some View { ScrollView { LazyVGrid(columns: columns, spacing: 20) { ForEach(data, id: \.self) { item in Text(item) } } .padding(.horizontal) } .frame(maxHeight: 300) } }
🔴 使用GridItem(.adaptive(最小值:80))意味着我们希望网格每行容纳尽可能多的项目,每个项目的最小大小为80个点。如果你想控制列的数量,你可以使用.flexible(),它也可以让你指定每个项目应该有多大,但现在可以让你控制有多少列。例如,这将创建五列:
struct ContentView: View { let data = (1...100).map { "Item \($0)" } let columns = [ GridItem(.flexible()), GridItem(.flexible()), GridItem(.flexible()), GridItem(.flexible()), GridItem(.flexible()) ] var body: some View { ScrollView { LazyVGrid(columns: columns, spacing: 20) { ForEach(data, id: \.self) { item in Text(item) } } .padding(.horizontal) } .frame(maxHeight: 300) } }
🔴 第三种选择是使用固定尺寸。例如,这将使第一列正好是100点宽,并允许第二列填满所有剩余的空间:
struct ContentView: View { let data = (1...100).map { "Item \($0)" } let columns = [ GridItem(.fixed(100)), GridItem(.flexible()), ] var body: some View { ScrollView { LazyVGrid(columns: columns, spacing: 20) { ForEach(data, id: \.self) { item in Text(item) } } .padding(.horizontal) } .frame(maxHeight: 300) } }
🔴 您也可以使用LazyHGrid来创建一个水平滚动的网格,它的工作方式基本相同,只是它在其初始化器中接受行。例如,我们可以创建10个并排的标题图像,它们像这样水平滚动:
struct ContentView: View { let items = 1...50 let rows = [ GridItem(.fixed(50)), GridItem(.fixed(50)) ] var body: some View { ScrollView(.horizontal) { LazyHGrid(rows: rows, alignment: .center) { ForEach(items, id: \.self) { item in Image(systemName: "\(item).circle.fill") .font(.largeTitle) } } .frame(height: 150) } } }
🔴 正如您所看到的,创建水平和垂直网格所需的代码几乎相同,只是将行改为列。如果您需要支持iOS 13,您将无法访问LazyHGrid或LazyVGrid,因此请阅读下面的替代方案。SwiftUI为我们提供了用于垂直布局的VStack和用于水平布局的HStack,但没有任何东西可以同时做到这两点-没有任何东西可以在网格结构中布局视图。幸运的是,我们可以通过利用SwiftUI的视图构建器系统自己编写一个。这意味着编写一个必须使用行和列计数创建的类型,以及一个闭包,它可以运行以检索网格中给定单元格的视图。然后,在主体内部,它可以循环遍历所有行和列,并在VStack和HStack中创建单元格,以创建网格,每次调用视图闭包来询问单元格中应该有什么。在代码中,它看起来像这样:
struct GridStack<Content: View>: View { let rows: Int let columns: Int let content: (Int, Int) -> Content var body: some View { VStack { ForEach(0 ..< rows, id: \.self) { row in HStack { ForEach(0 ..< columns, id: \.self) { column in content(row, column) } } } } } init(rows: Int, columns: Int, @ViewBuilder content: @escaping (Int, Int) -> Content) { self.rows = rows self.columns = columns self.content = content } } // An example view putting GridStack into practice. struct ContentView: View { var body: some View { GridStack(rows: 4, columns: 4) { row, col in Image(systemName: "\(row * 4 + col).circle") Text("R\(row) C\(col)") } } }
创建一个4x 4网格,每个单元格中包含图像和文本。这是对这段代码的引用👇enter link description here快乐编码)
5条答案
按热度按时间wqsoz72f1#
checkout 基于ZStack的示例here
k7fdbhmy2#
iOS 14
您可以使用两个新的本机
View
:LazyHGrid
LazyVGrid
使用代码或直接从库中:
该库包含一个完全工作的示例代码,您可以自己测试。
4uqofj5v3#
你可以像这样创建你的customView来实现UICollectionView行为:
8e2ybdfx4#
适用于Xcode 12上的iOS/iPadOS 14。您可以使用LazyVGrid将用户看到的内容加载到屏幕上,而不是整个列表,List默认为lazy。
不要忘记将infoobjects替换为您的info,将YourObjectView替换为您的customView。
dfddblmv5#
🔴 SwiftUI的LazyVGrid和LazyHGrid为我们提供了相当灵活的网格布局。
最简单的网格是由三件事组成的:您的原始数据,描述您想要的布局的GridItem数组,以及将数据和布局结合在一起的LazyVGrid或LazyHGrid。
例如,这将使用大小为80点的单元格创建垂直网格布局:
🔴 使用GridItem(.adaptive(最小值:80))意味着我们希望网格每行容纳尽可能多的项目,每个项目的最小大小为80个点。
如果你想控制列的数量,你可以使用.flexible(),它也可以让你指定每个项目应该有多大,但现在可以让你控制有多少列。例如,这将创建五列:
🔴 第三种选择是使用固定尺寸。例如,这将使第一列正好是100点宽,并允许第二列填满所有剩余的空间:
🔴 您也可以使用LazyHGrid来创建一个水平滚动的网格,它的工作方式基本相同,只是它在其初始化器中接受行。
例如,我们可以创建10个并排的标题图像,它们像这样水平滚动:
🔴 正如您所看到的,创建水平和垂直网格所需的代码几乎相同,只是将行改为列。
如果您需要支持iOS 13,您将无法访问LazyHGrid或LazyVGrid,因此请阅读下面的替代方案。
SwiftUI为我们提供了用于垂直布局的VStack和用于水平布局的HStack,但没有任何东西可以同时做到这两点-没有任何东西可以在网格结构中布局视图。
幸运的是,我们可以通过利用SwiftUI的视图构建器系统自己编写一个。这意味着编写一个必须使用行和列计数创建的类型,以及一个闭包,它可以运行以检索网格中给定单元格的视图。然后,在主体内部,它可以循环遍历所有行和列,并在VStack和HStack中创建单元格,以创建网格,每次调用视图闭包来询问单元格中应该有什么。
在代码中,它看起来像这样:
创建一个4x 4网格,每个单元格中包含图像和文本。
这是对这段代码的引用👇
enter link description here
快乐编码)