I have been trying to figure out how to pass my computed property from a foreach loop to another view as binding and I can’t seem to figure it out. I’m using a computed property for the foreach loop b/c it is used for a search bar. Let me start by showing my swift data models first.
import SwiftUI
import SwiftData
@Model
class Album: Identifiable {
var id: UUID = UUID()
var isPublicAlbum: Bool = false
var title: String = ""
var timeStamp: Date = Date()
@Relationship(deleteRule: .cascade, inverse: Media.album) var media: [Media]?
init(isPublicAlbum: Bool, title: String, timeStamp: Date = Date()) {
self.isPublicAlbum = isPublicAlbum
self.title = title
self.timeStamp = timeStamp
}
}
import SwiftUI
import SwiftData
@Model
class Media: Identifiable {
var id: UUID = UUID()
var albumID: UUID = UUID()
@Attribute(.externalStorage) var asset: Data? = nil
var isCover: Bool = false
var contentType: String = ""
var timeStamp: Date = Date()
//var album: Album?
@Relationship(deleteRule: .nullify) var album: Album?
init(albumID: UUID = UUID(), asset: Data? = nil, isCover: Bool = false, contentType: String = "", timeStamp: Date = Date()) {
self.albumID = albumID
self.asset = asset
self.isCover = isCover
self.contentType = contentType
self.timeStamp = timeStamp
}
}
I want to be able to pass the albumID as binding to the albumView so I can use @Query
in the albumView in hopes that my albumView will update in real-time as it syncs with Cloudkit. e.g. Fresh app installs and the media is downloading.
Here is the relevant code.
struct MainView: View {
@Environment(.modelContext) private var dbContext
@Environment(.horizontalSizeClass) var horizontalSizeClass
@Environment(.colorScheme) var colorScheme
@Query(filter: #Predicate<Album> { $0.isPublicAlbum == false }, sort: Album.title, order: .forward) private var listAlbums: [Album]
@State private var searchString: String = ""
private var filteredAlbums: [Album] {
if searchString.isEmpty {
return listAlbums
} else {
return listAlbums.filter { album in
album.title.localizedStandardContains(searchString)
}
}
}
//...
var body: some View {
VStack {
CustomSearchBar(text: $searchString, placeholder: NSLocalizedString("Search Private Albums", comment: "This is a search bar to search for private albums"))
//...
ForEach(filteredAlbums) { album in
VStack(spacing: 0) {
ZStack(alignment: .topTrailing) {
NavigationLink(destination: AlbumView(album: album)) {
//...
}
}
}
//...
}
}
}
No matter what I have tried I can’t seem to pass the album as binding without compiler errors or it just timing out. I don’t want to pass it as .constant(album)
b/c I need my child view to update in real-time which is my end goal here. Any thoughts on how to achieve this?