ios 在空的 UITextField 中检测退格

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1977934/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-30 16:44:24  来源:igfitidea点击:

Detect backspace in empty UITextField

iosiphoneuitextfieldbackspace

提问by marcc

Is there any way to detect when the Backspace/Deletekey is pressed in the iPhone keyboard on a UITextFieldthat is empty? I want to know when Backspaceis pressed only if the UITextFieldis empty.

有什么方法可以检测到空的 iPhone 键盘上的Backspace/Delete键何时被按下UITextField?我想知道Backspace只有在UITextField为空时才按下。



Based on the suggestion from @Alex Reynolds in a comment, I've added the following code while creating my text field:

根据@Alex Reynolds 在评论中的建议,我在创建文本字段时添加了以下代码:

[[NSNotificationCenter defaultCenter] addObserver:self
          selector:@selector(handleTextFieldChanged:)
              name:UITextFieldTextDidChangeNotification
            object:searchTextField];

This notification is received (handleTextFieldChangedfunction is called), but still not when I press the Backspacekey in an empty field. Any ideas?

收到此通知(handleTextFieldChanged调用函数),但当我Backspace在空白字段中按下键时仍然没有收到。有任何想法吗?



There seems to be some confusion around this question. I want to receive a notification when the Backspacekey is pressed. That's it. But the solution must also work when the UITextFieldis already empty.

这个问题似乎有些混乱。我想在Backspace按下键时收到通知。就是这样。但是当UITextField已经为空时,该解决方案也必须有效。

采纳答案by Andrew

This may be a long shot but it could work. Try setting the text field's text to a zero width space character \u200B. When backspace is pressed on a text field that appears empty, it will actually delete your space. Then you can just reinsert the space.

这可能是一个长镜头,但它可以工作。尝试将文本字段的文本设置为零宽度空格字符\u200B。当在显示为空的文本字段上按下退格键时,它实际上会删除您的空间。然后你可以重新插入空间。

May not work if the user manages to move the caret to the left of the space.

如果用户设法将插入符号移动到空格的左侧,则可能不起作用。

回答by jacob

Swift 4:

斯威夫特 4:



Subclass UITextField:

子类UITextField

// MyTextField.swift
import UIKit

protocol MyTextFieldDelegate: AnyObject {
    func textFieldDidDelete()
}

class MyTextField: UITextField {

    weak var myDelegate: MyTextFieldDelegate?

    override func deleteBackward() {
        super.deleteBackward()
        myDelegate?.textFieldDidDelete()
    }

}

Implementation:

执行:

// ViewController.swift

import UIKit

class ViewController: UIViewController, MyTextFieldDelegate {

    override func viewDidLoad() {
        super.viewDidLoad()

        // initialize textField
        let input = MyTextField(frame: CGRect(x: 50, y: 50, width: 150, height: 40))

        // set viewController as "myDelegate"
        input.myDelegate = self

        // add textField to view
        view.addSubview(input)

        // focus the text field
        input.becomeFirstResponder()
    }

    func textFieldDidDelete() {
        print("delete")
    }

}


Objective-C:

目标-C:



Subclass UITextField:

子类UITextField

//Header
//MyTextField.h

//create delegate protocol
@protocol MyTextFieldDelegate <NSObject>
@optional
- (void)textFieldDidDelete;
@end

@interface MyTextField : UITextField<UIKeyInput>

//create "myDelegate"
@property (nonatomic, assign) id<MyTextFieldDelegate> myDelegate;
@end

//Implementation
#import "MyTextField.h"

@implementation MyTextField

- (void)deleteBackward {
    [super deleteBackward];

    if ([_myDelegate respondsToSelector:@selector(textFieldDidDelete)]){
        [_myDelegate textFieldDidDelete];
    }
}

@end

Now simply add MyTextFieldDelegateto your UIViewControllerand set your UITextFieldsmyDelegateto self:

现在只需将MyTextFieldDelegate添加到您的UIViewController并将您的UITextFieldsmyDelegate设置为self

//View Controller Header
#import "MyTextField.h"

//add "MyTextFieldDelegate" to you view controller
@interface ViewController : UIViewController <MyTextFieldDelegate>
@end

//View Controller Implementation
- (void)viewDidLoad {
    //initialize your text field
    MyTextField *input = 
     [[MyTextField alloc] initWithFrame:CGRectMake(0, 0, 70, 30)];

    //set your view controller as "myDelegate"
    input.myDelegate = self;

    //add your text field to the view
    [self.view addSubview:input];
}

//MyTextField Delegate
- (void)textFieldDidDelete {
    NSLog(@"delete");
}

回答by ma11hew28

Update: See JacobCaraballo's answerfor an example that overrides -[UITextField deleteBackward].

更新:见JacobCaraballo的答案为例,它覆盖-[UITextField deleteBackward]

