mi imbatto nello stesso problema da poco e ci sono voluti un po 'per farlo riparare. Il problema è che quando il campo di testo è annidato in ReusableCollectionView il seguente non funziona.
[self.collectionView reloadData];
[self.textField becomeFirstResponder];
Inoltre, per me ha funzionato bene sul simulatore ma non ha funzionato sul dispositivo.
Impostazione vista controller come campo di testo delegato e attuazione
- (BOOL)textFieldShouldEndEditing:(UITextField *)textField {
return NO;
}
non ha funzionato perché, come la vista collezione risultato non aggiornare. La mia ipotesi è - prima di ricaricare la sua collezione di viste si tenta di rimuovere l'attenzione da tutti i controlli annidati, ma non può farlo - restituiamo NO dal metodo del delegato del campo di testo.
Quindi la soluzione per me era lasciare che il sistema rimuovesse lo stato attivo dal campo di testo, ma poi recuperarlo dopo averlo ricaricato. La domanda era quando effettivamente farlo.
In primo luogo, ho cercato di farlo nel
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
ma quando non c'erano articoli in collezione (che è caso normale durante la filtrazione) questo metodo non ha ottenuto chiamato.
Eventualmente ho risolto questo nel modo seguente. Ho creato la sottoclasse UICollectionReusableView che implementa due metodi: -prepareForReuse e -drawRect :. Il primo contiene la chiamata -setNeedsDesplay che pianifica la chiamata drawRect al successivo ciclo di disegno. Il secondo ripristina l'attenzione chiamando [self.textField becomeFirstResponder] se il flag corrispondente è impostato su YES. Quindi l'idea era di chiamare diventato prima "Rispondi" ma non troppo tardi, altrimenti si verifica un "salto" strano della tastiera.
mia abitudine vista di raccolta riutilizzabile assomiglia a questo:
@interface MyCollectionReusableView : UICollectionReusableView
@property (nonatomic, assign) BOOL restoreFocus;
@property (nonatomic, strong) UITextField *textField;
@end
@implementation MyCollectionReusableView
@synthesize restoreFocus;
@synthesize textField;
- (void)setTextField:(UITextField *)value {
textField = value;
[self addSubview:textField];
}
- (void)drawRect:(CGRect)rect {
[super drawRect:rect];
if (self.restoreFocus) {
[self.textField becomeFirstResponder];
}
}
- (void)prepareForReuse {
[self setNeedsDisplay];
}
Poi nel mio View Controller:
- (void)viewDidLoad {
[super viewDidLoad];
[self.collectionView registerClass:[MyCollectionReusableView class] forSupplementaryViewOfKind:UICollectionElementKindSectionHeader withReuseIdentifier:HeaderReuseIdentifier];
[self.textField addTarget:self action:@selector(textFieldDidChange:) forControlEvents:UIControlEventEditingChanged];
}
- (UICollectionReusableView *)collectionView:(UICollectionView *)collectionView viewForSupplementaryElementOfKind:(NSString *)kind atIndexPath:(NSIndexPath *)indexPath {
if (UICollectionElementKindSectionHeader == kind) {
MyCollectionReusableView *view = [collectionView dequeueReusableSupplementaryViewOfKind:UICollectionElementKindSectionHeader withReuseIdentifier:HeaderReuseIdentifier forIndexPath:indexPath];
//add textField to the reusable view
if (nil == view.textField) {
view.textField = self.textField;
}
//set restore focus flag to the reusable view
view.restoreFocus = self.restoreFocus;
self.restoreFocus = NO;
return view;
}
return nil;
}
- (void)textFieldDidChange:(UITextField *)textField {
self.restoreFocus = YES;
[self.collectionView reloadData];
}
non
Probabilmente la soluzione più elegante, ma funziona. :)
Grazie per questa domanda. – GeneCode