Deteksi backspace di UITextField kosong

126

Apakah ada cara untuk mendeteksi ketika tombol Backspace/ Deleteditekan di keyboard iPhone pada UITextFieldyang kosong? Saya ingin tahu kapan Backspaceditekan hanya jika UITextFieldkosong.


Berdasarkan saran dari @Alex Reynolds dalam komentar, saya telah menambahkan kode berikut saat membuat bidang teks saya:

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

Notifikasi ini diterima ( handleTextFieldChangedfungsi dipanggil), tetapi tetap tidak ketika saya menekan Backspacetombol di bidang kosong. Ada ide?


Tampaknya ada beberapa kebingungan di sekitar pertanyaan ini. Saya ingin menerima pemberitahuan ketika Backspacetombol ditekan. Itu dia. Tetapi solusinya juga harus bekerja ketika UITextFieldsudah kosong.

marcc
sumber
Saya pikir Anda mungkin bermaksud "hanya jika UITextField kosong" daripada "hanya jika keyboard kosong" ...?
Steve Harrison
@Steve Harrison: terima kasih. Diperbarui itu.
marcc
Saya mencoba melakukan sesuatu yang serupa, solusi apa yang Anda dapatkan saat itu? Apa yang saya lakukan adalah bidang teks dalam tampilan gulir, ketika saya mengetik beberapa teks, saran ditampilkan dan ketika saya mengklik satu, objek label ditempatkan di sebelah kiri bidang teks. Terima kasih sebelumnya: D
Dough
Solusi 2011/11 untuk UITextField kosong menggunakan tipuan runtime: bjhomer.blogspot.com/2011/11/…
Jano
4
Sangat menginginkan sesuatu yang sepele. Ini seharusnya tidak sulit.
Adam Waite

Jawaban:

36

Ini mungkin pukulan panjang tetapi bisa berhasil. Cobalah mengatur teks bidang teks ke karakter spasi nol lebar \u200B. Ketika backspace ditekan pada bidang teks yang tampak kosong, itu benar-benar akan menghapus ruang Anda. Maka Anda bisa memasukkan kembali ruang.

Mungkin tidak berfungsi jika pengguna berhasil memindahkan tanda sisipan di sebelah kiri ruang.

Andrew
sumber
3
@Andrew, ini adalah pendekatan yang saya putuskan untuk diambil. Butuh sedikit kode, tetapi tentu saja efektif. Terima kasih atas bantuannya daripada mencoba memberi tahu saya bahwa saya melakukan sesuatu yang salah.
marcc
2
Teknik ini dapat bekerja pada iPhone> 3.1.3, tetapi ini merupakan peretasan dan dapat merusak versi yang akan datang, dll. Saya pikir saya menemukan solusi yang lebih bersih dan lebih stabil untuk cara mendeteksi tombol tekan tombol hapus pada iPhone / iOS .
ma11hew28
6
Saya dapat mengonfirmasi bahwa penghapusan tidak terdeteksi jika pengguna berhasil memindahkan kursor ke sebelah kiri ruang. Jika Anda dapat mencari cara untuk memperbaikinya, maka Anda juga harus subclass UITextFielddan melaksanakan canPerformAction:withSender:untuk return NOuntuk select:dan selectAll:tindakan ketika teks sama dengan string @"\u200B".
ma11hew28
2
Masalahnya adalah ini tidak berfungsi untuk bidang uji aman. Ada ide bagaimana mengatasinya?
Kyle Clegg
7
Maaf, tapi ide ini buruk. Ini adalah hacky yang luar biasa dan seharusnya tidak menjadi jawaban yang diterima dengan 30 atau lebih upvotes. Saya akan subkelas UITextField sebagai gantinya, seperti beberapa komentator lain telah disebutkan.
Brian Sachetta
155

Swift 4:


Subkelas UITextField:

// MyTextField.swift
import UIKit

protocol MyTextFieldDelegate: AnyObject {
    func textFieldDidDelete()
}

class MyTextField: UITextField {

    weak var myDelegate: MyTextFieldDelegate?

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

}

Penerapan:

// 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")
    }

}

Tujuan-C:


Subkelas 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

