【问题标题】:UIDatePicker in UITextField in UITableView with custom UITableViewCell: realtime update带有自定义 UITableViewCell 的 UITableView 中的 UITextField 中的 UIDatePicker:实时更新
【发布时间】:2018-06-29 23:42:03
【问题描述】:

我的情况与这个问题完全相同:

UIDatePicker in UITextField in UITableView realtime update

总而言之:我在自定义单元格中有一个文本字段,它调用 UIDatePicker。我希望在修改日期选择器时更新文本字段,并且我希望它在点击“完成”按钮(位于为日期选择器创建的工具栏内)时存储最后一个值。

我可以获得在选择器视图中选择的值(我实际上将它打印到控制台),但我无法将该值放入文本字​​段中。

但是,我需要快速完成,但我做不到。我一直在尝试使用 action: #selector() 但由于它在选择器内的函数中不接受超过 1 个参数,因此对我没有帮助。

自定义表格视图单元格:

class employeesTableViewCell : UITableViewCell {
   @IBOutlet weak var employeeNumberField: UILabel!
   @IBOutlet weak var employeeNameField: UITextField!
   @IBOutlet weak var employeeSurnameField: UITextField!
   @IBOutlet weak var employeeIDField: UITextField!
   @IBOutlet weak var employeeBirthDateTxtFieldOutlet: UITextField!
}

在 ViewController 中(下图的标签策略是用于捕获通过 textFieldShouldReturn 编辑的字段):

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "employeeCell") as! employeesTableViewCell!

    createPickerView(sender:  (cell?.employeeBirthDateTxtFieldOutlet)!)
    createToolbar(sender:  (cell?.employeeBirthDateTxtFieldOutlet)!)

    cell?.employeeNameField.tag = indexPath.row * 10 + 1
    cell?.employeeSurnameField.tag = indexPath.row * 10 + 2
    cell?.employeeIDDocField.tag = indexPath.row * 10 + 3
    cell?.employeeBirthDateTxtFieldOutlet.tag = indexPath.row * 10 + 5
    cell?.employeeNumberField.text = "Employee \(indexPath.row + 1)"

    return cell!
}

func createPickerView(sender: UITextField){
    let datePickerView : UIDatePicker = UIDatePicker()

    datePickerView.datePickerMode = UIDatePickerMode.date
    sender.inputView = datePickerView
    datePickerView.tag = sender.tag
    datePickerView.addTarget(self, action: #selector(datePickerValueChanged(caller:destination:)), for: UIControlEvents.valueChanged)
}

@objc func datePickerValueChanged(caller: UIDatePicker, destination: UITextField){
    let dateFormatter = DateFormatter()
    dateFormatter.dateStyle = DateFormatter.Style.medium
    dateFormatter.timeStyle = DateFormatter.Style.none

    destination.text = dateFormatter.string(from: caller.date)  <-- I expected I could update the text here, as I'm referencing it through the parameter, but it doesn't work. However, no error is raised.
}



func createToolbar(sender: UITextField){
    let datePickerToolbar = UIToolbar()
    datePickerToolbar.sizeToFit()

    let doneButton = UIBarButtonItem(title: "Done", style: .plain, target: self, action: #selector(employeeRegisterController.dismissKeyboard))
    doneButton.tag = sender.tag

    datePickerToolbar.setItems([doneButton], animated: false)
    datePickerToolbar.isUserInteractionEnabled = true

    sender.inputAccessoryView = datePickerToolbar
}

@objc func dismissKeyboard(on: UIButton){
    view.endEditing(true)
}

【问题讨论】:

  • 请贴出您尝试编写的代码

标签: ios swift uitableview uidatepicker programmatically


【解决方案1】:

#selector() 中不能传递多个参数,但可以使用附加参数传递位置

然后改变下面两个函数

func createPickerView(sender: UITextField){
    let datePickerView : UIDatePicker = UIDatePicker()

    datePickerView.datePickerMode = UIDatePickerMode.date
    sender.inputView = datePickerView
    datePickerView.tag = sender.tag
    datePickerView.addTarget(self, action: #selector(datePickerValueChanged(caller:)), for: UIControlEvents.valueChanged)
}

 func datePickerValueChanged(caller: UIDatePicker){
    let dateFormatter = DateFormatter()
    dateFormatter.dateStyle = DateFormatter.Style.medium
    dateFormatter.timeStyle = DateFormatter.Style.none

    let indexRow = (caller.tag - 5) / 10

    let indexPath = IndexPath(row: indexRow, section: 0)
    let cell = tableView.cellForRow(at: indexPath) as! employeesTableViewCell

    cell.employeeBirthDateTxtFieldOutlet.text = dateFormatter.string(from: caller.date)  
}

希望对你有帮助

【讨论】:

  • 非常感谢!!我今天会测试它,我会让你知道结果。我有一个关于 indexPath 的问题:我曾想过这样做,但在这个论坛的其他帖子中,有人说在 tableView 函数之外使用它不是一个好习惯。我误会了吗?
  • 刚刚测试过,它就像一个魅力!谢谢!关于let indexRow = (caller.tag - 5) / 10这行,如果有帮助,为了根据字段标签获取每行中的行和字段,我使用函数let (q,r) = caller.tag.quotientAndRemainder(dividingBy: 10),它返回商和余数(商=行;余数=字段行中的标签)。为此,您需要以field.tag = row*10+field number 的方式为字段分配标签(如果您将行乘以另一个数字,则必须将 dividingBy 参数更改为相同的数字) .
  • 我们需要获取单元格的索引位置才能访问该单元格的内容。我们通过标签传递索引位置。但是,您通过乘以 10 并相加 5 来传递一些其他值 例如:如果索引位置为 1,但在相加和相乘之后,您将 15 传递给标记。此时,如果我们访问与索引行相同的标记意味着它将获得第 15 行 tableView 的访问权限因此我恢复并获取原始行以访问我们选择的特定单元格
  • 非常感谢您的帮助。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多