Detect when textfield has been pressed in swift - ios

I want to have an action when a certain textfield is pressed. I have tried
func textFieldDidBeginEditing(_ textField: UITextField) {
if textField == myTextField {
print("pressed")
}
}
but this didn't work for me. Does anyone have any solutions? Thanks

This function is the callback from UITextFieldDelegate. But it will only be fired if the class with this is connected to your UITextField's delegate.
simple Example using an iOS ViewController:
class yourViewController: UIViewController, UITextFieldDelegate
{
/* Make sure that your variable 'myTextField' was created using an IBOutlet from your storyboard*/
#IBOutlet var myTextField : UITextField!
override func ViewDidLoad()
{
super.viewDidLoad()
myTextField.delegate = self // here you set the delegate so that UITextFieldDelegate's callbacks like textFieldDidBeginEditing respond to events
}
func textFieldDidBeginEditing(_ textField: UITextField) {
if textField == myTextField {
print("pressed")
}
}
}
Make sure though that you understand the concept of the delegation pattern event handling, and how a delegate captures and posts events like this one for instance. A lot of Cocoa GUI components use this design. these are some useful links.
https://docs.swift.org/swift-book/LanguageGuide/Protocols.html
https://developer.apple.com/documentation/uikit/uitextfielddelegate
http://www.andrewcbancroft.com/2015/03/26/what-is-delegation-a-swift-developers-guide/

Related

Identifying UITextField when using a UITextField Collection in Swift iOS

I am creating a signup screen.
There are four UITextField, which is the ID, password, password check, name,
I am #Iboutlet var signupTextFields: [UITextField]! I connected it. After that, I want to make an ID, password validation.
First, I divided ViewController and UItextFieldDelegate.
class SignUpViewController: UIViewController {
#IBOutlet var signUpTextFields: [UITextField]! {
didSet {
signUpTextFields.forEach { textField in
textField.delegate = textFieldDelegate
textField.returnKeyType = .next
}
}
}
#IBOutlet weak var nextButton: UIButton!
private lazy var textFieldDelegate = TextFieldDelegate(self)
override func viewDidLoad() {
super.viewDidLoad()
signUpTextFields.first?.becomeFirstResponder()
}
#IBAction func nextButtonTapped(_ sender: UIButton) {
}
}
class TextFieldDelegate: NSObject, UITextFieldDelegate {
private weak var signUpViewController: SignUpViewController?
init(_ signUpViewController: SignUpViewController) {
self.signUpViewController = signUpViewController
}
func textFieldDidBeginEditing(_ textField: UITextField) {
textField.layer.borderWidth = 1
textField.layer.borderColor = UIColor.systemBlue.cgColor
}
func textFieldDidEndEditing(_ textField: UITextField, reason: UITextField.DidEndEditingReason) {
textField.layer.borderColor = UIColor.black.cgColor
}
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
textField.resignFirstResponder()
return true
}
}
The problem when using the functions provided by Delegate is that the example code is to identify UITextField using if-else, such as
func textFieldDidBeginEditing(_ textField: UITextField) {
if textField == idTextField {
//code
} else if textField == passwordTextField {
//code
}
}
I was not this way, but I thought I wanted to abstract the uitextfield a little more to use the Factory method or polymorphism.
Is there a way to identify a UITextField Collection without using if-Else?
I'd recommend - Tag + Enum. (tag field is the norm to identify a view instance from Storyboard / Xib in the cases where you don't have individual IBOutlets)
Set "tag" in the Storyboard - ensure they are unique. (simple index oughta be enough -- 0, 1, 2 .. etc.)
Create an enum inside the view controller.
enum TextField {
case name = 0
case password = 1
}
& so on (explicitly declare the tag values in the enum)
Use Switch instead of if-else for identification.
switch textField.tag {
case .name:
case .password:
}
This should suffice for your case (since you are just going through an example code). But it's good that you are interested in clean code -- I'd recommend creating the TextFields programmatically & using the enum to set the .tag field.
Using the same delegate for all of the text fields was bad design if your intention was to behave differently in the delegate methods. If it’s too late to change that, I would recommend an array of closures corresponding to the array of text fields. That way, calling the right closure is a one-liner based on firstIndex(of:).

