2016-10-19 7 views
10

Я следовал инструкциям here, но я все еще не уверен в этой части:Как передать данные из модального контроллера представления обратно, когда уволенный

modalVC.delegate=self; 
     self.presentViewController(modalVC, animated: true, completion: nil) 

Я попытался инстанцирование контроллера представления программно, но все еще нет.

вот мой код, когда отклоняя модальный контроллер представления:

@IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
     self.dismiss(animated: true) { 
      // 
     } 
    } 

Я использую раскадровку для модальных с непосредственно перейти зрения.

Это данные, которые я хотел бы передать обратно в контроллер родительского вида:

var typeState = "top" 
var categoryState = "casual" 

Какие два значения строк.

Edit:

Я пытался передать данные из модальный контроллер представления, как показано:

@IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
     self.dismiss(animated: true, completion: nil) 
     delegate?.sendValue(value: "success") 
     if let presenter = presentingViewController as? OOTDListViewController { 
      presenter.receivedValue = "test" 
     } 
    } 

в то время как на контроллере родительского вида я сделал так:

func sendValue(value: NSString) { 
     receivedValue = value as String 
    } 
    @IBAction func printReceivedValue(_ sender: UIButton) { 
     print(receivedValue) 
    } 

Я все равно не получаю никакого значения, когда нажимаю кнопку печати.

модальный контроллер представления:

protocol ModalViewControllerDelegate 
{ 
    func sendData(typeState: String, categoryState: String) 
} 

var delegate:ModalViewControllerDelegate! 

var typeState = "top" 
var categoryState = "casual" 
@IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
     self.dismiss(animated: true, completion: nil) 
     delegate?.sendData(typeState: typeState as String, categoryState: categoryState as String) 

    } 

Родитель-контроллер:

class parentViewController: UICollectionViewController, ModalViewControllerDelegate { 

var typeState: String? 
var categoryState: String? 
func sendData(typeState: String, categoryState: String) { 
     self.typeState = typeState as String 
     self.categoryState = categoryState as String 
    } 
@IBAction func printReceivedValue(_ sender: UIButton) { 
    print(typeState) 
} 

Edit:

Вот мой новый код без использования метода делегата:

модальный вид контроллера:

@IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
     self.dismiss(animated: true, completion: nil) 
     if let presenter = presentingViewController as? OOTDListViewController { 
      presenter.typeState = typeState 
      presenter.categoryState = categoryState 
     } 
    } 

OOTDListViewController:

@IBAction func presentModalView(_ sender: UIBarButtonItem) { 
     let modalView = storyboard?.instantiateViewController(withIdentifier: "filterViewController") as! ModalViewController 
     let navModalView: UINavigationController = UINavigationController(rootViewController: modalView) 
     self.present(navModalView, animated: true, completion: nil) 
    } 
@IBAction func printValue(_ sender: UIButton) { 
     print(typeState) 
     print(categoryState) 
    } 
+0

Вы представляете viewcontroller с помощью segue или кода? – smeshko

+0

Я представляю модальный просмотр с раскадрой segue – Wilson

+0

печать все еще вернула нуль или пустой ответ – Wilson

ответ

8

В зависимости от данных, которые вы хотите передать, вы можете создать свойство в контроллере представления представления, которые вы можете установить при отклонении контроллера представления модального, так что вы можете сэкономить себе делегат.

Например, у вас есть ContactsViewController, содержащий var contacts: [Contact] = []. Когда вы хотите создать новый контакт, вы представляете контроллер модального представления с разными значениями, необходимыми для создания нового объекта Contact. Когда вы закончите и хотите отклонить контроллер вида, вы вызываете функцию так же, как и в своем коде, но устанавливаете свойство в ContactsViewController.Это будет выглядеть примерно так:

@IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
    if let presenter = presentingViewController as? ContactsViewController { 
     presenter.contacts.append(newContact) 
    } 
    dismiss(animated: true, completion: nil) 
} 

