Как установить флаг и передать некоторые значения из контроллера представления модели Popup в основной контроллер представления Tabbar с помощью Swift 4.2?

Мой сценарий: у меня Tabbar с тремя viewcontroller. Здесь первая панель вкладок viewcontroller, я показываю tableview. Если я щелкну ячейку таблицы, она покажет один всплывающий контроллер представления модели. В этом текущем всплывающем окне viewcontroller я поддерживаю две кнопки отмены и готово. Если я нажму «Готово», он закроется и покажет tabbar контроллер основного вида. В то время как dismiss раз мне нужно передать некоторые значения с флагом кнопки из текущего контроллера представления всплывающего окна в основной контроллер представления панели вкладок.

Здесь ниже мой код управления просмотром пропуска popup (VC 2)

@IBAction func apply_click(_ sender: Any) {
        print("Dimiss Filter")
        dismiss(animated: true, completion: {

            if let navView = self.tabBar?.viewControllers?[0] as? UINavigationController {
                if let secondTab = navView.viewControllers[0] as? HomeViewController {
                    secondTab.selectedIndexFromFirstTab = self.selectedIndex
                    //secondTab.item = self.item
                    secondTab.tfData = "YES"
                }
            }
            self.tabBar?.selectedIndex = 0
        })
    }

Здесь Tabbar контроллер основного вида code (получение значений) (VC 1)

override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)

        print("SELECTED INDEX:\(selectedIndexFromFirstTab)")
        print("RESPONSE:\(tfData)")
    }

Я не получаю значения, как решить эту проблему.


person devmikle    schedule 20.02.2019    source источник


Ответы (3)


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

Для этого в первую очередь вам нужно объявить метод в свой основной TabBarViewController

func tabPressedWithIndex(index: Int, valueToPass: String) {
    print("selected Index: \(index)")
    print("Value from user: \(valueToPass)")
}

Теперь вам нужно передать этот контроллер панели вкладок в подробное представление с помощью метода didSelectRowAt, и это будет выглядеть так:

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

    let vc = self.storyboard?.instantiateViewController(withIdentifier: "DetailViewController") as! DetailViewController
    vc.selectedIndex = indexPath.row
    vc.tabBar = self.tabBarController as? TabBarViewController  // Here you need to assign tab bar controller.
    self.present(vc, animated: true, completion: nil)
}

Теперь следующее: когда вы нажимаете кнопку «Отклонить» в контроллере подробного представления, вам нужно добавить одну строку ниже self.tabBar?.selectedIndex = 1:

self.tabBar?.tabPressedWithIndex(index: 1, valueToPass: self.userTF.text!)

Теперь это передаст значения контроллеру основной панели вкладок, а метод tabPressedWithIndex вызовет и распечатает ваши данные на главной вкладке.

Ознакомьтесь с демонстрационным проектом для получения дополнительной информации.

person Dharmesh Kheni    schedule 20.02.2019
comment
Спасибо @Dharmesh Kheni - person devmikle; 20.02.2019

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

Использование протокола

Шаг 1:

Объявите протокол в вашем контроллере модального представления

@objc protocol ModalViewControllerProtocol {
    func dismiss(with data: String)
}

Шаг 2:

ViewController, который представляет этот ModalViewController, позволяет подтвердить протокол

extension HomeViewController: ModalViewControllerProtocol {
    func dismiss(with data: String) {
        //use the data here
        self.presentedViewController?.dismiss(animated: true, completion: nil)
    }
}

Шаг 3.

Объявите переменную для хранения ссылки на делегата в ModalViewController

weak var delegate: ModalViewControllerProtocol? = nil

Шаг 4:

В вашем ViewCOntroller, который представляет modalViewController, передайте себя в качестве делегата ModalViewController перед представлением

    let modalVC = //...
    modalVC.delegate = self
    self.present(modalVC, animated: true, completion: nil)

Наконец, в IBAction ModalViewController просто вызовите

@IBAction func apply_click(_ sender: Any) {
    self.delegate?.dismiss(with: "your_data_here")
}

Использование блокировки/закрытия

Шаг 1:

В вашем модальном ViewController объявите свойство, которое принимает блок/закрытие

var completionBlock: (((String) -> ()))? = nil

Шаг 2:

В вашем ViewController, который представляет этот ModalViewController, передайте блок перед его представлением

    let modalVC = //...
    modalVC.completionBlock = {(data) in
        debugPrint(data)
        self.presentedViewController?.dismiss(animated: true, completion: nil)
    }
    self.present(modalVC, animated: true, completion: nil)

Шаг 3.

Наконец, в IBAction ModalViewController просто выполните переданный блок

    if let block = completionBlock {
        block("your data here")
    }

Надеюсь, поможет

person Sandeep Bhandari    schedule 20.02.2019
comment
Спасибо. Не могли бы вы обновить, какой из них является контроллером основного вида панели вкладок, а какой - контроллером всплывающего окна. судя по моему титулу, это сделает Clea @Sandeep Bhandari - person devmikle; 20.02.2019
comment
@devmikle: я указал, что viewController — это контроллер представления на панели вкладок, где modalViewController — это контроллер представления, который вы планируете представить модально. - person Sandeep Bhandari; 20.02.2019
comment
Извиняюсь. Я не могу понять. Если вы не возражаете, пожалуйста, скажите очень ясно @Sandeep Bhandari - person devmikle; 20.02.2019
comment
@devmikle: это общий ответ, из которого вы можете получить представление о том, как применить его к своему сценарию. - person Sandeep Bhandari; 20.02.2019
comment
@SandeepBhandari Идеальный ответ! - person Harjot Singh; 20.02.2019
comment
Но мой вопрос заключается в передаче данных от ребенка к родительскому. @Сандип Бхандари - person devmikle; 20.02.2019
comment
@Sandeep Bhandari Что делать, если я хочу передать блок другому контроллеру представления, который я не выталкиваю из этого контроллера представления? как мы можем этого добиться? Я знаю с делегатом. - person Harjot Singh; 20.02.2019
comment
@harjot-singh: В любом случае, если вы можете получить ссылку на представленный контроллер представления, передача блока должна быть прямой :) - person Sandeep Bhandari; 20.02.2019
comment
@Sandeep Bhandari Не могли бы вы сделать это с примером в редактировании? Я не могу думать об этом, что у тебя на уме? - person Harjot Singh; 20.02.2019
comment
@harjot-singh: Было бы неуместно добавлять что-либо подобное здесь, так как это выходит за рамки контекста к этому вопросу, рассмотрите возможность добавления нового вопроса, который даст более четкий контекст вашего вопроса, а также откроет вопрос для более широкой аудитории и кто знает, что кто-то с лучшим пониманием может дать лучший ответ :) - person Sandeep Bhandari; 20.02.2019
comment
@Сандип Бхандари, пожалуйста, ответь как можно скорее. stackoverflow.com/questions/54782250/ - person Harjot Singh; 20.02.2019

Это решение

self.dismiss(animated: true) {
            if let tabController = self.presentingViewController as? UITabBarController {
                if let navController = tabController.selectedViewController as? UINavigationController {
                    if let secondTab = navController.viewControllers.first as? HomeViewController {
                        secondTab.tfData = "YES"
                    }
                } else {
                    if let secondTab = tabController.selectedViewController as? HomeViewController {
                        secondTab.tfData = "YES"
                    }
                }
            }
        }
person Nilesh R Patel    schedule 20.02.2019