Check out UITextInput, specifically UIKeyInputhas a deleteBackwarddelegate methodthat alwaysgets called when the delete key is pressed. If you're doing something simple, then you might consider just subclassing UILabeland making it conform to the UIKeyInputprotocol, as done by SimpleTextInputand this iPhone UIKeyInput Example. Note: UITextInputand its relatives (including UIKeyInput) are only available in iOS 3.2 and later.

签出UITextInput,特别是UIKeyInput有一个deleteBackward委托方法,当按下删除键时总是会调用该方法。如果您正在做一些简单的事情,那么您可能会考虑只进行子类化UILabel并使其符合UIKeyInput协议,就像SimpleTextInput和这个iPhone UIKeyInput Example所做的那样注意:UITextInput及其亲属(包括UIKeyInput)仅在 iOS 3.2 及更高版本中可用。

回答by Jeffrey Loo

Code like following:

代码如下:

@interface MyTextField : UITextField
@end

@implementation MyTextField

- (void)deleteBackward
{
    [super deleteBackward];

    //At here, you can handle backspace key pressed event even the text field is empty
}

@end

At last, do forget to change the Custom Class property of the Text Field to "MyTextField"

最后,不要忘记将文本字段的自定义类属性更改为“MyTextField”

回答by Ruud Visser

Swift implementation:

斯威夫特实施:

import UIKit

protocol PinTexFieldDelegate : UITextFieldDelegate {
    func didPressBackspace(textField : PinTextField)
}

class PinTextField: UITextField {

    override func deleteBackward() {
        super.deleteBackward()

        // If conforming to our extension protocol
        if let pinDelegate = self.delegate as? PinTexFieldDelegate {
            pinDelegate.didPressBackspace(self)
        }
    }
}

回答by Jerapong Nampetch

I've founded other way easier than subclasssolution. Even its little bit strange but it works ok.

我已经建立了比subclass解决方案更容易的其他方式。即使它有点奇怪,但它工作正常。

- (BOOL)textView:(UITextView *)textView 
        shouldChangeTextInRange:(NSRange)range 
        replacementText:(NSString *)text
{
    const char * _char = [text cStringUsingEncoding:NSUTF8StringEncoding];
    int isBackSpace = strcmp(_char, "\b");

    if (isBackSpace == -8) {
       // is backspace
    }

    return YES;
}

It's a little bit strange for result of compare is -8. Maybe I'll wrong in some point of C Programming. But its right work ;)

比较结果是-8 有点奇怪。也许我会在某些方面出错C Programming。但它的正确工作;)

回答by Niklas Alvaeus

Try the delegate

试试 delegate

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

Then check if the range.length == 1which seems to be the case when backspaceis hit.

然后检查range.length == 1backspace被击中时似乎是这种情况。

回答by Pritesh

please use below code it will help you to detect keyboard delete key even if you textfield is empty.

请使用下面的代码,即使您的文本字段为空,它也会帮助您检测键盘删除键。

Objective C :

目标C:

- (BOOL)keyboardInputShouldDelete:(UITextField *)textField { return YES; }

- (BOOL)keyboardInputShouldDelete:(UITextField *)textField { return YES; }

Swift :

斯威夫特:

func keyboardInputShouldDelete(_ textField: UITextField) -> Bool { return true }

回答by Ben Call

Niklas Alvaeus's answer helped me out with a similar issue

Niklas Alvaeus 的回答帮助我解决了类似的问题

I was limiting entry to a specific character set, but it was ignoring backspaces. So I had it check range.length == 1before trimming the NSString. If it is true, I just return the string and don't trim it. See below

我限制进入特定字符集,但它忽略了退格。所以我range.length == 1在修剪NSString. 如果是真的,我只返回字符串而不修剪它。见下文

 - (BOOL) textField:(UITextField *)textField 
          shouldChangeCharactersInRange:(NSRange)range 
          replacementString:(NSString *)string
 {
     NSCharacterSet *nonNumberSet = 
      [[NSCharacterSet characterSetWithCharactersInString:@"0123456789."] 
         invertedSet];

    if (range.length == 1) {
       return string;
    }
    else {
       return ([string stringByTrimmingCharactersInSet:nonNumberSet].length > 0);
    }   
 }

回答by Himanshu padia

Yup, use below method to detect backspace, when textField is empty.

是的,当 textField 为空时,使用以下方法检测退格。

Need to add UITextFieldDelegate

需要添加UITextFieldDelegate

yourTextField.delegate = self (MUST REQUIRED)

yourTextField.delegate = self (必须要求)

Swift:

迅速:

func keyboardInputShouldDelete(_ textField: UITextField) -> Bool { 
    return true
}
func keyboardInputShouldDelete(_ textField: UITextField) -> Bool { 
    return true
}

Objective C:

目标 C:

- (BOOL)keyboardInputShouldDelete:(UITextField *)textField { 
    return YES; 
}
- (BOOL)keyboardInputShouldDelete:(UITextField *)textField { 
    return YES; 
}