Sekarang cukup tambahkan MyTextFieldDelegate ke Anda UIViewControllerdan atur UITextFields myDelegate Anda ke 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");
}
Jacobs
sumber
9
Ini solusi terbaik. Jawaban yang diterima adalah retasan. Objective C didasarkan pada subklasifikasi dan solusi ini menggunakannya dengan benar untuk menyelesaikan masalah.
TJ
Apa yang akan terjadi pada metode delegasi saya yang ada di ViewController kelas jika saya mengatur delegasi textfield saya menjadi subkelas UITextFieldalih-alihUIViewController
rohan-patel
4
Ini tampaknya tidak berfungsi di ios8 sekarang, karena apa yang tampak seperti Bug Apple: devforums.apple.com/message/1045312#1045312
chug2k
1
Saya menggunakan solusi untuk bug ios8 seperti pada jawaban saya dan itu berhasil. Mungkin bermanfaat bagi mereka yang mencari solusi.
furkan3ayraktar
1
deleteBackward()tidak akan dipanggil jika Anda berada return falseditextField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool
igrrik
41

Pembaruan: Lihat jawaban JacobCaraballo untuk contoh yang mengabaikan -[UITextField deleteBackward].

Lihat UITextInput, secara khusus UIKeyInputmemiliki deleteBackwardmetode delegasi yang selalu dipanggil ketika tombol hapus ditekan. Jika Anda melakukan sesuatu yang sederhana, maka Anda dapat mempertimbangkan hanya subklas UILabeldan membuatnya sesuai dengan UIKeyInputprotokol, seperti yang dilakukan oleh SimpleTextInput dan Contoh UIKeyInput iPhone ini . Catatan: UITextInputdan kerabatnya (termasuk UIKeyInput) hanya tersedia di iOS 3.2 dan yang lebih baru.

ma11hew28
sumber
2
Ini adalah jawaban yang benar. Ini non-hacky dan sangat sederhana dengan subclass cepat dari UITextField.
Sam
Baru saja melihat jawaban Yakub di bawah ini. Ini memberikan contoh terperinci tentang ini.
Sam
Perlu dicatat bahwa jawaban ini tidak berfungsi di iOS 5. Jika bidang teks kosong menekan backspace tidak memanggil metode ini.
jfeldman
31

Kode seperti berikut:

@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

Akhirnya, jangan lupa untuk mengubah properti Kelas Kustom dari Bidang Teks ke "MyTextField"

Jeffrey Loo
sumber
5
Ini harus menjadi jawaban yang diterima. Bersih, dan benar-benar menjawab pertanyaan itu.
Ryan Romanchuk
1
Itu menjawab pertanyaan ... Selama Anda menargetkan iOS 6.0+. Sayangnya, di iOS 5, deleteBackward tidak pernah dipanggil di subkelas Anda.
BJ Homer
2
BJ Homer, 93% perangkat ada di iOS 6, jadi tidak menargetkan iOS 5 umumnya bukan masalah besar.
Jonathan.
2
Saya senang saya terus menggulir ke bawah cukup untuk menemukan ini. 100% cara yang tepat untuk melakukan ini hari ini di iOS 7.
MusiGenesis
Saya telah melihat begitu banyak jawaban lain untuk pertanyaan ini yang hanya merupakan solusi, dan hampir tidak ada dari mereka yang berurusan dengan situasi di mana tombol backspace ditekan di bidang kosong. Namun ini sempurna, dan cara yang sangat bersih untuk melakukannya.
Christopher Hannah
19

Implementasi cepat:

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)
        }
    }
}
Ruud Visser
sumber
Terima kasih, boleh saya tahu metode ini direkomendasikan oleh apple atau hack-nya. tampaknya tidak berdokumen untuk bidang teks.
kalpesh jetani
Bekerja untuk saya dengan textView. terima kasih sudah berbagi;)
Edouard Barbier
Bekerja untuk saya ketika bidang teks kosong dan ruang belakang diklik.
Ramakrishna
17

Saya telah menemukan cara lain yang lebih mudah daripada subclasssolusi. Walaupun sedikit aneh tapi berfungsi dengan baik.

- (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;
}

Agak aneh untuk hasil bandingkan adalah -8. Mungkin saya akan salah dalam beberapa hal C Programming. Tapi itu berfungsi dengan benar;)

