Проблема в том, что функция вызывается дважды при каждой инициализации представления, т. е. при дублировании данных. Я не могу понять, почему .onReceive вызывается дважды.
Я думаю, это может быть как-то связано с тем, что функция вызывается, когда я запускаю модель выбора, а затем получаю другую уведомление от самого средства выбора, но я не знаю, как его обойти.
Вот мой код:
Модель средства выбора
Код: Выделить всё
import Foundation
class PickerModel: ObservableObject {
@Published var filter = 0
let pickerOptions = ["Popular", "Top Rated"]
}
Код: Выделить всё
import SwiftUI
struct FilteredMoviesGridView: View {
@ObservedObject private var filteredMovieVM = FilteredMovieGridViewModel()
@ObservedObject private var pickerModel = PickerModel()
private var twoColumnGrid = [GridItem(.flexible()), GridItem(.flexible())]
var body: some View {
NavigationView {
VStack {
Picker(selection: $pickerModel.filter, label: Text("Select")) {
ForEach(0 ..< pickerModel.pickerOptions.count) {
Text(pickerModel.pickerOptions[$0])
}
}.onReceive(pickerModel.$filter) { (value) in
switch value {
case 0:
filteredMovieVM.movies.removeAll()
filteredMovieVM.currentPage = 1
filteredMovieVM.fetchMovies(filter: "popularity")
case 1:
filteredMovieVM.movies.removeAll()
filteredMovieVM.currentPage = 1
filteredMovieVM.fetchMovies(filter: "vote_average")
default:
filteredMovieVM.movies.removeAll()
filteredMovieVM.currentPage = 1
filteredMovieVM.fetchMovies(filter: "popularity")
}
}.pickerStyle(SegmentedPickerStyle())
ScrollView {
LazyVGrid(columns: twoColumnGrid, spacing: 10) {
ForEach(filteredMovieVM.movies, id:\.id) { movie in
NavigationLink(destination: MovieDetailView(movie: movie)) {
MovieGridItemView(movies: movie)
}.buttonStyle(PlainButtonStyle())
.onAppear(perform: {
if movie == self.filteredMovieVM.movies.last {
switch pickerModel.filter {
case 0:
self.filteredMovieVM.checkTotalMovies(filter: "popularity")
case 1:
self.filteredMovieVM.checkTotalMovies(filter: "vote_average")
default:
self.filteredMovieVM.checkTotalMovies(filter: "popularity")
}
}
})
}
}
}
.navigationBarTitle("Movies")
}
}.accentColor(.white)
}
}
Код: Выделить всё
import Foundation
class FilteredMovieGridViewModel: ObservableObject {
@Published var movies = [Movie]()
private var filteredMovies = [MovieList]()
var currentPage = 1
func checkTotalMovies(filter: String) {
if filteredMovies.count < 20 {
fetchMovies(filter: filter)
}
}
func fetchMovies(filter: String) {
WebService().getMoviesByFilter(filter: filter, page: currentPage) { movie in
if let movie = movie {
self.filteredMovies.append(movie)
for movie in movie.movies {
self.movies.append(movie)
print(self.movies.count)
}
}
}
if let totalPages = filteredMovies.first?.totalPages {
if currentPage
Подробнее здесь: [url]https://stackoverflow.com/questions/63694325/onreceive-firing-twice-swiftui[/url]