Hiding the Keyboard triggered by textField via resignFirstResponder

Environment: Xcode Version 8.2 (8C38)/Swift 3.0
A textFiled object in the View is wire up to a method named textFieldReturn in the controller via IBAction. The related codes are presented as follow
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
}
#IBAction func textFieldReturn(_ sender: Any) {
_ = (sender as AnyObject).resignFirstResponder()
}
}
What I expect:
When I hit the Return key of the virtual keyboard the function textFieldReturn(_:) will be called and the keyboard will be hidden
Issue Observer:
The function is not called after I tapped the return key, the keyboard is still there
Resource:
This code spinet come from the example of the Chapter 16 of the book iOS 10 App Development Essentials by Neil Symth (pp-114)
The only difference between this code and original code is the type of the function argument (Sender). It is AnyObject in the original book while I've got Any by default, therefore I've cast to AnyObject inside the function body
Question:
Its seems to be a decent book, but the sample code doesn't work for me. How can I call the resignFirstResponder() method when I hit the return key
Alternative try out:
Instead of using IBAction, I turn to the idea of delegate, I've set the VeiwController as the delegate of the textField
class ViewController: UIViewController, UITextFieldDelegate {
#IBOutlet weak var tempText: UITextField! //reference the TextField as the variable **tempText** in the controller
override func viewDidLoad() {
super.viewDidLoad()
self.tempText.delegate = self //set up the delegation
}
func textFieldReturn(_ textField: UITextField) -> Bool {
textField.resignFirstResponder()
return(true)
}
}
Problem
The alternative solution still not working.
Thanks for your time and help
Why are you not using the original delegate function of UITextField?
I think the default function will work as you want:
class ViewController: UIViewController, UITextFieldDelegate {
#IBOutlet weak var tempText: UITextField! //reference the TextField as the variable **tempText** in the controller
override func viewDidLoad() {
super.viewDidLoad()
self.tempText.delegate = self //set up the delegation
}
func textFieldShouldReturn(_ textField: UITextField) -> Bool{
textField.resignFirstResponder()
return false
}
}
Replace your textFieldReturn method with this and it should work just fine.
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
textField.resignFirstResponder()
return true
}
Make sure to keep the following in your viewDidLoad()
self.tempText.delegate = self

Call TextFieldShouldReturn Programmatically Swift

I have a textField in my TableViewController with a search return key.
I succeeded to put some text programmatically in the search textField but I didn't succueed to run the search option programmatically.
This is my code so far:
When I try to run the last row (textFieldShouldReturn(search_textfield)), the application crashes.
How can I call programmatically to textFieldShouldReturn in order to activate the "Search" button?
if i understood your question correctly you want the following:
import UIKit
class ViewController: UIViewController, UITextFieldDelegate {
#IBOutlet weak var textField: UITextField!
override func viewDidLoad() {
super.viewDidLoad()
textField.delegate = self
}
the textFieldShouldReturn function gets called when you hit the return key on the keyboard
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
self.resignFirstResponder() //to hide the keyboard
//call any of your functions
callFunction()
return true
}
func callFunction() {
print("called function after return key was pressed...")
}
All this works perfectly for me in Xcode8 with swift3 and ios10.
As from your code it looks like you want to search the default value that is written in your textfield that why you write textfieldShould Return..
you can do this by creating a method like
-(void)PerformSearch:(NSString*)searchStr
{
//Do what ever Logic you implement in searching
}
Call this method in your ViewDidLoadMethod to perform Search
-(void)ViewDidLoad
{
[super:ViewDidLoad];
[self performSearch:textfield.text];
}

Swift: how to use UISwitch to control UITextField to be enabled or disabled with a delegate