Jerapong Nampetch
sumber
1
Gaya punggung tidak diatur '\ b'. Tetapi jika Anda hati-hati men-debug maka Anda akan melihat '\ 0'. Jadi saya mendapatkan hasil 0 yaitu dua nilai sama dalam metode strcmp. const char * stoke = [teks cStringUsingEncoding: NSASCIIStringEncoding]; const char * backstroke = "\ 0"; // ini sama dengan \ b -> "\ x08"; strcmp (gaya punggung, stoke);
Yoon Lee
Juga, dengan definisi strcmp (s1, s2), mengembalikan 0 jika s1 == s2,> 0 s1 secara leksikografis lebih besar dari s2 sebaliknya.
Yoon Lee
Saya tidak mengerti bagaimana ini bisa berhasil? @YoonLee: tidakkah Anda mengatakan strcmpkembali juga -1, 0, or 1? Itulah pengertian saya.
chug2k
1
di textview Anda selalu mendeteksi backspace bahkan jika tidak ada teks, UITextField berbeda
LolaRun
2
Ini adalah UITextViewDelegatemetode, bukan UITextFieldDelegate.
pkamb
11

Coba delegate

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

Kemudian periksa apakah range.length == 1yang tampaknya menjadi kasus ketika backspacedipukul.

Niklas Alvaeus
sumber
8
Hanya dipanggil saat bidang tidak kosong. Perhatikan pertanyaan aslinya. :)
Eric Goldberg
Gunakan UITextView untuk ini.
Oleg
11

silakan gunakan kode di bawah ini akan membantu Anda mendeteksi tombol hapus keyboard bahkan jika bidang teks Anda kosong.

Sasaran C:

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

Cepat:

func keyboardInputShouldDelete(_ textField: UITextField) -> Bool { return true }
Pritesh
sumber
Tx - hanya apa yang saya butuhkan. Tapi di mana itu didokumentasikan ??
Andy Weinstein
9

Jawaban Niklas Alvaeus membantu saya keluar dengan masalah serupa

Saya membatasi entri ke set karakter tertentu, tetapi mengabaikan ruang mundur. Jadi saya memeriksanya range.length == 1sebelum memotong NSString. Jika itu benar, saya hanya mengembalikan string dan tidak memotongnya. Lihat di bawah

 - (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);
    }   
 }
Ben Call
sumber
Metode ini mengharapkan boolean dan bukan string sebagai nilai balik
Pascalius
4

Untuk orang-orang yang memiliki masalah tentang jawaban Yakub saya menerapkan subkelas textfield saya sebagai berikut dan itu bekerja dengan baik!

#import <UIKit/UIKit.h>

@class HTTextField;

@protocol HTBackspaceDelegate <NSObject>

@optional
- (void)textFieldDidBackspace:(HTTextField*)textField;
@end

@interface HTTextField : UITextField<UIKeyInput>

@property (nonatomic, assign) id<HTBackspaceDelegate> backspaceDelegate;

@end


#import "HTTextField.h"

@implementation HTTextField

- (void)deleteBackward {
    [super deleteBackward];
    if ([self.backspaceDelegate respondsToSelector:@selector(textFieldDidBackspace:)]){
        [self.backspaceDelegate textFieldDidBackspace:self];
    }
}

- (BOOL)keyboardInputShouldDelete:(UITextField *)textField {
    BOOL shouldDelete = YES;

    if ([UITextField instancesRespondToSelector:_cmd]) {
        BOOL (*keyboardInputShouldDelete)(id, SEL, UITextField *) = (BOOL (*)(id, SEL, UITextField *))[UITextField instanceMethodForSelector:_cmd];

        if (keyboardInputShouldDelete) {
            shouldDelete = keyboardInputShouldDelete(self, _cmd, textField);
        }
    }

    if (![textField.text length] && [[[UIDevice currentDevice] systemVersion] intValue] >= 8) {
        [self deleteBackward];
    }

    return shouldDelete;
}

@end
furkan3ayraktar
sumber
Anda dapat menulis kode untuk cepat. Saya mendapat beberapa kesalahan "redundant confirmance to protoco uikeyinput"
Raj Aggrawal
4

Yup, gunakan metode di bawah ini untuk mendeteksi backspace, ketika textField kosong.

Perlu menambahkan UITextFieldDelegate

yourTextField.delegate = diri (HARUS DIBUTUHKAN)

Cepat:

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

Sasaran C:

- (BOOL)keyboardInputShouldDelete:(UITextField *)textField { 
    return YES; 
}
Himanshu padia
sumber
5
Ini bahkan tidak memanggilku. Semua metode delegasi lainnya dipanggil sebagai dan kapan suatu peristiwa terjadi.
Hemang
Terima kasih sobat .. Anda berhasil. :)
MS.
@ McDonal_11 Saya pikir Anda lupa mengatur textfield.delegate = self of textfield.
Himanshu padia
Saya telah menetapkan. Metode delegasi UITextField lainnya berfungsi dengan baik. Yang ini saja tidak berfungsi. Apa yang saya lewatkan ??
McDonal_11
3

