WWDC22 SALE: Save 50% on all my Swift books and bundles! >>

SOLVED: Day 41: EXC_BAD_ACCESS (code=2, address=0x7ff7b904aff8)

Forums > 100 Days of SwiftUI

There is a lot of code in the Moonshot Project, and I'm honestly confused over this line.

I just finished everything before the last AstronautView. When I run the app, Xcode gives me this. Nothing else. When I run the simulator, and click an icon to show the details, the app gets stuck, and then the above message pops out. Clearly, the detailed view is not working properly.

Any idea what I can do here?

MoonshitApp:

import SwiftUI

@main
struct MoonshotApp: App {
    var body: some Scene {
        WindowGroup {
            ContentView()
        }
    }
}

ContentView:

import SwiftUI

// with an extension on Bundle, that's all it takes to get a [String: Astronaut] dictionary.
// add a Type Annotation to let Swift know what type our return will be
let astronauts: [String: Astronaut] = Bundle.main.decode("astronauts.json")
let missions: [Mission] = Bundle.main.decode("missions.json")

struct ContentView: View {
    // note, this is an Array
    let columns = [
        GridItem(.adaptive(minimum: 150))
    ]

    var body: some View {
        NavigationView {
            ScrollView {
                LazyVGrid(columns: columns) {
                    ForEach(missions) {mission in
                        NavigationLink {
                            MissionView(mission: mission, astronauts: astronauts)
                        } label: {
                            VStack {
                                Image(mission.image)
                                    .resizable()
                                    .scaledToFit()
                                    .frame(width: 100, height: 100)
                                    .padding()
                                VStack {
                                    Text(mission.displayName).font(.headline)
                                        .font(.headline)
                                        .foregroundColor(.white)
                                    Text(mission.formattedLaunchDate).font(.headline).font(.caption)
                                        .font(.caption)
                                        .foregroundColor(.white.opacity(0.5))
                                }
                                .padding(.vertical)
                                .frame(maxWidth: .infinity)
                                .background(.lightBackground)
                            }
                            .clipShape(RoundedRectangle(cornerRadius: 10))
                            .overlay(RoundedRectangle(cornerRadius: 10).stroke(.lightBackground))
                        }
                    }
                }
                .padding([.horizontal, .bottom])
            }
            .navigationTitle("Moonshot")
            .background(.darkBackground)
            // "Moonshot" will appear black or white depending on whether the user is in light mode or dark mode
            .preferredColorScheme(.dark)
        }
    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}

Mission View

import SwiftUI

struct MissionView: View {
    // a mission property so we can show the mission badge and description
    let mission : Mission

    struct CrewMember {
        let role : String
        let astronaut : Astronaut
    }

    let crew : [CrewMember]

    init(mission: Mission, astronauts: [String : Astronaut]) {
        self.mission = mission

        self.crew = mission.crew.map { member in
            if let astronaut = astronauts[member.name] {
                return CrewMember(role: member.role, astronaut: astronaut)
            }
            else {
                fatalError("Missing \(member.name)")
            }
        }
    }

    var body: some View {
        GeometryReader {geometry in
            ScrollView {
                VStack {
                    Image(mission.image)
                        .resizable()
                        .scaledToFit()
                        .frame(maxWidth: geometry.size.width * 0.6)

                    VStack(alignment: .leading) {
                        Text("Mission Highlights")
                            .font(.title.bold())
                            .padding(.bottom, 5)

                        Text(mission.description)
                    }
                    .padding(.horizontal)

                    ScrollView(.horizontal, showsIndicators: false) {
                        HStack {
                            ForEach(crew, id : \.role) { crewMember in 
                                NavigationLink {
                                    Text("Astronaut Details")
                                } label: {
                                    HStack {
                                        Image(crewMember.astronaut.id)
                                            .resizable()
                                            .frame(width: 104, height: 72)
                                            .clipShape(Capsule())
                                            .overlay(Capsule().strokeBorder(.white, lineWidth: 1)
                                            )

                                        VStack(alignment: .leading) {
                                            Text(crewMember.astronaut.name)
                                                .foregroundColor(.white)
                                                .font(.headline)
                                            Text(crewMember.role)
                                                .foregroundColor(.secondary)
                                        }
                                    }
                                    .padding(.horizontal)
                                }
                            }
                        }
                    }
                }
                .padding(.bottom)
            }
        }
        .navigationTitle(mission.displayName)
        navigationBarTitleDisplayMode(.inline)
        background(.darkBackground)
    }
}

struct MissionView_Previews: PreviewProvider {
    static let missions : [Mission] = Bundle.main.decode("missions.json")
    static let astronauts : [String : Astronaut] = Bundle.main.decode("astronauts.json")

    static var previews: some View {
        MissionView(mission: missions[0], astronauts: astronauts)
            .preferredColorScheme(.dark)
    }
}

Bundle-Decodable

import Foundation

extension Bundle {
    func decode<T: Codable>(_ file: String) -> T {
        guard let url = self.url(forResource: file, withExtension: nil) else {
            fatalError("Failed to locate \(file) in bundle.")
        }

        guard let data = try? Data(contentsOf: url) else {
            fatalError("Failed to load \(file) from bundle.")
        }

        let decoder = JSONDecoder()
        let formatter = DateFormatter()
        formatter.dateFormat = "y-MM-dd"
        decoder.dateDecodingStrategy = .formatted(formatter)

        guard let loaded = try? decoder.decode(T.self, from: data) else {
            fatalError("Failed to load \(file) from bundle.")
        }

        return loaded
    }
}

Not putting Mission, Astronaut, and Color-Theme here since they are simple code.

Appreciate anything.

Will try run the simulator again after all modules on Project 8 is finished and see if I run into the same problem again.

   

Just ran a couple of breakpoints:

I got this in my ContentView's ScrollView line, just below NavigationlInk:

Thread 1: breakpoint 1.1 (1)

   

Hi @swiftHu

The error is your app has crashed! It not very helpful to where it crashed, so you have to see a what point you are in the app when crashed.

Firstly these two lines are missing the point (.) in the MassionView

navigationBarTitleDisplayMode(.inline)
background(.darkBackground)

click an icon to show the details

Do you mean when tapped on NavigationLink to MissionView or do you mean when tap on the NavigationLink to show "Astronaut Details"?

Thread 1: breakpoint 1.1 (1)

This is because you added the break point it not an error message.

.preferredColorScheme(.dark) will produce dark regardless if user has light mode on

// "Moonshot" will appear black or white depending on whether the user is in light mode or dark mode
.preferredColorScheme(.dark)

1      

NigelGee, thank you very much ! I added those two dots, and now it works fine.

   

Just had the same problem! Thank you @NigelGee! I missed a period for the navBarTitleDisplay. Would have drove me nuts!

   

Save 50% in my Black Friday sale.

SAVE 50% To celebrate WWDC22, all our books and bundles are half price, so you can take your Swift knowledge further without spending big! Get the Swift Power Pack to build your iOS career faster, get the Swift Platform Pack to builds apps for macOS, watchOS, and beyond, or get the Swift Plus Pack to learn advanced design patterns, testing skills, and more.

Save 50% on all our books and bundles!

Sponsor Hacking with Swift and reach the world's largest Swift community!

Reply to this topic…

You need to create an account or log in to reply.

All interactions here are governed by our code of conduct.

 
Unknown user

You are not logged in

Log in or create account
 

Link copied to your pasteboard.