57

I am having a weird issue in which my UITextField which holds a secure entry is always getting cleared when I try to edit it. I added 3 characters to the field, goes to another field and comes back, the cursor is in 4th character position, but when I try to add another character, the whole text in the field gets cleared by the new character. I have 'Clears when editing begins' unchecked in the nib. So what would be the issue? If I remove the secure entry property, everything is working fine, so, is this the property of Secure entry textfields? Is there any way to prevent this behaviour?

Manoj Rlogical
  • 239
  • 1
  • 4
Nithin
  • 6,435
  • 5
  • 43
  • 56

28 Answers28

63

Set,

textField.clearsOnBeginEditing = NO;

Note: This won't work if secureTextEntry = YES. It seems, by default, iOS clears the text of secure entry text fields before editing, no matter clearsOnBeginEditing is YES or NO.

EmptyStack
  • 51,274
  • 23
  • 147
  • 178
  • I unchecked the same in nib, but added in the code too as you said. But no change.One more thing, If I remove the secure entry property, everything is working fine – Nithin Sep 05 '11 at 08:38
  • 2
    EmtyStack is right. It feels a bit weird but I think it makes sense to have it work like that. When you are typing into a secure textfield you only see the last character for a second. So if the user goes back to edit it he/she would have to remember exactly what they typed, which is not the case often. Hence, it clears everything to avoid users constantly sending wrong secure data. – rjgonzo Sep 05 '11 at 21:14
  • is this recorded in apple documentation? – Khushal Dugar Oct 17 '17 at 11:49
50

If you don't want the field to clear, even when secureTextEntry = YES, use:

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {

    NSString *updatedString = [textField.text stringByReplacingCharactersInRange:range withString:string];

    textField.text = updatedString;

    return NO;
}

I encountered a similar issue when adding show/hide password text functionality to a sign-up view.

Eric
  • 2,045
  • 17
  • 24
34

If you're using Swift 3, give this subclass a go.

class PasswordTextField: UITextField {

    override var isSecureTextEntry: Bool {
        didSet {
            if isFirstResponder {
                _ = becomeFirstResponder()
            }
        }
    }

    override func becomeFirstResponder() -> Bool {

        let success = super.becomeFirstResponder()
        if isSecureTextEntry, let text = self.text {
            self.text?.removeAll()
            insertText(text)
        }
        return success
    }

}

Why does this work?

TL;DR: if you're editing the field while toggling isSecureTextEntry, make sure you call becomeFirstResponder.


Toggling the value of isSecureTextEntry works fine until the user edits the textfield - the textfield clears before placing the new character(s). This tentative clearing seems to happen during the becomeFirstResponder call of UITextField. If this call is combined with the deleteBackward/insertText trick (as demonstrated in answers by @Aleksey and @dwsolberg), the input text is preserved, seemingly canceling the tentative clearing.

However, when the value of isSecureTextEntry changes while the textfield is the first responder (e.g., the user types their password, toggles a 'show password' button back and forth, then continues typing), the textfield will reset as usual.

To preserve the input text in this scenario, this subclass triggers becomeFirstResponder only if the textfield was the first responder. This step seems to be missing in other answers.

Thanks @Patrick Ridd for the correction!

Thomas Verbeek
  • 2,361
  • 28
  • 30
  • 3
    Beautifully small and elegant, great solution. Best answer for this question in 2017 / Swift 3. – Jeremy Aug 03 '17 at 22:21
  • Very nice solution! Unfortunately, if the user inputs some text while the UITextField is in secure mode, the font will change. Did someone notice the same behaviour? – Zeb Aug 04 '17 at 08:29
  • 2
    Oops, I discovered this has a bug as identified by @patrick-ridd. His solution fixes it. See https://stackoverflow.com/a/44185845/155186. – Jeremy Sep 06 '17 at 17:31
  • I've noticed one other small bug with this. If you toggle on isSecureTextEntry with the keyboard on screen, the Return button is disabled. I haven't found a workaround for that yet. – Jeremy Nov 21 '17 at 16:21
  • 2
    Update you can set `enablesReturnKeyAutomatically = false`, but then you have the problem that the return key is enabled even when the field is empty. I can't believe how much time I've spent on a Show/Hide password field. – Jeremy Nov 21 '17 at 16:37
  • 2
    I'd suggest to use `insertText("\(text)+")`, after that `deleteBackward()`. This prevents the last character in the password field to be shown when becoming first responder again. – fredpi Dec 27 '17 at 15:56