EDIT:

Если вы не хотите использовать делегат, это то, как вы идете по этому поводу:

В вашем OOTDListViewController :

var testValue: String = "" 

@IBAction func printReceivedValue(_ sender: UIButton) { 
    print(testValue) 
} 

В вашем модульном контроллере (я назову его)):

@IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
    // if your OOTDListViewController is part of a UINavigationController stack, this check will probably fail. 
    // you need to put a breakpoint here and check if the presentingViewController is actually a UINavigationController. 
    // in that case, you will need to access the viewControllers variable and find your OOTDListViewController 
    if let presenter = presentingViewController as? OOTDListViewController { 
     presenter.testValue = "Test" 
    } 
    dismiss(animated: true, completion: nil) 
} 

Если вы хотите использовать делегат, это то, как сделать это:

В вашем OOTDListViewController:

protocol ModalDelegate { 
func changeValue(value: String) 
} 

class OOTDListViewController: ModalDelegate { 

var testValue: String = "" 
@IBAction func presentViewController() { 
    // here, you either create a new instance of the ViewController by initializing it, or you instantiate it using a storyboard. 
    // for simplicity, I'll use the first way 
    // in any case, you cannot use a storyboard segue directly, bevause you need access to the reference of the presentedViewController object 
    let presentedVC = PresentedViewController() 
    presentedVC.delegate = self 
    present(presentedVC, animated: true, completion: nil) 
} 

func changeValue(value: String) { 
    testValue = value 
    print(testValue) 
} 

}

В вашей PresentedViewController :

class PresentedViewController { 
    var delegate: ModalDelegate? 
    var testValue: String = "" 

    @IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
     if let delegate = self.delegate { 
      delegate.changeValue(testValue) 
     } 
     dismiss(animated: true, completion: nil) 
    } 

} 
+0

Извините, но Я действительно не понимаю, как это значение можно вернуть обратно в родительский контроллер представления. они сказали использовать метод создания протокола в модальном представлении, а затем создать функцию, которая получит это значение в родительском контроллере представления. Я сделал все это, кроме той части, которую я выделил и не мог получить никаких данных. – Wilson

+0

Я использовал метод non delegate, и я создал все по коду. Но мне нужна панель навигации, если бы не было верхнего бара, чтобы я мог сделать простую кнопку. Я обновил свой пост с текущим кодом, который я использую. – Wilson

0

Вам нужно вызвать метод делегата в dismissViewController метода

@IBAction func dismissViewController(_ sender: UIBarButtonItem) { 
     delegate?.sendData(typeState: "top", categoryState: "casual") 
     self.dismiss(animated: true) { 
      // 
     } 
} 

в вас Модальные ViewController класс создать делегат

var delegate: MyProtocol? 

создать протокол с именем метода SendData в MyProtocol и в вашем presentingViewController где вы назначают делегата, внедряют метод MyProtocol

protocol MyProtocol: class { 
    func sendData(typeState: String, categoryState: String) 
} 

class ViewController: UIViewController, MyProtocol { 
    var typeState: String? 
    var categoryState: String? 

    func sendData(typeState: String, categoryState: String) { 
     self.typeState = typeState 
     self.categoryState = categoryState 
    } 
} 
+0

Нет еще не работает. Просто чтобы уточнить, предполагается, что протокол должен быть создан в скоростном файле контроллера модального представления? Может быть, потому, что я использовал раскадровую сегу, чтобы представить контроллер модального зрения, и поэтому его не работает? – Wilson

+0

протокол должен быть создан отдельно от модального или представленного класса. следуйте данному ответу – suhit

0

Я использую табуляцию, так что рабочий код ниже

  if let tabBar = self.presentingViewController as? UITabBarController { 
      let homeNavigationViewController = tabBar.viewControllers![0] as? UINavigationController 
      let homeViewController = homeNavigationViewController?.topViewController as! HomeController 
      homeViewController._transferedLocationID = self.editingLocationID! 
     }