import SwiftUI import SwiftData struct HomeView: View { @EnvironmentObject private var router: AppRouter @Environment(\.dependencies) private var dependencies @Query(sort: \LibraryBook.dateAdded, order: .reverse) private var libraryBooks: [LibraryBook] @StateObject private var viewModel: HomeViewModel init(viewModel: HomeViewModel) { _viewModel = StateObject(wrappedValue: viewModel) } var body: some View { ScrollView { VStack(spacing: 28) { header ForEach(viewModel.categories) { category in ShelfSectionView( title: category.name, books: category.books, gradient: viewModel.gradient(for: category.name), imageCache: dependencies.imageCache, onTapCategory: { router.path.append(.category(name: category.name)) }, onTapBook: { router.path.append(.detail($0)) } ) } } .padding(.top, 16) .padding(.bottom, 120) } .background(Theme.background.ignoresSafeArea()) .safeAreaInset(edge: .bottom, spacing: 0) { ZStack { BlurFogOverlay() .frame(height: 96) PrimaryPillButton(title: String(localized: "home.addBooks")) { router.path.append(.addBooks) } .padding(.horizontal, 24) .padding(.bottom, 12) } .frame(height: 100) } .onAppear { viewModel.refresh(from: libraryBooks) } .onChange(of: libraryBooks.map(\.localId)) { _, _ in viewModel.refresh(from: libraryBooks) } .task(id: libraryBooks.count) { viewModel.refresh(from: libraryBooks) } } private var header: some View { VStack(spacing: 4) { Text(String(localized: "home.myFavourite")) .font(.footnote.weight(.light)) .kerning(1.2) .foregroundStyle(Color.black.opacity(0.7)) Text(String(localized: "home.books")) .font(Theme.headerSerif(size: 56).weight(.bold)) .foregroundStyle(.black) .kerning(1) } .frame(maxWidth: .infinity) .padding(.top, 12) .accessibilityElement(children: .combine) } }