22

@Eric's answer works but I had two issues with it.

  1. As @malex pointed out, any change of text in middle will place carriage at the end of text.
  2. I'm using rac_textSignal from ReactiveCocoa and changing the text directly wouldn't trigger the signal.

My final code

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    //Setting the new text.
    NSString *updatedString = [textField.text stringByReplacingCharactersInRange:range withString:string];
    textField.text = updatedString;

    //Setting the cursor at the right place
    NSRange selectedRange = NSMakeRange(range.location + string.length, 0);
    UITextPosition* from = [textField positionFromPosition:textField.beginningOfDocument offset:selectedRange.location];
    UITextPosition* to = [textField positionFromPosition:from offset:selectedRange.length];
    textField.selectedTextRange = [textField textRangeFromPosition:from toPosition:to];

    //Sending an action
    [textField sendActionsForControlEvents:UIControlEventEditingChanged];

    return NO;
}

Swift3 addition by @Mars:

  func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    let nsString:NSString? = textField.text as NSString?
    let updatedString = nsString?.replacingCharacters(in:range, with:string);

    textField.text = updatedString;


    //Setting the cursor at the right place
    let selectedRange = NSMakeRange(range.location + string.length, 0)
    let from = textField.position(from: textField.beginningOfDocument, offset:selectedRange.location)
    let to = textField.position(from: from!, offset:selectedRange.length)
    textField.selectedTextRange = textField.textRange(from: from!, to: to!)

    //Sending an action
    textField.sendActions(for: UIControlEvents.editingChanged)

    return false;
}
Mars
  • 2,505
  • 17
  • 26
Ahmad Baraka
  • 1,093
  • 9
  • 12
14

Swift 5

yourtextfield.clearsOnInsertion = false
yourtextfield.clearsOnBeginEditing = false

Note: This won't work if secureTextEntry = YES. It seems, by default, iOS clears the text of secure entry text fields before editing, no matter clearsOnBeginEditing is YES or NO.

Easy way use class and its work 100%

class PasswordTextField: UITextField {

    override var isSecureTextEntry: Bool {
        didSet {
            if isFirstResponder {
                _ = becomeFirstResponder()
                //MARK:- Do something what you want
            }
        }
    }

    override func becomeFirstResponder() -> Bool {

        let success = super.becomeFirstResponder()
        if isSecureTextEntry, let text = self.text {
            self.text?.removeAll()
            insertText(text)
        }
         return success
    }
}
Shakeel Ahmed
  • 5,361
  • 1
  • 43
  • 34
6

I've tried all solutions here and there and finally came with that overriding:

- (BOOL)becomeFirstResponder
{
    BOOL became = [super becomeFirstResponder];
    if (became) {
        NSString *originalText = [self text];
        //Triggers UITextField to clear text as first input
        [self deleteBackward];

        //Requires setting text via 'insertText' to fire all associated events
        [self setText:@""];
        [self insertText:originalText];
    }
    return became;
}

It triggers UITextField's clear and then restores original text.

Aleksey
  • 875
  • 8
  • 8
6

@Thomas Verbeek's answer helped me a lot:

class PasswordTextField: UITextField {

    override var isSecureTextEntry: Bool {
        didSet {
            if isFirstResponder {
                _ = becomeFirstResponder()
            }
        }
    }

    override func becomeFirstResponder() -> Bool {

        let success = super.becomeFirstResponder()
        if isSecureTextEntry, let text = self.text {
            deleteBackward()
            insertText(text)
        }
        return success
    }

}

Except I did find a bug in my code with it. After implementing his code, if you have text in the textField and you tap on the textField box, it will only delete the first char and then insert all of the text in again. Basically pasting the text in again.

To remedy this I replaced the deleteBackward() with a self.text?.removeAll() and it worked like a charm.

I wouldn't have gotten that far without Thomas' original solution, so thanks Thomas!

Brunner
  • 1,945
  • 23
  • 26
