从班级

时间:2017-03-18 20:02:42

标签: ios swift uiview swift3

我正在使用Swift 3,当登录成功时,我想从我班上的一个函数中改变我的观点。

我有一个包含此功能的 LoginViewController

static let sharedInstance = LoginViewController()

//...

func showNextView() {
    let storyboard = UIStoryboard(name: "Main", bundle: Bundle.main)
        guard let eventVC = storyboard.instantiateViewController(
            withIdentifier: "EventsTVC") as? EventsTableViewController else {
                assert(false, "Misnamed view controller")
                return
    }
    self.present(eventVC, animated: false, completion: nil)
}

在我的班级APIManager中,我使用 Alamofire 在我的异步方法中调用此函数:

func processAuth(_ data: [String: String]) {
    print("-- auth process started")

    //... defining vars

    Alamofire.request(tokenPath, method: .post, parameters: tokenParams, encoding: JSONEncoding.default, headers: tokenHeader)
        .responseJSON { response in
            guard response.result.error == nil else {
                print(response.result.error!)
                return
            }

            guard let value = response.result.value else {
                print("No string received in response when swapping data for token")
                return
            }

            guard let result = value as? [String: Any] else {
                print("No data received or data not JSON")
                return
            }

            // -- HERE IS MY CALL
            LoginViewController.sharedInstance.showNextView()

            print("-- auth process ended")
    }
}

我的控制台会返回以下错误消息:

  

- auth进程开始
2017-03-18 20:38:14.078043警告:尝试出现    谁的观点不在窗口   层次!
   - 身份验证过程已结束

我认为在异步方法结束时更改我的视图不是最好的做法。

我不知道自己要做什么。目前,这是一个过程:

  1. 用户打开应用程序,如果没有保存令牌,则显示LoginViewController(Facebook登录)
  2. 如果必须登录,则会显示“使用Facebook登录”按钮
  3. 登录成功后,我在processAuth()
  4. APIManager class功能中发送Facebook数据
  5. 当我的API返回令牌时,我将其保存并将视图更改为EventsTVC
  6. 我把问题放在哪里。我想知道这是否是我案例中的最佳做法。如果是这样,如何避免我的错误消息?

    我希望自己明白了。谢谢你的帮助!

1 个答案:

答案 0 :(得分:1)

实际发生的是,您的单例实例LoginViewController想要在不在视图层次结构中时呈现自己。让我彻底解释一下:

class LoginViewController: UIViewController {
    static let sharedInstance = LoginViewController()

    func showNextView() {
        ...
        // presentation call
        self.present(eventVC, animated: false, completion: nil)
    }

在此函数中,您将从您的单例实例中调用present()。您必须从(最好)位于视图层次结构堆栈顶部的视图中调用它。解决方案可能首先不是在VC上使用单例。您应该从当前在屏幕上的VC实例化并呈现它。希望这有帮助!