Jak stwierdzono tutaj: Zdarzenie zmiany tekstu UITextField , wydaje się, że od iOS 6 (sprawdzone iOS 6.0 i 6.1) nie jest możliwe pełne wykrycie zmian w UITextField
obiektach po prostu obserwując UITextFieldTextDidChangeNotification
.
Wygląda na to, że śledzone są teraz tylko te zmiany wprowadzone bezpośrednio przez wbudowaną klawiaturę iOS. Oznacza to, że jeśli zmienisz UITextField
obiekt tylko przez wywołanie czegoś takiego: myUITextField.text = @"any_text"
nie otrzymasz powiadomienia o żadnych zmianach.
Nie wiem, czy to błąd, czy zamierzony. Wygląda na błąd, ponieważ nie znalazłem żadnego uzasadnionego wyjaśnienia w dokumentacji. Jest to również stwierdzone tutaj: Zdarzenie zmiany tekstu UITextField .
Moje „rozwiązanie” tego problemu polega na tym, że faktycznie wysyłam powiadomienie o każdej wprowadzonej przeze mnie zmianie UITextField
(jeśli ta zmiana zostanie dokonana bez użycia wbudowanej klawiatury iOS). Coś takiego:
myUITextField.text = @"I'm_updating_my_UITextField_directly_in_code";
NSNotification *myTextFieldUpdateNotification =
[NSNotification notificationWithName:UITextFieldTextDidChangeNotification
object:myUITextField];
[NSNotificationCenter.defaultCenter
postNotification:myTextFieldUpdateNotification];
W ten sposób masz 100% pewności, że otrzymasz takie samo powiadomienie po zmianie .text
właściwości swojegoUITextField
obiektu, albo kiedy zaktualizujesz go „ręcznie” w kodzie, albo za pomocą wbudowanej klawiatury iOS.
Należy wziąć pod uwagę, że ponieważ nie jest to udokumentowane zachowanie, takie podejście może prowadzić do otrzymania 2 powiadomień o tej samej zmianie w UITextField
obiekcie. W zależności od potrzeb (co faktycznie robisz po UITextField.text
wprowadzeniu zmian) może to być dla Ciebie niedogodne.
Nieco innym podejściem byłoby opublikowanie niestandardowego powiadomienia (to znaczy o niestandardowej nazwie innej niż UITextFieldTextDidChangeNotification
), jeśli faktycznie chcesz wiedzieć, czy powiadomienie było twoje, czy „wykonane na iOS”.
EDYTOWAĆ:
Właśnie znalazłem inne podejście, które moim zdaniem mogłoby być lepsze:
Dotyczy to funkcji Key-Value Observing (KVO) Objective-C ( http://developer.apple.com/library/ios/#documentation/cocoa/conceptual/KeyValueObserving/KeyValueObserving.html#//apple_ref/doc/uid / 10000177-BCICJDHA ).
Zasadniczo rejestrujesz się jako obserwator nieruchomości, a jeśli ta właściwość się zmieni, zostaniesz o tym powiadomiony. „Zasada” jest dość podobna do tego NSNotificationCenter
, jak działa, jest to główna zaleta, że to podejście działa automatycznie również od iOS 6 (bez żadnych specjalnych poprawek, takich jak konieczność ręcznego publikowania powiadomień).
W naszym UITextField
scenariuszu działa to dobrze, jeśli dodasz ten kod, na przykład do tego, UIViewController
który zawiera pole tekstowe:
static void *myContext = &myContext;
- (void)viewDidLoad {
[super viewDidLoad];
//Observing changes to myUITextField.text:
[myUITextField addObserver:self forKeyPath:@"text"
options:NSKeyValueObservingOptionNew|NSKeyValueObservingOptionOld
context:myContext];
}
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object
change:(NSDictionary *)change context:(void *)context {
if(context == myContext) {
//Here you get notified every time myUITextField's "text" property is updated
NSLog(@"New value: %@ - Old value: %@",
[change objectForKey:NSKeyValueChangeNewKey],
[change objectForKey:NSKeyValueChangeOldKey]);
}
else
[super observeValueForKeyPath:keyPath ofObject:object
change:change context:context];
}
Podziękowania dla tej odpowiedzi dotyczącej zarządzania „kontekstem”: https://stackoverflow.com/a/12097161/2078512
Uwaga: Wydaje się, gdy jesteś w procesie edycji UITextField
z wbudowaną klawiaturą iOS, „Tekst” własność pola tekstowego nie jest aktualizowany przy każdej nowej litery wpisane / usunięte. Zamiast tego obiekt pola tekstowego jest aktualizowany „jako całość” po rezygnacji ze statusu pierwszego pola odpowiadającego w polu tekstowym.