Patrick Ridd
  • 401
  • 6
  • 4
  • Thank you! I noticed the same bug (the secure text field lost first responder when I brought up a UIAlertController) but your solution fixes it. I would suggest editing your answer with the corrected code for those people who are too lazy and tl;dr. The one thing I notice that when tapping the field, it reveals the last character, but I can live with it. – Jeremy Sep 06 '17 at 17:33
  • 2
    with this solution when you tap in a already filled text field, it will reveal the last char. In order to solve this bug change insertText(text) for self.text = text – Nathan Barreto Jul 19 '18 at 15:01
  • does not work well in iOS13 and shows editing popover – Peter Lapisu Jun 08 '20 at 13:24
  • 1
    Does not work in SwiftUI – Richard Topchii Dec 02 '21 at 23:25
5

I had a similar problem. I have login (secureEntry = NO) and password (secureEntry = YES) text fields embedded in a table view. I tried setting

textField.clearsOnBeginEditing = NO;

inside both of the relevant delegate methods (textFieldDidBeginEditing and textFieldShouldBeginEditing), which didn't work. After moving from the password field to the login field, the whole login field would get cleared if I tried to delete a single character. I used the textFieldShouldChangeCharactersInRange to solve my problem, as follows:

-(BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    if (range.length == 1 && textField.text.length > 0) 
    {
        //reset text manually
        NSString *firstPart = [textField.text substringToIndex:range.location]; //current text minus one character
        NSString *secondPart = [textField.text substringFromIndex:range.location + 1]; //everything after cursor
        textField.text = [NSString stringWithFormat:@"%@%@", firstPart, secondPart];

        //reset cursor position, in case character was not deleted from end of 
        UITextRange *endRange = [textField selectedTextRange];
        UITextPosition *correctPosition = [textField positionFromPosition:endRange.start offset:range.location - textField.text.length];
        textField.selectedTextRange = [textField textRangeFromPosition:correctPosition toPosition:correctPosition];

        return NO;
    }
    else
    {
        return YES;
    }
}

The range.length == 1 returns true when the user enters a backspace, which is (strangely) the only time that I would see the field cleared.

Ampers4nd
  • 787
  • 1
  • 11
  • 20
5

Based on Aleksey's solution, I'm using this subclass.

class SecureNonDeleteTextField: UITextField {

    override func becomeFirstResponder() -> Bool {
        guard super.becomeFirstResponder() else { return false }
        guard self.secureTextEntry == true else { return true }
        guard let existingText = self.text else { return true }
        self.deleteBackward() // triggers a delete of all text, does NOT call delegates
        self.insertText(existingText) // does NOT call delegates
        return true
    }
}

Changing the replace characters in range doesn't work for me because I'm doing other things with that at times, and adding more makes it more likely to be buggy.

This is nice because it pretty much works perfectly. The only oddity is that the last character is shown again when you tap back into the field. I actually like that because it acts as a sort of placeholder.

dwsolberg
  • 879
  • 9
  • 8
5

IOS 12, Swift 4

  • Does not display the last character when text field becoming first responder again.
  • Does not duplicate the existing text when you repeatedly touch the text field.

If you want to use this solution not only with secure text entry, add the isSecureTextEntry check.

class PasswordTextField: UITextField {
    override func becomeFirstResponder() -> Bool {
        let wasFirstResponder = isFirstResponder
        let success = super.becomeFirstResponder()
        if !wasFirstResponder, let text = self.text {
            insertText("\(text)+")
            deleteBackward()
        }
        return success
    }
}
Iaenhaall
  • 404
  • 5
  • 9
1

If you want to use secureTextEntry = YES and proper visual behavior for carriage, you need this:

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
{

    if (!string.length) {
        UITextPosition *start = [self positionFromPosition:self.beginningOfDocument offset:range.location];
        UITextPosition *end = [self positionFromPosition:start offset:range.length];
        UITextRange *textRange = [self textRangeFromPosition:start toPosition:end];
        [self replaceRange:textRange withText:string];
    }
    else {
       [self replaceRange:self.selectedTextRange withText:string];
    }

    return NO;
}
malex
  • 9,874
  • 3
  • 56
  • 77
1

After playing with solution from @malex I came to this Swift version:

1) Don't forget to make your view controller a UITextFieldDelegate:

class LoginViewController: UIViewController, UITextFieldDelegate {
...
}