In XCode 6.3.2, I have a UITextField:
#IBOutlet weak var uiswitchControlledTextField: UITextField!
I am now using a UISwitch (named mySwitch) to control its enabled or disabled state in the following way:
#IBOutlet weak var mySwitch: UISwitch!
mySwitch.addTarget(self, action: Selector("stateChanged:"), forControlEvents: UIControlEvents.ValueChanged)
//callback below:
func stateChanged(switchState: UISwitch) {
uiswitchControlledTextField.enabled = switchState.on
}
The above works well, however, I am looking to try if it would be possible to create a UITextFieldDelegate to control the above UITextField in the same way. So far, I have the following by implementing textFieldShouldBeginEditing, in which I wish to return false to disable the UITextField, but I don't know how to let the UISwitch dynamically return true or false from textFieldShouldBeginEditing
import Foundation
import UIKit
class SwitchControlledTextFieldDelegate: NSObject, UITextFieldDelegate {
func textFieldShouldBeginEditing(textField: UITextField) -> Bool {
return false; //do not show keyboard or cursor
}
}
In ViewController, I try to set
self.uiswitchControlledTextField.delegate = SwitchControlledTextFieldDelegate()
but it does not work as I wished. Any help would be appreciated.
self.uiswitchControlledTextField.delegate = SwitchControlledTextFieldDelegate()
The problem is that that line merely creates an instance of your SwitchControlledTextFieldDelegate class, which then immediately goes right back out of existence.
You need to use, as your text field delegate, some instance which already exists and which will persist - like, perhaps, your view controller!
(Xcode 7)
Use this:
override func viewDidLoad() {
super.viewDidLoad()
// Setting the delegate
self.textField3.delegate = self
self.editingSwitch.setOn(false, animated: false)
}
// Text Field Delegate Methods
func textFieldShouldBeginEditing(textField: UITextField) -> Bool {
return self.editingSwitch.on
}
#IBAction func toggleTheTextEditor(sender: AnyObject) {
if !(sender as! UISwitch).on {
self.textField3.resignFirstResponder()
}
}

Swift UITextFieldShouldReturn Return Key Tap

(iOS8, Xcode6, Swift)
Using Swift, how do I capture a tap on the "Return" button?
The doc at the following link specifies using the textFieldShouldReturn method:
// Swift
#optional func textFieldShouldReturn(_ textField: UITextField!) -> Bool
Where I'm hung up is in the "_ textField" part. I've created the text field using Storyboard. How do I capture notifications for this specific text field? Do I need to create a new class and set it as a delegate for this text field? Do I assign the text filed a name, and then somehow hook into it?
https://developer.apple.com/documentation/uikit/uitextfielddelegate/1619603-textfieldshouldreturn
class ViewController: UIViewController,UITextFieldDelegate //set delegate to class
#IBOutlet var txtValue: UITextField //create a textfile variable
override func viewDidLoad() {
super.viewDidLoad()
txtValue.delegate = self //set delegate to textfile
}
func textFieldShouldReturn(_ textField: UITextField) -> Bool { //delegate method
textField.resignFirstResponder()
return true
}
Implement this function
func textFieldShouldReturn(_ textField: UITextField) -> Bool { //delegate method
textField.resignFirstResponder()
return true
}
And for delegate you can set using the Utilities pane / Connections Inspector / delegate and then drag to ViewController (yellow button in the storyboard)
Then you do not need to set the delegate programmatically for every text field
In Swift 4.2 and Xcode 10.1
//UITextField delegate method
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
if textField == TF1 {
textField.resignFirstResponder()//
TF2.becomeFirstResponder()//TF2 will respond immediately after TF1 resign.
} else if textField == TF2 {
textField.resignFirstResponder()
TF3.becomeFirstResponder()//TF3 will respond first
} else if textField == TF3 {
textField.resignFirstResponder()
}
return true
}
You need to set an object as the text field's delegate. Usually that would be the view controller that the text field exists in. You don't need to inherit from any other class, or, strictly speaking, implement a delegate (but you could implement UITextFieldDelegate to make things a little clearer.)

Resources