Penggunaan terbaik yang saya temukan untuk mendeteksi backspace adalah mendeteksi ketika pengguna telah menekan backspace dalam keadaan kosong UITextField. Misalnya, jika Anda memiliki penerima 'bubbled' di aplikasi email, ketika Anda menekan backspace di UITextField, itu memilih penerima 'bubbled' terakhir.

Ini bisa dilakukan dengan cara yang mirip dengan jawaban Jacob Caraballo. Tetapi dalam jawaban Jacob, jika UITextFieldsatu karakter tersisa ketika Anda menekan backspace, pada saat pesan delegasi diterima, UITextFieldsudah akan kosong, jadi Anda secara efektif mendeteksi backspacepada bidang teks dengan paling banyak satu karakter.

Sebenarnya, jika Anda ingin mendeteksi backspacepada UITextFieldkarakter yang benar-benar nol (kosong), maka Anda harus mengirim pesan ke delegatesebelum panggilan super deleteBackward. Sebagai contoh:

#import "MyTextField.h"

//Text field that detects when backspace is hit with empty text
@implementation MyTextField

#pragma mark - UIKeyInput protocol
-(void)deleteBackward
{
  BOOL isTextFieldEmpty = (self.text.length == 0);
  if (isTextFieldEmpty) {
    if ([self.delegate 
         respondsToSelector:@selector(textFieldDidHitBackspaceWithEmptyText:)]) {

        [self.delegate textFieldDidHitBackspaceWithEmptyText:self];
        }
    }
    [super deleteBackward];
}
@end

Antarmuka untuk bidang teks seperti itu akan terlihat seperti ini:

@protocol MyTextFieldDelegate;

@interface MyTextField : UITextField
@property(nonatomic, weak) id<MyTextFieldDelegate> delegate;
@end

@protocol MyTextFieldDelegate <UITextFieldDelegate>
@optional
-(void)textFieldDidHitBackspaceWithEmptyText:(MyTextField *)textField;
@end
Sam
sumber
2
Agar ini berfungsi di iOS8 (di mana ada bug yang menyebabkan metode delegasi ini tidak pernah dipanggil), silakan lihat jawaban ini: stackoverflow.com/a/25862878/893101 . Lebih detail tentang bug ios8
pIkEL
2

Di iOS 6, metode deleteBackward dipanggil di UITextField saat backspace ditekan, termasuk saat bidang kosong. Jadi Anda dapat subkelas UITextField dan memberikan implementasi deleteBackward Anda sendiri (memanggil super juga.)

Saya masih mendukung iOS 5 jadi saya akan membutuhkan kombinasi jawaban Andrew dan ini.

tracy
sumber
1

:) hanya untuk judul "Deteksi backspace", tempat saya menggunakan UIKeyboardTypeNumberPad .

Saya juga menjawab pertanyaan yang sama malam ini, dan berikut ini adalah kode saya untuk mengetahuinya:

- (BOOL)textField:(UITextField *)textField 
        shouldChangeCharactersInRange:(NSRange)range 
        replacementString:(NSString *)string
{
    NSLog([NSString stringWithFormat:@"%d", [string length]]);
}

Karena dengan UIKeyboardTypeNumberPad, pengguna hanya dapat memasukkan angka atau backspace, jadi ketika panjang string adalah 0, itu harus menjadi kunci backspace.

Semoga hal di atas akan membantu.

Jason Lee
sumber
Sama dengan semua jenis keyboard.
ma11hew28
bagaimana cara menghubungkan metode ini ke bidang teks saya?
user230910
1

Daripada mencoba untuk membangun apa yang AKAN MENJADI di bidang teks atau mencari tahu karakter khusus apa yang telah dimasukkan dalam shouldChangeCharactersInRangemetode ini, saya sarankan melakukan yang berikut:

[self performSelector:@selector(manageSearchResultsDisplay) 
           withObject:nil 
           afterDelay:0];

Ini memungkinkan Anda untuk memanggil metode secara langsung setelah operasi saat ini selesai. Apa yang keren tentang ini adalah bahwa, pada saat itu selesai, nilai yang diubah akan berada di UITextField. Pada titik itu, Anda bisa memeriksa panjangnya dan / atau memvalidasi berdasarkan apa yang ada di sana.