override func viewDidLoad() {
   super.viewDidLoad()
   textfieldPassword.delegate = self
}

2) use this:

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    if let start: UITextPosition = textField.positionFromPosition(textField.beginningOfDocument, offset: range.location),
       let end: UITextPosition = textField.positionFromPosition(start, offset: range.length),
       let textRange: UITextRange = textField.textRangeFromPosition(start, toPosition: end) {
           textField.replaceRange(textRange, withText: string)
    }
    return false
}

...and if you are doing this for the "show/hide password" functionality most probably you will need to save and restore caret position when you switch secureTextEntry on/off. Here's how (do it inside the switching method):

var startPosition: UITextPosition?
var endPosition: UITextPosition?

// Remember the place where cursor was placed before switching secureTextEntry
if let selectedRange = textfieldPassword.selectedTextRange {
   startPosition = selectedRange.start
   endPosition = selectedRange.end
}

...

// After secureTextEntry has been changed
if let start = startPosition {
   // Restoring cursor position
   textfieldPassword.selectedTextRange = textfieldPassword.textRangeFromPosition(start, toPosition: start)
   if let end = endPosition {
       // Restoring selection (if there was any)
       textfieldPassword.selectedTextRange = textfield_password.textRangeFromPosition(start, toPosition: end)
       }
}
Vitalii
  • 4,267
  • 1
  • 40
  • 45
1

We solved it based on dwsolberg's answer with two fixes:

  • the password text was duplicated when tapping into an already focused password field
  • the last character of the password was revealed when tapping into the password field
  • deleteBackward and insertText cause the value changed event to be fired

So we came up with this (Swift 2.3):

class PasswordTextField: UITextField {

    override func becomeFirstResponder() -> Bool {
        guard !isFirstResponder() else {
            return true
        }
        guard super.becomeFirstResponder() else {
            return false
        }
        guard secureTextEntry, let text = self.text where !text.isEmpty else {
            return true
        }

        self.text = ""
        self.text = text

        // make sure that last character is not revealed
        secureTextEntry = false
        secureTextEntry = true

        return true
    }
}
Community
  • 1
  • 1
fluidsonic
  • 4,655
  • 2
  • 24
  • 34
1

This is swift code from my project is tested and deals with, backspace and secure-entry changes false/true

// get the user input and call the validation methods

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

    if (textField == passwordTextFields) {

        let newString = (textField.text! as NSString).replacingCharacters(in: range, with: string)

        // prevent backspace clearing the password
        if (range.location > 0 && range.length == 1 && string.characters.count == 0) {
            // iOS is trying to delete the entire string
            textField.text = newString
            choosPaswwordPresenter.validatePasword(text: newString as String)

            return false
        }

        // prevent typing clearing the pass
        if range.location == textField.text?.characters.count {
            textField.text = newString
            choosPaswwordPresenter.validatePasword(text: newString as String)

            return false
        }

        choosPaswwordPresenter.validatePasword(text: newString as String)
    }

    return true
}
ovidiur
  • 328
  • 2
  • 9
  • It works. Question: How would it be implemented once I press on the textfield it would clear the pass and take the newString and validate it? – habed May 30 '17 at 10:07
  • So in my example : I call this : choosPaswwordPresenter.validatePasword(text: newString as String) , and in that method I save the current state of that input. – ovidiur May 31 '17 at 10:29
1

Create a subclass of UITextField and override below two methods below:

-(void)setSecureTextEntry:(BOOL)secureTextEntry {
    [super setSecureTextEntry:secureTextEntry];

    if ([self isFirstResponder]) {
        [self becomeFirstResponder];
    }
}

-(BOOL)becomeFirstResponder {
    BOOL became = [super becomeFirstResponder];
    if (became) {
        NSString *originalText = [self text];
        //Triggers UITextField to clear text as first input
        [self deleteBackward];

        //Requires setting text via 'insertText' to fire all associated events
        [self setText:@""];
        [self insertText:originalText];
    }
    return became;
}

Use this class name as your text field class name.

Milan Agarwal
  • 427
  • 2
  • 15
1

The solutions posted didn't work for me, I ended up with this one:

import UIKit

final class SecureTextFieldFixed: UITextField {
    override var isSecureTextEntry: Bool {
        didSet {
            if isFirstResponder {
                _ = becomeFirstResponder()
            }
        }
    }

