2017-05-26 80 views
2

所以我有一个UIAlertController,有2个文本框,然后我想监视每当这些文本框编辑,看看他们是否符合一定的标准。如何使用#selector函数传递变量?以及传递给textField:UITextField的内容?

在这种情况下,只要两个文本字段的输入都短于要传递给该函数的数字,我希望我的警报按钮处于非活动状态。

所以我加入这个目标到两个文本框:

textField.addTarget(自我,动作:#selector(self.handleTextFieldEdit),用于:.editingChanged)

内handleTextFieldEdit我有这样的:

func handleTextFieldEdit(_ textField: UITextField, number: Int) 
{ 
    let number = number 
    let alertController:UIAlertController = self.presentedViewController as! UIAlertController; 
    let textField: UITextField = alertController.textFields![0] 
    let confirmField: UITextField = alertController.textFields![1] 
    let addAction: UIAlertAction = alertController.actions[0]; 

    if ((textField.text?.characters.count)! > number && (confirmField.text?.characters.count)! > number) 
    { 
     addAction.isEnabled = true 
    } 
    else if ((textField.text?.characters.count)! <= number || (confirmField.text?.characters.count)! <= number) 
    { 
     addAction.isEnabled = false 
    } 
} 

现在我的第一个问题是我似乎无法通过#selector func传递任何变量。

我的第二个问题是,我不知道该怎么传递给_文本框:的UITextField

我曾经尝试都的UITextField和文本框(这是我宣布我的UITextFields到)。

出现的错误是:无法将类型'UITextField'.Type的值转换为期望的参数类型'UITextField'。

编辑:我所有的代码工作,只要我不通过一个变量与函数btw。问题是我希望每当我调用函数时都改变最小值。

回答

0

这是一些测试代码。基本上,我已经子类UIAlertViewController,添加功能以添加UITextFieldsUIAlertAction

通过传递包含最小长度和占位符值的元组(Int,String)来创建文本字段。 OK按钮在创建时被禁用。

在内部,我已经添加了handleTextFieldEdit()函数,但是重构了。它在第二个数组中设置一个Bool - 您可以简单地使用一个数组,但这只是一个示例 - 然后调用一个新函数来设置okButton.isEnabled属性。

在我UIViewController

public func showAlert(_ title:String, _ message:String) { 

    // use the subclassed UIAlertViewController 
    // - add two text fields with minimum length and placeholders 
    // - add an OK button 

    let alertVC = MyAlertController(
     title: "MyTitle", 
     message: "MyMessage", 
     preferredStyle: .alert) 
    alertVC.addTextFields([(5,"Enter First Name"),(10,"Enter Last Name")]) 
    alertVC.addOkAction() 

    present(
     alertVC, 
     animated: true, 
     completion: nil) 
} 

我的子类UIAlertViewController:

class MyAlertController: UIAlertController { 

    var textMinLengths = [Int]() 
    var textMinLengthsReached = [Bool]() 
    var okAction:UIAlertAction! 

    // add UITextFields: 
    // - append textMinLengths[] 
    // - set placeholder 
    // - append "false" to textMinLengthsReached[] 
    // - set tag value to array index 
    // - add target action handleTextFieldEdit() 

    func addTextFields(_ textConfigs:[(Int,String)]) { 
     var tagValue:Int = 0 
     for textConfig in textConfigs { 
      textMinLengths.append(textConfig.0) 
      textMinLengthsReached.append(false) 
      self.addTextField { (textField : UITextField!) -> Void in 
       textField.placeholder = textConfig.1 
       textField.tag = tagValue 
       textField.addTarget(self, action: #selector(self.handleTextFieldEdit(_:)), for: .editingChanged)   } 
      tagValue += 1 
     } 
    } 

    // add a *disabled* OK button 

    func addOkAction() { 
     okAction = UIAlertAction(
      title: "OK", 
      style: .cancel, 
      handler: { action -> Void in 
     }) 
     self.addAction(okAction) 
     okAction.isEnabled = false 
    } 

    // every keystroke, check the character count against the minimum, setting if it's been reached, 
    // always checking whether to show alert action afterwards 

    func handleTextFieldEdit(_ sender: UITextField) { 
     if (sender.text?.characters.count)! >= textMinLengths[sender.tag] { 
      textMinLengthsReached[sender.tag] = true 
     } else { 
      textMinLengthsReached[sender.tag] = false 
     } 
     showAlertAction() 
    } 

    // loop through textMinLengthsReached, setting okButton.isEnabled 

    func showAlertAction() { 
     var isEnabled = true 
     for textMinLengthReached in textMinLengthsReached { 
      if !textMinLengthReached { 
       isEnabled = false 
       break 
      } 
     } 
     okAction.isEnabled = isEnabled 
    } 
} 
+0

非常感谢您的详细解答! – Elhoej

0

试试下面的代码

textField.addTarget(self, action: #selector(self.handleTextFieldEdit(sender:)), for: .editingChanged) 

func handleTextFieldEdit(sender: UITextField) { 
} 
+0

我不知道这将如何解决我的问题?你能再解释一下吗? – Elhoej

1

你想一个额外的参数(一个int)添加到IBAction选择。你不能那样做。 IBActions有3个选择器之一:

@IBAction func actionNoParams() { 
} 

@IBAction func actionWSender(_ sender: Any) { 
} 

@IBAction func actionWSenderAndEvent(_ sender: Any, forEvent event: UIEvent) { 
} 

这些是你唯一的选择。您不能添加其他参数,或者更改任一可能参数的类型。

当控件需要调用目标/动作时,系统会调用您的函数。 (任何时候当您向控件添加目标/动作时,即使您没有使用@IBAction关键字标记您的功能,您也必须使用上述功能签名之一(您应该真的在做这些事情,顺便说一下)。

+0

为什么要将@IBAction添加到我的代码中?是不是只用于故事板? – Elhoej

+1

这是很好的做法。它表明函数正在被目标/动作中的控件调用。 –

0

,以追踪在文本字段更改一些对象必须是例如当您创建AlertController与文本字段内,你应该指定委托给它这个文本字段

的代表。

方法内某处一些YourViewController的:

self.alertView = UIAlertController.init(title: "Your title", message: Your message", preferredStyle: .alert) 
self.alertView.addTextField(configurationHandler: { textfield in 
textfield.font = UIFont.fontProximaNovaLight(18) 
textfield.textColor = UIColor.colorAppLightGray2() 
textfield.keyboardType = .default 
textfield.delegate = self 
}) 

扩展您的viewController:

extension YourViewController: UITextFieldDelegate { 

    func textField(_ textField: UITextField, 
        shouldChangeCharactersIn range: NSRange, 
        replacementString string: String) -> Bool { 

     let text = textField.text?.replacingCharacters(in: range.toRange(textField.text!), with: string) 
     // some test verification 
     // for example you can use your function to verify textfield against value 
     // validate (textfield, number) 



     if text?.characters.count > 0 { 
      self.alertView.actions[0].isEnabled = true 
     } else { 
      self.alertView.actions[0].isEnabled = false 
     } 

     return true 
    } 
} 
0

子类的UITextField,并添加另一个属性用于您的长度要求。然后,您可以将其作为发件人的一部分阅读。