I have a textfield which can be edited. Below this textfield, I have another textfield on the tap of which I go to another screen.
When I tap the 1st textfield, the keyboard comes up. But when I tap on the 2nd textfield the keyboard still remains (maybe because it is also a textfield). But I want the keyboard to dismiss the moment I tap the second textfield.
I'm using IQKeyboardManager.
This is what I have..But it's not working...
#IBAction func secondTextfield_Clicked(_ sender: Any) {
(sender as! UITextField).resignFirstResponder()
self.performSegue(withIdentifier: "mySegue", sender: nil)
}
First you need to set the delegate to the second textfield and implement the textFieldShouldBeginEditing delegate method.
secondTextField.delegate = self
In the following delegate method you can check the textfield and return true/false based on your textfield.
func textFieldShouldBeginEditing(_ textField: UITextField) -> Bool {
view.endEditing(true) //with will end editing for the view
if textField == secondTextField {
self.performSegue(withIdentifier: "mySegue", sender: nil)
return false
}
return true
}
By returning false for the secondTextField the keyboard will not be opened for the second text field.
First of all why are you using textfield to go to anther page?
why don't you just use button instead
Second thing, if you want you can do this:
override func viewDidLoad() {
super.viewDidLoad()
...
secondTF.delegate = self
...
}
And call this function anywhere in your code:
func textFieldShouldBeginEditing(_ textField: UITextField) -> Bool {
view.endEditing(true)
if textField == secondTF {
// Navigate to the second VC with using storyBoard or navigationController
return false
}
return true
}
Related
I have a UITextfield in a storyboard.
ClearButton is set to 'is always visible'
searchTextField.addTarget(self, action: #selector(searchTextFieldDidChange(textField:)), for: .editingChanged)
When the text field changes, this method is called
#objc func searchTextFieldDidChange(textField: UITextField){
if textField.text == "" {
textField.resignFirstResponder()
}
fireSearch()
}
When I clear the text field using backspace, textField.resignFirstResponder() is called, the keyboard vanishes as I want it.
When I clear the text field using the clear button, textField.resignFirstResponder() is called, the keyboard vanishes and appears again immediately.
What can I do that the keyboard keeps being closed when I tap the clear button?
Give this a try...
// conform to UITextFieldDelegate
class ViewController: UIViewController, UITextFieldDelegate {
// assuming this is created in Storyboard
#IBOutlet var searchTextField: UITextField!
override func viewDidLoad() {
super.viewDidLoad()
searchTextField.addTarget(self, action: #selector(searchTextFieldDidChange(textField:)), for: .editingChanged)
// set the delegate
searchTextField.delegate = self
}
#objc func searchTextFieldDidChange(textField: UITextField){
if textField.text == "" {
textField.resignFirstResponder()
}
fireSearch()
}
func textFieldShouldClear(_ textField: UITextField) -> Bool {
// clear the text
// Note: this does NOT fire searchTextFieldDidChange()
textField.text = ""
// resign
textField.resignFirstResponder()
// if you want to fire the search after text has been cleared
//fireSearch()
// return false to stop the default action of the clear button
return false
}
func fireSearch() {
print(#function)
}
}
I got problem while showing timer picker. There are two text fields: 1. first one opens a number pad. 2. second opens time picker from material controls.
Once I start editing first TF & if I tap on second TF the number pad is not getting dismissed even if I tap on Done button.
the done button is created using ToolBar & the method contains "view.endEditing" code. It works fine normally but not in above condition.
override func viewDidLoad() {
super.viewDidLoad()
rateInPointsTextField.delegate = self
}
extension MyAvailabilityVC : UITextFieldDelegate{
let toolbar = UIToolbar()
toolbar.sizeToFit()
//done button for toolbaar
let done = UIBarButtonItem(barButtonSystemItem: .done, target: self, action: #selector(donePressed))
toolbar.setItems([done], animated: false)
self.rateInPointsTextField.inputAccessoryView = toolbar
#objc func donePressed(){
self.view.endEditing(true)
}
func textFieldDidBeginEditing(_ textField: UITextField) {
if textField == self.fromTimeTextField{
let timePicker = MDTimePickerDialog()
timePicker.delegate = self
timePicker.tag = 100
timePicker.clockMode = .mode12H
timePicker.show()
self.view.endEditing(true)
}
}
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
self.rateInPointsTextField.resignFirstResponder()
return true
}
}
Confirm UITextFieldDelegate in your view controller & set TF delegate to self
class YourViewController: UIViewController, UITextFieldDelegate {
#IBOutlet weak var your_tf: UITextField!
override func viewDidLoad() {
super.viewDidLoad()
your_tf.delegate = self;
}
....
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
textField.resignFirstResponder()
return true
}
}
Now when you will press done/return button of keyboard then keyboard will dismiss. If you want to dismiss from your created button then make call from done #Action fun to textFieldShouldReturn(your_tf) like this.
...
#objc func donePressed(){
textFieldShouldReturn(your_tf)
}
Is there a way to temporarily disable the interaction and input for all textfields on a ViewController if one is currently being edited. After keyboard or UIPicker disapears, I would like the textField interaction to be enabled again.
I understand to disable touch interaction I can use:
textField.isUserInteractionEnabled = false
But what if I also have textField2 and textField3 how can I temporarily disable user interaction of both textFields when I am editing textfield1 ?
Create outlet collection for all the textfields like
#IBOutlet var textFs:[UITextField]!
Then set the vc as the delegate for all of them in viewDidLoad
textFs.forEach { $0.delegate = self }
Implement
func textFieldDidBeginEditing(_ textField: UITextField) {
textFs.forEach {
if $0 != textField {
$0.isUserInteractionEnabled = false
}
}
}
func textFieldDidEndEditing(_ textField: UITextField) {
textFs.forEach { $0.isUserInteractionEnabled = true }
}
func textFieldDidBeginEditing(textField: UITextField) {
scrlView.setContentOffset(CGPointMake(0, textField.frame.origin.y-70), animated: true)
}
func textFieldShouldReturn(textField: UITextField) -> Bool {
textField.resignFirstResponder()
scrlView .setContentOffset(CGPointMake(0, 0), animated: true)
return true
}
How can I move cursor from one textfield to another automatically after entering value in the first textfield?
first, you need add tags to your text fields orderly
func textFieldShouldReturn(textField: UITextField) -> Bool {
let nextTag = textField.tag + 1;
// Try to find next responder
var nextResponderTxt: UITextField!
nextResponderTxt = textField.superview?.viewWithTag(nextTag) as? UITextField
if ((nextResponderTxt) != nil) {
// Found next responder, so set it.
nextResponderTxt.becomeFirstResponder()
} else {
// Not found, so remove keyboard.
textField.resignFirstResponder()
}
return false; // We do not want UITextField to insert line-breaks.
}
Also you can change the return key to next
I have a button and text textfield in my view. when i click on the textfield a keyboard appears and i can write on the textfield and i also able to dismiss the keyboard by clicking on the button by adding:
[self.inputText resignFirstResponder];
Now I want to enable return key of keyboard. when i will press on the keyboard keyboard will disappear and something will happen. How can I do this?
Ensure "self" subscribes to UITextFieldDelegate and initialise inputText with:
self.inputText.delegate = self;
Add the following method to "self":
- (BOOL)textFieldShouldReturn:(UITextField *)textField {
if (textField == self.inputText) {
[textField resignFirstResponder];
return NO;
}
return YES;
}
Or in Swift:
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
if textField == inputText {
textField.resignFirstResponder()
return false
}
return true
}
With extension style in swift 3.0
First, set up delegate for your text field.
override func viewDidLoad() {
super.viewDidLoad()
self.inputText.delegate = self
}
Then conform to UITextFieldDelegate in your view controller's extension
extension YourViewController: UITextFieldDelegate {
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
if textField == inputText {
textField.resignFirstResponder()
return false
}
return true
}
}
While the other answers work correctly, I prefer doing the following:
In viewDidLoad(), add
self.textField.addTarget(self, action: #selector(onReturn), for: UIControl.Event.editingDidEndOnExit)
and define the function
#IBAction func onReturn() {
self.textField.resignFirstResponder()
// do whatever you want...
}
Just add a target on textField setup function on viewDidLoad, then add its related function as selector.
override func viewDidLoad() {
super.viewDidLoad()
textField.addTarget(self, action: #selector(textFieldShouldReturn(sender:)), for: .primaryActionTriggered)
}
#objc func textFieldShouldReturn(sender: UITextField) {
textField.resignFirstResponder()
}
Use Target-Action UIKit mechanism for "primaryActionTriggered" UIEvent sent from UITextField when a keyboard done button is tapped.
textField.addTarget(self, action: Selector("actionMethodName"), for: .primaryActionTriggered)