    override func becomeFirstResponder() -> Bool {
        let success = super.becomeFirstResponder()
        if isSecureTextEntry, let enteredText = text {
            text?.removeAll()
            insertText(enteredText)
        }
        return success
    }
}
Richard Topchii
  • 7,075
  • 8
  • 48
  • 115
0

I realize this is a little old, but in iOS 6 the UITextField "text" is now by default "Attributed" in Interface Builder. Switching this to be "Plain", which is how it was in iOS 5, fixes this problem.

Also posted this same answer over in the question that @Craig linked.

Matt S.
  • 1,882
  • 13
  • 17
0

i had the same problem, but got the solution;

-(BOOL)textFieldShouldReturn:(UITextField *)textField
    {

        if(textField==self.m_passwordField)
        {
            text=self.m_passwordField.text;  
        }

        [textField resignFirstResponder];

        if(textField==self.m_passwordField)
        {
            self.m_passwordField.text=text;
        }
        return YES;
    }
Superdev
  • 562
  • 7
  • 13
0

My solution (until the bug is fixed I suppose) is to subclass UITextField such that it appends to existing text instead of clearing as before (or as in iOS 6). Attempts to preserve original behavior if not running on iOS 7:

@interface ZTTextField : UITextField {
    BOOL _keyboardJustChanged;
}
@property (nonatomic) BOOL keyboardJustChanged;
@end

@implementation ZTTextField
@synthesize keyboardJustChanged = _keyboardJustChanged;

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        // Initialization code
        _keyboardJustChanged = NO;
    }
    return self;
}

- (void)insertText:(NSString *)text {
#if __IPHONE_OS_VERSION_MAX_ALLOWED >= 70000
    if (self.keyboardJustChanged == YES) {
        BOOL isIOS7 = NO;
        if ([[UIApplication sharedApplication] respondsToSelector:@selector(backgroundRefreshStatus)]) {
            isIOS7 = YES;
        }
        NSString *currentText = [self text];
        // only mess with editing in iOS 7 when the field is masked, wherein our problem lies
        if (isIOS7 == YES && self.secureTextEntry == YES && currentText != nil && [currentText length] > 0) {
            NSString *newText = [currentText stringByAppendingString: text];
            [super insertText: newText];
        } else {
            [super insertText:text];
        }
        // now that we've handled it, set back to NO
        self.keyboardJustChanged = NO;
    } else {
        [super insertText:text];
    }
#else
    [super insertText:text];
#endif
}

- (void)setKeyboardType:(UIKeyboardType)keyboardType {
    [super setKeyboardType:keyboardType];
    [self setKeyboardJustChanged:YES];
}

@end
Billy Gray
  • 1,747
  • 4
  • 18
  • 23
0

I experimented with answers of dwsolberg and fluidsonic and this seem's to work

override func becomeFirstResponder() -> Bool {

    guard !isFirstResponder else { return true }
    guard super.becomeFirstResponder() else { return false }
    guard self.isSecureTextEntry == true else { return true }
    guard let existingText = self.text else { return true }
    self.deleteBackward() // triggers a delete of all text, does NOT call delegates
    self.insertText(existingText) // does NOT call delegates

    return true
}
Ivan
  • 1
0

I needed to adjust @thomas-verbeek solution, by adding a property which deals with the case when user tries to paste any text to the field (text has been duplicated)

class PasswordTextField: UITextField {

    private var barier = true

    override var isSecureTextEntry: Bool {
        didSet {
            if isFirstResponder {
                _ = becomeFirstResponder()
            }
        }
    }

    override func becomeFirstResponder() -> Bool {
        let success = super.becomeFirstResponder()
        if isSecureTextEntry, let text = self.text, barier {
            deleteBackward()
            insertText(text)
        }
        barier = !isSecureTextEntry
        return success
    }

}
olejnjak
  • 1,163
  • 1
  • 9
  • 23
0

