I have data loaded into an HStack
that is in a Scroll View
in SwiftUI
. Right now I have it coded where a user can tap on one of those items and have it selected. I'd like for the 0th item to already be selected upon load.
import SwiftUI
import Combine
import Contentful
struct moviesView : View {
@ObservedObject var fetcher = MovieFetcher()
@State var selectMovie: Movie? = nil
@Binding var show: Bool
var body: some View {
HStack(alignment: .bottom) {
if show {
ScrollView(.horizontal) {
Spacer()
HStack(alignment: .bottom, spacing: 30) {
ForEach(fetcher.movies, id: \.self) { item in
selectableRow(movie: item, selectMovie: self.$selectMovie)
}
.onAppear() {
self.selectMovie = self.movies.count > 0 ? self.movies.first! : nil
}
}
.frame(minWidth: 0, maxWidth: .infinity)
}
.padding(.leading, 46)
.padding(.bottom, 26)
}
}
}
}
struct selectableRow : View {
var movie: Movie
@Binding var selectedMovie: Movie?
@State var initialImage = UIImage()
var body: some View {
ZStack(alignment: .center) {
if movie == selectedMovie {
Image("")
.resizable()
.frame(width: 187, height: 254)
.overlay(
RoundedRectangle(cornerRadius: 13)
Image(uiImage: initialImage)
.resizable()
.cornerRadius(13.0)
.frame(width: 182, height: 249)
.onAppear {
let urlString = "\(urlBase)\(self.movie.movieId).png?"
guard let url = URL(string: self.urlString) else { return }
URLSession.shared.dataTask(with: url) { (data, response, error) in
guard let data = data else { return }
guard let image = UIImage(data: data) else { return }
RunLoop.main.perform {
self.initialImage = image
}
}.resume()
}
} else {
Image(uiImage: initialImage)
.resizable()
.cornerRadius(13.0)
.frame(width: 135, height: 179)
.onAppear {
let urlString = "\(urlBase)\(self.movie.movieId).png?"
guard let url = URL(string: self.urlString) else { return }
URLSession.shared.dataTask(with: url) { (data, response, error) in
guard let data = data else { return }
guard let image = UIImage(data: data) else { return }
RunLoop.main.perform {
self.initialImage = image
}
}.resume()
}
}
}
.onTapGesture {
self.selectedMovie = self.movie
}
}
}
EDIT:
I've added the below suggestion but it's still now working properly. Maybe it's where I added the .onAppear
?
So when I launch my app I see the 0th item is selected but when I tap on any item the view just reloads but the 0th item always stays selected.
Additional issue:
Also, my @ObservedObject var fetcher = MovieFetcher()
in moviesView
is called repeatedly.