Harun
sumber
1

Subclassing UITextField tidak berfungsi untuk saya di iOS 8.3, deleteBackward tidak pernah dipanggil.

Berikut adalah solusi yang saya gunakan, bekerja pada semua versi iOS 8 dan juga harus bekerja pada versi iOS lainnya

for textField in textFields {
            textField.text = " "
}

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
        if string == "" && textField.text == " "   {
            // Do stuff here
            return false
        }
        return true
}
joel.d
sumber
1

Dalam file .h tambahkan delegasi UIKeyInput

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

if ([textField isEqual:_txtFirstDigit]) {

}else if([textField isEqual:_txtSecondDigit]) {
    [_txtFirstDigit becomeFirstResponder];

}else if([textField isEqual:_txtThirdDigit]) {
    [_txtSecondDigit becomeFirstResponder];

}else if([textField isEqual:_txtFourthDigit]) {
    [_txtThirdDigit becomeFirstResponder];
}
return YES;
}   

Pemformatan yang ditingkatkan

Anjali Prasad
sumber
1

Saya telah menerapkan solusi serupa dengan perbaikan kecil yang akan memberi tahu saya bahwa jika bidang teks memiliki nilai sementara pengguna telah mengetuk backspace. Ini berguna untuk kasus saya ketika saya hanya harus fokus pada bidang teks lain jika bidang teks kosong ketika backspace ditekan.

protocol MyTextFieldDelegate : UITextFieldDelegate {
    func textFieldDidDelete(textField: MyTextField, hasValue: Bool)
}

override func deleteBackward() {
    let currentText = self.text ?? ""
    super.deleteBackward()
    let hasValue = currentText.isEmpty ? false : true
    if let delegate = self.delegate as? MyTextFieldDelegate {
        delegate.textFieldDidDelete(textField: self, hasValue: hasValue)
    }
}
Hemang
sumber
1

Jawaban yang paling populer adalah satu hal - kemampuan untuk mendeteksi apakah bidang teks kosong atau tidak.

Yaitu, saat Anda mengganti metode deleteBackwards () dari subkelas TextField, Anda masih tidak tahu apakah bidang teks sudah kosong. (Baik sebelum dan sesudah deleteBackwards (), textField.text!adalah string kosong:"" )

Inilah peningkatan saya, dengan memeriksa kekosongan sebelum penghapusan.

1. Buat protokol delegasi yang memperluas UITextFieldDelegate

protocol MyTextFieldDelegate: UITextFieldDelegate {
    func textField(_ textField: UITextField, didDeleteBackwardAnd wasEmpty: Bool)
}

2. Subkelas UITextField

class MyTextField: UITextField {
    override func deleteBackward() {
        // see if text was empty
        let wasEmpty = text == nil || text! == ""

        // then perform normal behavior
        super.deleteBackward()

        // now, notify delegate (if existent)
        (delegate as? MyTextFieldDelegate)?.textField(self, didDeleteBackwardAnd: wasEmpty)
    }
}

3. Terapkan protokol delegasi baru Anda

extension MyViewController: MyTextFieldDelegate {
    func textField(_ textField: UITextField, didDeleteBackwardAnd wasEmpty: Bool) {
        if wasEmpty {
            // do what you want here...
        }
    }
}
Tim
sumber
1

Penangan komprehensif untuk bidang teks dengan nomor satu digit untuk Swift 5.1 :

  • Dengan asumsi bahwa Anda memiliki koleksi outlet textFields (dengan delegasi yang terhubung juga)

1 Langkah

protocol MyTextFieldDelegate: class {
    func textField(_ textField: UITextField, didDeleteBackwardAnd wasEmpty: Bool) 
}

final class MyTextField: UITextField {

    weak var myDelegate: MyTextFieldDelegate?

    override func deleteBackward() {
        let wasEmpty = text == nil || text == ""

        // then perform normal behavior
        super.deleteBackward()

        // now, notify delegate (if existent)
        (delegate as? MyTextFieldDelegate)?.textField(self, didDeleteBackwardAnd: wasEmpty)
    }
}

2 Langkah

final class ViewController: UIViewController {

    @IBOutlet private var textFields: [MyTextField]!

    override func viewDidLoad() {
        super.viewDidLoad()
        textFields.forEach {
            $0.delegate = self
            $0.myDelegate = self
        }
    }
}

