2017-08-30 48 views
0

我有一個的tableView在SubMenuViewController,當用戶點擊一個細胞和塞格斯(使用didSelectRowAt),我需要的是細胞傳遞到下一個UserInputViewController如何從performSegue()傳遞indexPath值prepareForSegue()

這裏是我的代碼:

class SubMenuViewController: UIViewController { 

    //MARK: - Properties and outlets 

    var node: Node? 
    @IBOutlet weak var tableView: UITableView! 

    //MARK: - View controller methods 

    override func viewDidLoad() { 

     super.viewDidLoad() 

     self.navigationController?.isNavigationBarHidden = false 
     self.navigationItem.title = node?.value.rawValue 

     let nib = UINib(nibName: "SubMenuTableViewCell", bundle: nil) 
     tableView.register(nib, forCellReuseIdentifier: "SubMenuCell") 
    } 

    override func prepare(for segue: UIStoryboardSegue, sender: Any?) { 
     if segue.identifier == "userInput" { 
      let vc = segue.destination as! UserInputViewController 
      let indexPath = sender as! IndexPath 
      vc.node = node?.childenNode[indexPath.row] 
     } 
    } 
} 

//MARK: UITableViewDataSource methods 

extension SubMenuViewController: UITableViewDataSource { 

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int { 
     return node!.childCount 
    } 

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { 

     let cell = tableView.dequeueReusableCell(withIdentifier: "SubMenuCell", for: indexPath) as! SubMenuTableViewCell 
     let desciptionModule = node?.childenNode[indexPath.row].value 

     let description = Modules.description(module: desciptionModule!) 

     cell.title.text = description.main 
     cell.subtitle.text = description.sub 

     return cell 
    } 
} 

//MARK: - UITableViewDelegate methods 

extension SubMenuViewController: UITableViewDelegate { 
    func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat { 
     return 68 
    } 

    func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { 

     tableView.deselectRow(at: indexPath, animated: true) 

     guard let selectedNode = node?.childenNode[indexPath.row] else { 
      return 
     } 

     if selectedNode.isLeaveNode() { 
      performSegue(withIdentifier: "userInput", sender: indexPath) 
     } else { 
      let subMenuViewController = self.storyboard!.instantiateViewController(withIdentifier: "subMenu") as! SubMenuViewController 
      subMenuViewController.node = selectedNode 
      //let subMenuViewController = SubMenuViewController(node: selectedNode) 
      self.navigationController?.pushViewController(subMenuViewController, animated: true) 
     } 
    } 
} 

現在,在我的performSegue,我通過我的indexPath到發送者,我應該會找回來的prepareForSegue,但我不能。任何建議傢伙?

感謝

+0

你說這行'讓indexPath =發件人作爲! IndexPath'崩潰? –

+0

您是否嘗試將選定的索引路徑作爲屬性存儲在SubMenuViewController中(選中單元格時),然後在需要時使用它(例如在prepareForSegue中)? –

+0

@ArtKirillov這是一種解決方法,但他的方法是有效的,必須工作,糾正我,如果我錯了 –

回答

1

我看來它不是通過索引路徑(或計數一個的「數據」的任何其他數值)作爲sender參數非常好的做法;顧名思義,它旨在傳遞發送消息的對象(即,稱爲操作方法),在這種情況下爲self(如果您的操作方法調用另一個操作方法,則可以「中繼」原始發件人,但這是在這裏討論)。

正如@sCha在評論中指出的那樣,儘管如此,蘋果關於這種方法的文檔似乎仍然有疑問。參數名稱發送者顯然來自遵循Cocoa標籤/動作模式的所有控制動作中的同聲參數。

我的建議:

,你可以做我認爲最好是指數路徑在您的視圖控制器的財產

var selectedIndexPath: IndexPath? 

... 將其設置爲 on tableView(_:didSelectRowAt:)

if selectedNode.isLeaveNode() { 
    self.selectedIndexPath = indexPath 
    performSegue(withIdentifier: "userInput", sender: indexPath) 
} else { 
    self.selectedIndexPath = nil 
    // ... 

...和retieve它(並重置)在prepareForSegue(_:sender:)實現目標視圖控制器:

if let vc = segue.source as? SubmenuViewController { 
    if let indexPath = vc.selectedIndexPath { 
     vc.selectedIndexPath = nil // (reset it, just to be safe) 

     // Use indexPath... 
    }  
} 
+1

我不認爲使用'sender'是不好的做法。 Apple文檔將這個'sender'解釋爲:**您想用來啓動segue的對象。該對象在實際過程中可用於提供信息。**您可以發送任何想要啓動搜索的信息。 – sCha

+0

謝謝你指出。 「用於引導這個部分」部分似乎重申了我所說的。「對象可用於信息目的」部分更加模糊,我同意......取決於「信息」是什麼(不限於「傳遞的數據」)。在任何情況下,我都根據所有**控制**行爲共同的歷史發件人論點(我相信即使對於'prepareForSegue()'這個名稱來說) –