简体   繁体   English

如何将UIDatePicker的背景颜色设置为UITextField inputView?

[英]How to change background color of UIDatePicker set as UITextField inputView?

Please do not mark as duplicate. 请不要标记为重复。 The available answers haven't answered my issue. 可用的答案没有回答我的问题。

I am using a UIDatePicker as UITextField's inputView (inside a UITableViewCell ): 我使用UIDatePicker作为UITextField's inputView (在UITableViewCell ):

@IBOutlet weak var theTextField: UITextField!

func textFieldDidBeginEditing(_ textField: UITextField) {

        let picker = UIDatePicker()
        picker.setValue(Colors.CI2, forKeyPath: "textColor")

        picker.datePickerMode = .date

        textField.inputView = picker
        textField.inputView?.backgroundColor = Colors.CI1 // my desired color

        picker.addTarget(self, action: #selector(datePickerValueChanged), for: .valueChanged)

}

The problem: The color does only change, once the picker is called a second time. 问题:一旦第二次调用选择器,颜色只会改变。

在此输入图像描述 在此输入图像描述

I guess, that this issue occurs because the inputView is optional and only once the picker is called a second time, the inputView is instantiated at the moment where I want to change the color. 我想,出现这个问题是因为inputView是可选的,只有在第二次调用inputView时, inputView才会在我想要更改颜色的时刻实例化。

I have tried to subclass UITextField and observe inputView . 我试图inputView UITextField并观察inputView

class DateTextField: UITextField {

    override var inputView: UIView? {

        didSet {

            self.inputView?.backgroundColor = Colors.CI1
            self.reloadInputViews()

        }

    }

}

Unfortunately without success. 很遗憾没有成功。 Same behavior. 相同的行为。 What am I missing? 我错过了什么? Help is very appreciated. 非常感谢帮助。

The mistake was that I had set the keyboard appearance in the Interface Builder. 错误是我在Interface Builder中设置了键盘外观。 Once set back to default it worked like it was supposed to. 一旦恢复到default它就像它应该的那样工作。

在此输入图像描述

您可以使用以下库来自定义颜色https://github.com/prolificinteractive/PIDatePicker

create a function which holds the date picker colours, and call it in the textFieldDidBeginEditing . 创建一个保存日期选择器颜色的函数,并在textFieldDidBeginEditing调用它。 I think that should solve your issue. 我认为这应该可以解决你的问题。

So you mention that this text field is within a UITableViewCell ... What I would suggest is adding the first block of code to a UITextFieldDelegate and then in the tableView(_:willDisplay:forRowAt:) function in the UITableViewDelegate , set the delegate of the text field to your custom UITextFieldDelegate . 所以你提到这个文本字段在UITableViewCell ...我建议将第一个代码块添加到UITextFieldDelegate然后在UITableViewDelegate中的tableView(_:willDisplay:forRowAt:)函数中,设置委托自定义UITextFieldDelegate的文本字段。

Without knowledge of more of your code structure I can only provide you with a very generic implementation: 如果不了解更多代码结构,我只能为您提供非常通用的实现:

@IBOutlet weak var theTextField: UITextField!

//Add your customisation to the textField...
extension ViewController : UITextFieldDelegate {
    func textFieldDidBeginEditing(_ textField: UITextField) {

            let picker = UIDatePicker()
            picker.setValue(Colors.CI2, forKeyPath: "textColor")

            picker.datePickerMode = .date

            textField.inputView = picker
            textField.inputView?.backgroundColor = Colors.CI1 // my desired color

            picker.addTarget(self, action: #selector(datePickerValueChanged), for: .valueChanged)

    }
}

extension ViewController : UITableViewDelegate {
    //Set the delegate when the UITableViewCell appears:
    func tableView(_ tableView: UITableView, 
                willDisplay cell: UITableViewCell, 
                   forRowAt indexPath: IndexPath) {
        let dateCell = = self.tableView.dequeueReusableCellWithIdentifier("cell") as! DateCell

        dateCell.delegate = self

        return dateCell
    }
}

Do not change inputView in textFieldDidBeginEditing() . 不要在textFieldDidBeginEditing()更改inputView The last time you can change the textField.inputView property is in textFieldShouldBeginEditing() . 您最后一次更改textField.inputView属性是在textFieldShouldBeginEditing()

As for the best practice: you should move all the code for the textView.inputView configuration to the place where you create the textView to do a one time configuration . 至于最佳实践:您应该将textView.inputView配置的所有代码移动到创建textView以进行一次性配置 For instance: 例如:

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    // get the cell
    // get your instance of textField
    // ...

    // Configure everything you want about your input view
    let picker = UIDatePicker()
    picker.setValue(Colors.CI2, forKeyPath: "textColor")
    picker.datePickerMode = .date
    picker.backgroundColor = Colors.CI1
    textField.inputView = picker // <-- You just have to assign this ONCE

    // ... Continue your setup ...
    return cell
}

If you need to change the configuration of the inputView each time it has to appear on screen, do the change of textView.inputView = ... in textFieldShouldBeginEditing(){ ... } . 如果每次必须在屏幕上显示时需要更改inputView的配置,请在textFieldShouldBeginEditing(){ ... }更改textView.inputView = ...


Why it did not work 为什么它不起作用

In your code (when you do the change in textField DID BeginEditing ), the UIDatePicker shown was always the previously created one. 在您的代码中(当您在textField DID BeginEditing进行更改时),显示的UIDatePicker始终是先前创建的。 It seems that the gray one was set (but not configured) when you created the textField instance. 在创建textField实例时,似乎设置了灰色的(但未配置)。

In textFieldDidBeginEditing() , the system has already drawn the textView.inputView and it will NOT look again at the inputView property if you modify it. textFieldDidBeginEditing()该系统已经提请textView.inputView它不会再次在看inputView如果你修改属性。

This code is working for me 这段代码对我有用

func textFieldDidBeginEditing(_ textField: UITextField) {   
        let picker = UIDatePicker()
        picker.datePickerMode = .date

        textField.inputView = picker
        textField.inputView?.backgroundColor = UIColor.blue

}

截图

Even on the first edit it shows up blue. 即使在第一次编辑时它也显示为蓝色。

Also: 也:

Instead of creating a picker instance inside textField delegate method, you could create the picker in viewDidLoad method, set its background color, give it a tag and then access this picker using the tag in the delegate method instead of creating the variable there. 您可以在viewDidLoad方法中创建选择器实例,设置其背景颜色,为其指定标签,然后使用委托方法中的标记访问此选择器,而不是在那里创建变量,而不是在textField委托方法中创建选取器实例。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM