为什么我不能在函数(Swift3)中访问ViewController变量?

时间:2017-03-26 03:01:55

标签: ios swift

这让我疯了。这应该是世界上最简单的事情,无论我尝试什么,它都无法正常工作。

我想做的事情非常简单。我的视图中有一个文本字段和一个按钮。您在文本字段中输入ID号,然后单击按钮。当您点击按钮时,它会执行Web请求,将ID号发送到PHP脚本,然后处理它并返回一个字符串。我只想将返回的字符串存储到变量中,并通过segue将其发送到新的视图控制器。

到目前为止,这是我的代码:

class ViewController: UIViewController {
    //================ Member Variables ================//
    var customerDetails: NSString = ""

    //================ Object Outlets ================//
    @IBOutlet weak var deviceID: UITextField!

    //================ Object Actions ================//
    @IBAction func checkDeviceID(_ sender: UIButton) {
        print(deviceID.text!)
        validateDevice(deviceID: deviceID.text!)
    }

    override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
        let step2VC: Step2ViewController = segue.destination as! Step2ViewController
        step2VC.deviceID = deviceID.text!
        step2VC.customerDetails = customerDetails
    }

    //================ Custom Methods ================//
    func validateDevice(deviceID: String) {
        //Send a request out to server to validate credentials
        let sessionConfig = URLSessionConfiguration.default
        let session = URLSession(configuration: sessionConfig, delegate: nil, delegateQueue: nil)
        guard let URL = URL(string: "http://monitt.dynamiscms.com/library/getCustomerDetails.php") else {return}
        let request = NSMutableURLRequest(url: URL)

        request.httpMethod = "POST"

        request.addValue("application/json; charset=utf-8", forHTTPHeaderField: "Content-Type")

        let bodyObject: [String: String] = [
            "deviceID": deviceID
        ]

        request.httpBody = try! JSONSerialization.data(withJSONObject: bodyObject, options: [])
        var responseString: NSString = ""

        let task = URLSession.shared.dataTask(with: request as URLRequest) {
            data, response, error in

            if (error == nil) {
                // Success
                let statusCode = (response as! HTTPURLResponse).statusCode
                print("URL Session Task Succeeded: HTTP \(statusCode)")

                responseString = NSString(data: data!, encoding: String.Encoding.utf8.rawValue)!
                self.customerDetails = responseString

                print("responseString = \(responseString)")
            }
            else {
                // Failure
                print("URL Session Task Failed: %@", error!.localizedDescription);
            }
        }

        task.resume()
        session.finishTasksAndInvalidate()

        performSegue(withIdentifier: "setupStep2", sender: nil)
    }
}

在我的validateDevice函数中,我有print语句,它成功显示了PHP脚本返回的结果。但是,尽管事实上我在函数之外预先定义了变量,但我仍然无法获得customerDetails变量来保存脚本返回的结果。

任何人都可以对我做错了什么有所了解吗?

一个成功的答案是允许我将“customerDetails”的内容设置为下一个ViewController中的文本字段,并让它包含来自Web脚本的内容。

2 个答案:

答案 0 :(得分:2)

您应该在网络通话结束后执行Segue

WebProject1.config

此外,无需致电

 let task = URLSession.shared.dataTask(with: request as URLRequest) {
        data, response, error in

        if (error == nil) {
            // Success
            let statusCode = (response as! HTTPURLResponse).statusCode
            print("URL Session Task Succeeded: HTTP \(statusCode)")

            responseString = NSString(data: data!, encoding: String.Encoding.utf8.rawValue)!
            self.customerDetails = responseString
            //Here
            self.performSegue(withIdentifier: "setupStep2", sender: nil)
            print("responseString = \(responseString)")
        }
        else {
            // Failure
            print("URL Session Task Failed: %@", error!.localizedDescription);
        }
    }

    task.resume()

答案 1 :(得分:0)

你会使用self,看起来就像你一样。

在访问(或通过)customerDetails之前,您是否等待网络通话完成后?

performSegue(forIdentifier:sender:)调用移至网络调用内部。编辑器会警告您,您需要添加self

func validateDevice(deviceID: String) {

    //Send a request out to server to validate credentials

    let sessionConfig = URLSessionConfiguration.default
    let session = URLSession(configuration: sessionConfig, delegate: nil, delegateQueue: nil)
    guard let URL = URL(string: "http://monitt.dynamiscms.com/library/getCustomerDetails.php") else {return}
    let request = NSMutableURLRequest(url: URL)

    request.httpMethod = "POST"

    request.addValue("application/json; charset=utf-8", forHTTPHeaderField: "Content-Type")

    let bodyObject: [String: String] = [
        "deviceID": deviceID
    ]

    request.httpBody = try! JSONSerialization.data(withJSONObject: bodyObject, options: [])
    var responseString: NSString = ""

    let task = URLSession.shared.dataTask(with: request as URLRequest) {
        data, response, error in

        if (error == nil) {
            // Success
            let statusCode = (response as! HTTPURLResponse).statusCode
            print("URL Session Task Succeeded: HTTP \(statusCode)")

            responseString = NSString(data: data!, encoding: String.Encoding.utf8.rawValue)!
            self.customerDetails = responseString

            print("responseString = \(responseString)")
            self.performSegue(withIdentifier: "setupStep2", sender: nil)
        }
        else {
            // Failure
            print("URL Session Task Failed: %@", error!.localizedDescription);
        }
    }

    task.resume()
}