I have a multi-level dictionary that I need use to build navigation links. Now I have a 2-level depth dictionary:
let multiDimDict: [String: [[String: [String]]]
It is not clear from provided snapshot how list of dictionaries should be presented, and, actually, why is it used a dictionary as base model at all, but irrelative to uncertainties here is possible direction (not final but tested & can be considered)
struct PlayingWithMultiDimNavLink2: View {
let multiDimDict: [String: [[String: [String]]]]
= ["A": [["A1": ["A11", "A12"]], ["A2": ["A21", "A22"]]],
"B": [["B1": ["B11", "B12"]], ["B2": ["B21", "B22"]]]
]
var body: some View {
NavigationView{
GenericChildView(model: multiDimDict)
}
}
}
struct GenericChildView: View {
let model: [String: Any]
var body: some View {
List{
ForEach(model.keys.sorted(), id: \.self) { key in
self.nextLevelView(for: key)
}
}
}
private func nextLevelView(for key: String) -> some View {
let next = model[key]
return Group {
if next as? String != nil {
Text(next as! String)
} else if next as? [Any] != nil {
NavigationLink(destination: GenerateChildListView(infoList: next as! [Any]))
{ Text(key) }
} else if next as? [String: Any] != nil {
NavigationLink(destination: GenericChildView(model: next as! [String: Any]))
{ Text(key) }
}
}
}
}
struct GenerateChildListView: View {
var infoList: [Any]
init(infoList: [Any]){
self.infoList = infoList
}
var body: some View {
Group {
if infoList.count == 1 {
self.singleContentView()
}
if infoList.count > 1 {
List{
self.contentView()
}
}
}
}
private func singleContentView() -> some View {
return Group {
if infoList as? [String] != nil {
Text(infoList[0] as! String)
} else if infoList as? [[String: Any]] != nil {
GenericChildView(model: self.infoList[0] as! [String: Any])
}
}
}
private func contentView() -> some View {
return Group {
if infoList as? [String] != nil {
ForEach(infoList as! [String], id:\.self) { content in
Text(content)
}
} else if infoList as? [[String: Any]] != nil {
ForEach((infoList as! [[String: Any]]).indices, id: \.self) { i in
GenericChildView(model: self.infoList[i] as! [String: Any])
}
}
}
}
}