2016-10-11 28 views
1

NSCollectionViewItemをクリックすると、あるビューから次のビューにデータが渡されるようになっています。アイテムをクリックすると、新しいビューにデータを渡して、各アイテムのより詳細なビューを表示するだけです。1つのView Controllerから別のView Controllerへデータを渡す方法

「致命的なエラーが発生する:オプション値をアンラッピングしている間に予期せずnilが見つかりました」。 ProductDetail.swiftファイルの重要なステップが欠けているような気がします。このエラーは、prepare()メソッドのViewController.swiftの下部に表示されます。 OS Xでこれを行う方法に関するプロセスは、iOSとはまったく異なりますので、どんな助けでも大歓迎です。

ViewController.swift

import Cocoa 

class ViewController: NSViewController { 


@IBOutlet weak var colView: NSCollectionView! 

var productCategories: [ProductCategory]? 

var productsArray: [ProductModel]? 

var detailLabel: test1? 



override func viewWillAppear() { 
    super.viewWillAppear() 

    preferredContentSize = NSSize(width: 1025, height: 1200) 

} 

override func viewDidLoad() { 

    super.viewDidLoad() 

    getJSON() 

} 

func getJSON() { 

    let requestURL: NSURL = NSURL(string: "http://myurl.php")! 
    let urlRequest: NSMutableURLRequest = NSMutableURLRequest(url: requestURL as URL) 
    let session = URLSession.shared 
    let task = session.dataTask(with: urlRequest as URLRequest) { 
     (data, response, error) -> Void in 

     let httpResponse = response as! HTTPURLResponse 
     let statusCode = httpResponse.statusCode 



     if (statusCode == 200) { 

      do{ 

       let json = try JSONSerialization.jsonObject(with: data!, options:.mutableContainers) 

       self.productsArray = [ProductModel]() 

       if let products = json as? [[String: Any]] { 

        for product in products { 

         let testproduct = ProductModel() 

         testproduct.product_name = product["product_name"] as? String 
         testproduct.product_price = product["product_price"] as? String 
         testproduct.product_image = product["product_image"] as? String 



         self.productsArray?.append(testproduct) 



        } 

        DispatchQueue.main.async(){ 

         self.colView.reloadData() 
        } 
       } 

      }catch { 

       print("Error parsing the JSON: \(error)") 
      } 

     } 
    } 

    task.resume() 

} 

override var representedObject: Any? { 
    didSet { 
    // Update the view, if already loaded. 
    } 
} 

} 

extension ViewController: NSCollectionViewDataSource, NSCollectionViewDelegate{ 


func collectionView(_ collectionView: NSCollectionView, numberOfItemsInSection section: Int) -> Int { 

    return productsArray?.count ?? 0 
} 


func collectionView(_ collectionView: NSCollectionView, itemForRepresentedObjectAt indexPath: IndexPath) -> NSCollectionViewItem { 

    let item = collectionView.makeItem(withIdentifier: "test1", for: indexPath) as! test1 

     item.buildProduct = productsArray?[indexPath.item] 

    return item 
} 

func collectionView(_ collectionView: NSCollectionView, didSelectItemsAt indexPaths: Set<IndexPath>) { 

    print("selected") 

    self.performSegue(withIdentifier: "showProductDetail", sender: self) 



} 
override func prepare(for segue: NSStoryboardSegue, sender: Any?) { 


    if (segue.identifier == "showProductDetail") { 

     if let detailVC = segue.destinationController as? ProductDetail { 

     detailVC.testLabel.stringValue = (detailLabel?.label.stringValue)! 

     }else{ 
      detailLabel?.label.stringValue = "failed" 
     } 


    } 


} 
} 

test1.swift

import Cocoa 

class test1: NSCollectionViewItem { 

@IBOutlet weak var label: NSTextField! 
@IBOutlet weak var label2: NSTextField! 
@IBOutlet weak var productImageView: NSImageView! 

var productItem: ProductModel? 


var buildProduct: ProductModel? { 

    didSet{ 

     label.stringValue = (buildProduct?.product_name)! 
     label2.stringValue = (buildProduct?.product_price)! 


     setupAppIconImage() 
    } 
} 


override func viewDidLoad() { 

    super.viewDidLoad() 

} 


func setupAppIconImage() { 

    if let appIconImageURL = buildProduct?.product_image { 
     let url = NSURL(string: appIconImageURL) 

     URLSession.shared.dataTask(with: url! as URL,completionHandler:{(data, response, error) in 

      if error != nil { 
       print(error) 
       return 
      } 

      self.productImageView.image = NSImage(data: data!) 

     }).resume() 

    } 

} 
} 

ProductDetail.swift

import Cocoa 

class ProductDetail: NSViewController { 



@IBOutlet weak var testLabel: NSTextField! 


override func viewDidLoad() { 
    super.viewDidLoad() 
} 

} 
+0

?初期化されていないため、ゼロです。だからあなたのアプリはクラッシュしています。 – Santosh

+1

'didSelectItemAt'メソッドで' let item = collectionView.item(at:indexPaths)を! test1 detailLabel = item' – Santosh

+0

私はあなたの提案を試みましたが、「型の引数リスト(item: '')で 'item'を呼び出せません」というエラーが表示されました。 –

答えて

1

Iそれを理解し終わった。それは私が思ったよりずっと簡単でした。私は、新しいデータを渡すための変数を作成する必要がありました。彼の助けと指導のためにSantoshに感謝します。

ProductDetail.swift

class ProductDetail: NSViewController { 

@IBOutlet weak var testLabel: NSTextField! 

var theBigPass = String() 


override func viewDidLoad() { 
    super.viewDidLoad() 


    testLabel.stringValue = theBigPass 

} 

} 

ViewController.swiftセグエ方法あなたはViewController` ``であなたのdetailLabel`変数を初期化している

func collectionView(_ collectionView: NSCollectionView, didSelectItemsAt indexPaths: Set<IndexPath>) { 

    print("selected") 

    let selectedIndexPath = collectionView.selectionIndexPaths.first 
    let item = collectionView.item(at: selectedIndexPath!) 
    detailLabel = item as! test1? 

    self.performSegue(withIdentifier: "showProductDetail", sender: self) 


} 

override func prepare(for segue: NSStoryboardSegue, sender: Any?) { 



    if (segue.identifier == "showProductDetail") { 


     if let detailVC = segue.destinationController as? ProductDetail { 

      let passed = (detailLabel?.label.stringValue)! 

      detailVC.theBigPass = passed 


     } 

    } 
} 
関連する問題