Skip to content
This repository was archived by the owner on Dec 27, 2020. It is now read-only.

Commit e60ff4e

Browse files
committed
gitignore
1 parent cd6db81 commit e60ff4e

File tree

1 file changed

+44
-19
lines changed

1 file changed

+44
-19
lines changed

Sources/Grid/Grid.swift

Lines changed: 44 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -2,38 +2,61 @@ import SwiftUI
22

33
/// A view that arranges its children in a grid.
44
@available(iOS 13.0, OSX 10.15, *)
5-
public struct Grid<Data, Content> : View where Data: RandomAccessCollection, Data.Element: Identifiable, Content : View {
6-
public typealias Item = Data.Element.IdentifiedValue
7-
private let data: [Item]
8-
private let minimumItemWidth: Length
9-
private let spacing: Length
10-
private let content: (Item) -> Content
5+
public struct Grid<Data, Content> : View where Data: RandomAccessCollection, Content : View {
6+
private let data: [Data.Element]
7+
private let minimumItemWidth: CGFloat
8+
private let spacing: CGFloat
9+
private let content: (Data.Element) -> Content
1110

1211
public var body: some View {
1312
GeometryReader { geometry in
1413
ScrollView {
15-
VStack(spacing: self.spacing) {
16-
ForEach(0..<Int((Length(self.data.count) / max(1.0, geometry.size.width / self.minimumItemWidth).rounded(.down)).rounded(.up))) { rowIndex in
14+
VStack(alignment: .leading, spacing: self.spacing) {
15+
ForEach(0..<self.rowCount(with: geometry), id: \.self) { rowIndex in
1716
HStack(spacing: self.spacing) {
18-
ForEach(0..<Int(geometry.size.width / self.minimumItemWidth)) { columnIndex in
19-
if rowIndex * max(1, Int(geometry.size.width / self.minimumItemWidth)) + columnIndex <= self.data.count - 1 {
20-
self.content(self.data[rowIndex * max(1, Int(geometry.size.width / self.minimumItemWidth)) + columnIndex])
21-
} else {
22-
Rectangle().foregroundColor(.clear)
23-
}
17+
ForEach(0..<self.columnCount(with: geometry), id: \.self) { (columnIndex: Int) -> Content? in
18+
self.item(with: geometry, rowIndex: rowIndex, columnIndex: columnIndex)
19+
}
20+
ForEach(0..<self.emptyElementsCount(geometry: geometry, row: rowIndex), id: \.self) { _ in
21+
Spacer()
2422
}
2523
}
2624
}
27-
.clipped()
2825
}
2926
.padding()
3027
}
28+
3129
}
32-
3330
}
3431

35-
public init(_ data: Data, minimumItemWidth: Length = 300, spacing: Length = 8, content: @escaping (Item) -> Content) {
36-
self.data = data.map { $0.identifiedValue }
32+
func emptyElementsCount(geometry:GeometryProxy, row: Int) -> Int {
33+
let isLastRow = rowCount(with: geometry) - 1 == row
34+
let possibleItemsCount = rowCount(with: geometry) * columnCount(with: geometry)
35+
return isLastRow ? possibleItemsCount % data.count : 0
36+
}
37+
38+
func rowCount(with geometry: GeometryProxy) -> Int {
39+
Int((CGFloat(self.data.count) / max(1.0, geometry.size.width / self.minimumItemWidth).rounded(.down)).rounded(.up))
40+
}
41+
42+
func columnCount(with geometry: GeometryProxy) -> Int {
43+
Int(geometry.size.width / self.minimumItemWidth)
44+
}
45+
46+
func itemIndex(with geometry: GeometryProxy, rowIndex: Int, columnIndex: Int) -> Int {
47+
rowIndex * max(1, Int(geometry.size.width / self.minimumItemWidth)) + columnIndex
48+
}
49+
50+
func item(with geometry: GeometryProxy, rowIndex: Int, columnIndex: Int) -> Content? {
51+
if self.itemIndex(with: geometry, rowIndex: rowIndex, columnIndex: columnIndex) <= self.data.count - 1 {
52+
return self.content(self.data[self.itemIndex(with: geometry, rowIndex: rowIndex, columnIndex: columnIndex)])
53+
} else {
54+
return nil
55+
}
56+
}
57+
58+
public init(_ data: Data, minimumItemWidth: CGFloat = 300, spacing: CGFloat = 8, content: @escaping (Data.Element) -> Content) {
59+
self.data = data.map { $0 }
3760
self.content = content
3861
self.spacing = spacing
3962
self.minimumItemWidth = minimumItemWidth
@@ -43,7 +66,9 @@ public struct Grid<Data, Content> : View where Data: RandomAccessCollection, Dat
4366
#if DEBUG
4467
struct Grid_Previews: PreviewProvider {
4568
static var previews: some View {
46-
Text("123")
69+
Grid(0...100) {
70+
Text("\($0)")
71+
}
4772
}
4873
}
4974
#endif

0 commit comments

Comments
 (0)