3 Langkah

extension ViewController: UITextFieldDelegate, MyTextFieldDelegate {
    func textFieldHasChanged(with text: String, _ tag: Int, for textField: UITextField) {
        textField.text = text

        if let someTextField = (textFields.filter { $0.tag == tag }).first {
            someTextField.becomeFirstResponder()
        } else {
            view.endEditing(true)
        }
    }

    func textField(_ textField: UITextField, didDeleteBackwardAnd wasEmpty: Bool) {
        // If the user was pressing backward and the value was empty, go to previous textField
        textFieldHasChanged(with: "", textField.tag - 1, for: textField)
    }

    func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
        // Restrict to only digits
        let aSet = NSCharacterSet(charactersIn: "0123456789").inverted
        let compSepByCharInSet = string.components(separatedBy: aSet)
        let numberFiltered = compSepByCharInSet.joined(separator: "")

        guard string == numberFiltered, let text = textField.text else { return false }

        if text.count >= 1 && string.isEmpty {
            // If the user is deleting the value
            textFieldHasChanged(with: "", textField.tag - 1, for: textField)
        } else {
            textFieldHasChanged(with: string, textField.tag + 1, for: textField)
        }

        return false
    }
}
Latenec
sumber
0

Di sini solusi saya berdasarkan ide @andrew:

suatu tempat, misalnya di viewDidLoad

        textField.delegate = self
        textField.addTarget(self, action: #selector(valueChanged(_:)), for: .editingDidBegin)

lalu

    @objc func valueChanged(_ textField: UITextField) {
        textField.text = "\u{200B}"
    }

    override func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
        textField.text = string
        if string == "" {
            //backpaspace pressed 
        }
rastislv
sumber
0

Anda dapat memeriksa teks dari tampilan teks / bidang untuk melihat apakah itu kosong dan pastikan teks pengganti juga kosong dalam metode delegasi shouldChangeTextIn.

func textView(_ textView: UITextView, shouldChangeTextIn range: NSRange, replacementText text: String) -> Bool {
    if (textView.text == "" && text == "") {
        print("Backspace on empty text field.")
    }
    return true
}
michael-k101
sumber
-2

Sesuatu seperti ini:

- (BOOL)textField:(UITextField *)textField 
        shouldChangeCharactersInRange:(NSRange)range 
        replacementString:(NSString *)string       
{  
    if (![text hash] && ![textField.text length])  
        [self backspaceInEmptyTextField];  
}

Tentu saja hash adalah untuk satu karakter string.

pengguna1375355
sumber
-2

Menggunakan metode Delegasi TextField:

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

Tambahkan kode berikut dalam metode di atas untuk mendeteksi acara yang dihapus

if(textField == YourTextField)
{
    if ([string length] == 0 && range.length > 0)
    {
        // Your Code after deletion of character
    }
}
kalim sayyad
sumber
-3

Agar Tetap Sederhana di sini adalah satu-satunya syarat yang perlu Anda periksa

     if (range.length==1)
Bhumit Mehta
sumber
-3
+ (BOOL)detectBackspaceOnly:(NSString *)string
{
    for(int i=0 ; i<string.length ; i++){
        unichar caract = [string characterAtIndex:i];
        if(caract != ' ' && caract != '\n')
            return NO;
    }

    return YES;
}
K-AnGaMa
sumber
2
Mungkin sedikit penjelasan di mana harus meletakkan ini?
Alex Cio
-4

Di UITextViewDelegate:

- (BOOL)               textView:(UITextView *)textView 
        shouldChangeTextInRange:(NSRange)range 
                replacementText:(NSString *)text
{
    if(text isEqualToString:@"");
    {
        NSLog(@"press backspace.");
    }
}

itu berfungsi baik untuk saya.

pembaruan untuk input tulisan tangan dan tulisan tangan Cina sederhana:

- (BOOL)               textView:(UITextView *)textView 
        shouldChangeTextInRange:(NSRange)range 
                replacementText:(NSString *)text
{
    if (range.length > 0 && [text isEqualToString:@""]) {
        NSLog(@"press Backspace.");
    }
    return YES;
}

berdasarkan dokumen mengatakan:

"Jika pengguna menekan deleteKey, panjang rentang adalah 1 dan objek string kosong menggantikan karakter tunggal itu."

pelawak
sumber
1
Pertanyaan ini tentang UITextField, bukan UITextView.
ma11hew28