I used @EmptyStack answer textField.clearsOnBeginEditing = NO; on my password text field passwordTextField.secureTextEntry = YES; but it didn't work out in iOS11 SDK with Xcode 9.3 so I done following code to achieve. Actually I want to keep text(in text field) if user switch between different fields.

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    if (textField.tag == 2) {
        if ([string isEqualToString:@""] && textField.text.length >= 1) {
            textField.text = [textField.text substringToIndex:[textField.text length] - 1];
        } else{
            textField.text = [NSString stringWithFormat:@"%@%@",textField.text,string];
        }
        return false;
    } else {
        return true;
    }
}

I returned false in shouldChangeCharactersInRange and manipulated as i want this code also works if user click on delete button to delete character.

Aleem
  • 3,173
  • 5
  • 33
  • 71
0

when my project upgrade to iOS 12.1 and have this issue. This is my solution about this. It's work okay.



    - (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
        NSMutableString *checkString = [textField.text mutableCopy];
        [checkString replaceCharactersInRange:range withString:string];
        textField.text = checkString;
        NSRange selectedRange = NSMakeRange(range.location + string.length, 0);
        UITextPosition* from = [textField positionFromPosition:textField.beginningOfDocument offset:selectedRange.location];
        UITextPosition* to = [textField positionFromPosition:from offset:selectedRange.length];
        textField.selectedTextRange = [textField textRangeFromPosition:from toPosition:to];
        [textField sendActionsForControlEvents:UIControlEventEditingChanged];
        return NO;
    }

Ace
  • 219
  • 1
  • 3
0

Thanks to the answers before me. It seems that all that needs to be done is removing and insertion of the text on the same string object right after isSecureTextEntry is set. So I've added the extension below:

extension UITextField {
    func setSecureTextEntry(_ on: Bool, clearOnBeginEditing: Bool = true)   {
        isSecureTextEntry = on

        guard on,
              !clearOnBeginEditing,
              let textCopy = text
        else { return }

        text?.removeAll()
        insertText(textCopy)
    }
}
0

Swift5 version of https://stackoverflow.com/a/29195723/1979953.

func textField(
    _ textField: UITextField,
    shouldChangeCharactersIn range: NSRange,
    replacementString string: String
) -> Bool {
    let nsString = textField.text as NSString?
    let updatedString = nsString?.replacingCharacters(
        in: range,
        with: string
    )
    textField.text = updatedString

    // Setting the cursor at the right place
    let selectedRange = NSRange(
        location: range.location + string.count,
        length: 0
    )

    guard let from = textField.position(
        from: textField.beginningOfDocument,
        offset: selectedRange.location
    ) else {
        assertionFailure()
        return false
    }

    guard let to = textField.position(
        from: from,
        offset: selectedRange.length
    ) else {
        assertionFailure()
        return false
    }

    textField.selectedTextRange = textField.textRange(
        from: from,
        to: to
    )

    // Sending an action
    textField.sendActions(for: UIControl.Event.editingChanged)

    return false
}
shingo.nakanishi
  • 2,045
  • 2
  • 21
  • 55
0

I have modified Ahmed's answer for swift 5.

    func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    if textField.isEqual(txtFieldPassword) {
    let nsString:NSString? = textField.text as NSString?
        let updatedString = nsString?.replacingCharacters(in:range, with:string);

        textField.text = updatedString;


        //Setting the cursor at the right place
        let selectedRange = NSMakeRange(range.location + (string as NSString).length, 0)
        let from = textField.position(from: textField.beginningOfDocument, offset:selectedRange.location)
        let to = textField.position(from: from!, offset:selectedRange.length)
        textField.selectedTextRange = textField.textRange(from: from!, to: to!)

        //Sending an action
    textField.sendActions(for: UIControl.Event.editingChanged)

        return false;
    } else {
        return true
    }
    
}
Narasimha Nallamsetty
  • 1,215
  • 14
  • 16
-1

There is another stackoverflow question post: Question

Reading that post it lookes like you need to set the textField.clearsOnBeginEditing = NO in the textFieldShouldBeginEditing delegate method

Community
  • 1
  • 1
Craig Mellon
  • 5,399
  • 2
  • 20
  • 25
-2

Save the text entered in a property. For example:

NSString *_password;

And then in the delegate:

textFieldDidBeginEditing:(UITextField *)textField
assign textField.text = _password;
A5C1D2H2I1M1N2O1R2T1
  • 190,393
  • 28
  • 405
  • 485
Lirik
  • 3,167
  • 1
  • 30
  • 31