In my app, the navigation should be ArmyListView -> ArmyListDetailsView -> IncludedUnitScreenView
My ArmyListView screen creates a NavigationStack and moving on to the ArmyListDetailsView works fine. When I click an item on the ArmyListDetailsView, the IncludedUnitScreenView never opens and it looks like it’s stuck in an infinite loop of creating the view.
I don’t understand why this is happening when the first navigation worked fine.
Here’s my code for ArmyListDetailsView
struct ArmyListDetailsView: View {
@Environment(.modelContext) private var modelContext
@Query private var theIncludedUnits: [IncludedUnit]
@Query private var theArmyList: [ArmyList]
@State var shouldPresentSheet = false
init(armyList: String = "") {
let includedUnitsPredicate = #Predicate<IncludedUnit> { includedUnit in
armyList.isEmpty || includedUnit.armyList.localizedStandardContains(armyList)
}
_theIncludedUnits = Query(filter: includedUnitsPredicate, sort: IncludedUnit.armyList)
let armyListPredicate = #Predicate<ArmyList> { armylist in
armyList.isEmpty || armylist.listTitle.localizedStandardContains(armyList)
}
_theArmyList = Query(filter: armyListPredicate, sort: ArmyList.listTitle)
}
var body: some View {
let armyList = theArmyList.first.unsafelyUnwrapped
List {
Section(header: Text("List Details")) {
ArmyListCoreDetails(theArmyList: armyList)
}
if !theIncludedUnits.isEmpty {
let groupedIncludedUnits = Dictionary(grouping: theIncludedUnits, by: .category)
ForEach(Array(groupedIncludedUnits.keys), id: .self) { category in
Section(header: Text(category)) {
let categoryIncludedUnits = getIncludedUnitsForCategory(theCategory: category, theIncludedUnits: groupedIncludedUnits)
ForEach(categoryIncludedUnits, id: .id) { theIncludedUnit in
NavigationLink {
IncludedUnitScreenView(theIncludedUnitId: theIncludedUnit.id,
theIncludedUnit: theIncludedUnit)
} label: {
IncludedUnitRow(includedUnit: theIncludedUnit)
}
}
}
}
} else {
ContentUnavailableView {
Label("No units have been added to this list.nPress + to choose some.", systemImage: "doc.on.doc")
}
}
}
.navigationTitle(armyList.listTitle)
}
…and the code for IncludedUnitScreenView
struct IncludedUnitScreenView: View {
@Environment(.modelContext) private var modelContext
@Query private var theUnitCompositions: [UnitComposition]
@Query private var theLoadouts: [Loadout]
@State private var theIncludedUnit: IncludedUnit
@State private var theIncludedUnitId: Int
init(theIncludedUnitId: Int = 0, theIncludedUnit: IncludedUnit) {
let unitCompositionPredicate = #Predicate<UnitComposition> { unitComposition in
theIncludedUnitId == 0 || unitComposition.includedUnitId == theIncludedUnitId
}
_theUnitCompositions = Query(filter: unitCompositionPredicate)
let loadoutPredicate = #Predicate<Loadout> { loadout in
theIncludedUnitId == 0 || loadout.includedUnitId == theIncludedUnitId
}
_theLoadouts = Query(filter: loadoutPredicate)
self.theIncludedUnit = theIncludedUnit
self.theIncludedUnitId = theIncludedUnitId
NSLog("IncludedUnitScreenView: Completed the init")
}
var body: some View {
List {
Section(header: Text("Unit Details")) {
IncludedUnitCoreDetails(theIncludedUnit: theIncludedUnit)
}
Section(header: Text("Models")) {
ForEach(theUnitCompositions, id: .model) { theUnitComposition in
NavigationLink {
LoadoutListView(theLoadoutList: theLoadouts.filter {$0.model == theUnitComposition.model})
} label: {
IncludedUnitDetailsRow(
theIncludedUnit: theIncludedUnit,
theUnitComposition: theUnitComposition,
theLoadouts: theLoadouts.filter {$0.model == theUnitComposition.model}
)
}
}
}
}
}
}
I can see the infinite loop by the NSLog statements in the debug window.