// // ItemGrid.swift // LuminateUI // // Created by Brendan Szymanski on 6/5/26. // @preconcurrency import Adwaita import LuminateCore public struct ItemGrid: View { var client: JellyfinClient var userId: String var parentId: String? var includeItemTypes: [Components.Schemas.BaseItemKind]? var title: String? @State private nonisolated(unsafe) var items: [Components.Schemas.BaseItemDto] = [] @State private nonisolated(unsafe) var isLoading = false private let pageSize: Int32 = 50 public init( client: JellyfinClient, userId: String, parentId: String? = nil, includeItemTypes: [Components.Schemas.BaseItemKind]? = nil, title: String? = nil ) { self.client = client self.userId = userId self.parentId = parentId self.includeItemTypes = includeItemTypes self.title = title } public var view: Body { VStack { if let title { Text(title) .title2() .halign(.start) .padding() } if isLoading { Spinner() } else { ScrollView { FlowBox(items) { item in PosterCell(item: item, client: client) } } } } .onAppear { loadItems() } } private func loadItems() { isLoading = true Task { [self] in do { let result = try await client.getItems( userId: userId, parentId: parentId, includeItemTypes: includeItemTypes, fields: [.overview, .genres, .people, .mediaSources], sortBy: [.sortName], sortOrder: [.ascending], startIndex: 0, limit: pageSize, recursive: true ) items = result.items ?? [] isLoading = false } catch { isLoading = false } } } }