-1

I'm new to swift and I'm learning from a course on Udemy.

I'm getting the error

"Thread 1: EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0x0)"

and the console explains it as "unexpectedly found nil while unwrapping an Optional value".

I've double checked to make sure my code is the exact same as my instructor's and even restarted once in case I messed something up but I'm still getting the same error.

My code is as follows :

    import UIKit
    import AVFoundation

    class ViewController: UIViewController {
        @IBOutlet weak var darkBlueBG: UIImageView!
        @IBOutlet weak var powerButton: UIButton!
        @IBOutlet weak var cloudHolder: UIView!
        @IBOutlet weak var rocket: UIImageView!
        @IBOutlet weak var hustleLbl: UILabel!
        @IBOutlet weak var onLbl: UILabel!

        var player: AVAudioPlayer!

        override func viewDidLoad() {
            super.viewDidLoad()

            let path = Bundle.main.path(forResource: "hustle-on", ofType: "wav")! //This is the line that the console says is causing the error
            let url = URL(fileURLWithPath: path)

            do {
                player = try AVAudioPlayer(contentsOf: url)
                player.prepareToPlay()
            } catch let error as NSError {
                print(error.description)
            }
        }


        @IBAction func powerButtonPressed(_ sender: Any) {
            cloudHolder.isHidden = false
            darkBlueBG.isHidden = true
            powerButton.isHidden = true

            player.play()

            UIView.animate(withDuration: 2.3, animations: {
            self.rocket.frame = CGRect(x: 0, y: 20, width: 375, height: 402)
            }) { (finished) in
                self.hustleLbl.isHidden = false
                self.onLbl.isHidden = false

            }
        }
    }
Steven
  • 33
  • 4
  • 4
    Every time you use a `!` in Swift, you're saying "I want my code to crash here if anything goes wrong". – Tom Harrington Oct 04 '17 at 20:29
  • @rmaddy I'm not sure this dupe flag is helpful. The OP's problem isn't "I don't understand what unwrapping nil means", but is "my code is the same as my instructor's, why does mine fail when my instructor's doesn't?" – Lily Ballard Oct 05 '17 at 02:51

3 Answers3

2

Please read the documentation for the path method:

https://developer.apple.com/documentation/foundation/bundle/1409670-path

It states that this method can return nil .

Return Value

The full pathname for the resource file, or nil if the file could not be located.

So you should take appropriate precautions by unwrapping the optional by either using guard or using if let in order to prevent a crash.

example:

if let path = Bundle.main.path(forResource: "hustle-on", ofType: "wav") {
    // work with the path value
} else {
    // take appropriate action since path is nil!
}

or

guard
    let path = Bundle.main.path(forResource: "hustle-on", ofType: "wav") else{
        // take appropriate action since path is nil!
        return
   }
Barns
  • 4,750
  • 3
  • 14
  • 28
0

Based on the line you flagged, it looks like the file hustle-on.wav is not included in your bundle resources. Double-check that you have this file in your project. If you do, select it and look at the File Inspector, and double-check that the target is checked.

Lily Ballard
  • 176,187
  • 29
  • 372
  • 338
0

You should never unwrap an optional like that, but instead use guard or if let as follows:

guard let path = Bundle.main.path(forResource: "hustle-on", ofType: "wav") else {
    // Add some logic here because the file wasn't found. Then return because it failed.
    return
}

or

if let path = Bundle.main.path(forResource: "hustle-on", ofType: "wav") {
    let url = URL(fileURLWithPath: path)

    do {
        player = try AVAudioPlayer(contentsOf: url)
        player.prepareToPlay()
    } catch let error as NSError {
        print(error.description)
    }
}

Then it will only try to use the path if it came back from the Bundle.main.path call.

davidethell
  • 11,398
  • 5
  • 40
  • 60