Add suggestions in search screen
This commit is contained in:
parent
356b9176f7
commit
9bdb9a2c62
|
@ -12,43 +12,70 @@ import SwiftUI
|
|||
struct LibrarySearchView: View {
|
||||
@StateObject var viewModel: LibrarySearchViewModel
|
||||
@State var searchQuery = ""
|
||||
|
||||
|
||||
@State private var tracks: [GridItem] = Array(repeating: .init(.flexible()), count: Int(UIScreen.main.bounds.size.width) / 125)
|
||||
|
||||
|
||||
func recalcTracks() {
|
||||
tracks = Array(repeating: .init(.flexible()), count: Int(UIScreen.main.bounds.size.width) / 125)
|
||||
}
|
||||
|
||||
|
||||
var body: some View {
|
||||
VStack {
|
||||
Spacer().frame(height: 6)
|
||||
SearchBar(text: $searchQuery)
|
||||
ZStack {
|
||||
if !viewModel.isLoading {
|
||||
ScrollView(.vertical) {
|
||||
if !viewModel.items.isEmpty {
|
||||
Spacer().frame(height: 16)
|
||||
LazyVGrid(columns: tracks) {
|
||||
ForEach(viewModel.items, id: \.id) { item in
|
||||
PortraitItemView(item: item)
|
||||
}
|
||||
Spacer().frame(height: 16)
|
||||
}
|
||||
.onRotate { _ in
|
||||
recalcTracks()
|
||||
}
|
||||
} else {
|
||||
Text("Query returned 0 results.")
|
||||
}
|
||||
}
|
||||
ZStack {
|
||||
VStack {
|
||||
SearchBar(text: $searchQuery)
|
||||
.padding(.vertical, 8)
|
||||
if searchQuery.isEmpty {
|
||||
suggestionsListView
|
||||
} else {
|
||||
ProgressView()
|
||||
itemsGridView
|
||||
}
|
||||
}
|
||||
if viewModel.isLoading {
|
||||
ProgressView()
|
||||
}
|
||||
}
|
||||
.onChange(of: searchQuery) { query in
|
||||
viewModel.searchQuerySubject.send(query)
|
||||
}
|
||||
.navigationBarTitle("Search", displayMode: .inline)
|
||||
}
|
||||
|
||||
var suggestionsListView: some View {
|
||||
ScrollView {
|
||||
LazyVStack(alignment: .leading, spacing: 8) {
|
||||
Text("Suggestions")
|
||||
.font(.title)
|
||||
.foregroundColor(.primary)
|
||||
.padding(.bottom, 8)
|
||||
ForEach(viewModel.suggestions, id: \.id) { item in
|
||||
Button {
|
||||
searchQuery = item.name ?? ""
|
||||
} label: {
|
||||
Text(item.name ?? "")
|
||||
.font(.body)
|
||||
.foregroundColor(.secondary)
|
||||
}
|
||||
}
|
||||
}
|
||||
.padding(.horizontal, 16)
|
||||
}
|
||||
}
|
||||
|
||||
var itemsGridView: some View {
|
||||
ScrollView {
|
||||
if !viewModel.items.isEmpty {
|
||||
LazyVGrid(columns: tracks) {
|
||||
ForEach(viewModel.items, id: \.id) { item in
|
||||
PortraitItemView(item: item)
|
||||
}
|
||||
}
|
||||
.padding(.bottom, 16)
|
||||
.onRotate { _ in
|
||||
recalcTracks()
|
||||
}
|
||||
} else {
|
||||
Text("Query returned 0 results.")
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -12,8 +12,9 @@ import Foundation
|
|||
import JellyfinAPI
|
||||
|
||||
final class LibrarySearchViewModel: ViewModel {
|
||||
@Published
|
||||
var items = [BaseItemDto]()
|
||||
@Published var items = [BaseItemDto]()
|
||||
|
||||
@Published var suggestions = [BaseItemDto]()
|
||||
|
||||
var searchQuerySubject = CurrentValueSubject<String, Never>("")
|
||||
var parentID: String?
|
||||
|
@ -23,9 +24,29 @@ final class LibrarySearchViewModel: ViewModel {
|
|||
super.init()
|
||||
|
||||
searchQuerySubject
|
||||
.filter { !$0.isEmpty }
|
||||
.debounce(for: 0.25, scheduler: DispatchQueue.main)
|
||||
.sink(receiveValue: search(with:))
|
||||
.store(in: &cancellables)
|
||||
|
||||
requestSuggestions()
|
||||
}
|
||||
|
||||
func requestSuggestions() {
|
||||
ItemsAPI.getItemsByUserId(userId: SessionManager.current.user.user_id!,
|
||||
limit: 20,
|
||||
recursive: true,
|
||||
parentId: parentID,
|
||||
includeItemTypes: ["Movie", "Series", "MusicArtist"],
|
||||
sortBy: ["IsFavoriteOrLiked", "Random"],
|
||||
imageTypeLimit: 0,
|
||||
enableTotalRecordCount: false,
|
||||
enableImages: false)
|
||||
.trackActivity(loading)
|
||||
.sink(receiveCompletion: handleAPIRequestCompletion(completion:)) { [weak self] response in
|
||||
self?.suggestions = response.items ?? []
|
||||
}
|
||||
.store(in: &cancellables)
|
||||
}
|
||||
|
||||
func search(with query: String) {
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
import Foundation
|
||||
import Combine
|
||||
import Nuke
|
||||
import UIKit
|
||||
|
||||
#if !os(tvOS)
|
||||
import WidgetKit
|
||||
|
@ -28,6 +29,7 @@ final class SplashViewModel: ViewModel {
|
|||
|
||||
#if !os(tvOS)
|
||||
WidgetCenter.shared.reloadAllTimelines()
|
||||
UIScrollView.appearance().keyboardDismissMode = .onDrag
|
||||
#endif
|
||||
|
||||
let nc = NotificationCenter.default
|
||||
|
|
Loading…
Reference in New Issue