2009-12-19 6 views
2

J'ai une situation ici, je dois gérer touchesBegan pour textfield. Ce champ de texte est en scrollview.handle touchesBegan méthode pour UITextField dans UIScrollView

J'ai essayé jusqu'à présent:

J'ai fait une sous-classe de UIScrollView

@interface CustomScrollView : UIScrollView 
{ 
} 
@end 

@implementation CustomScrollView 

-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    NSLog(@"good"); 
} 

@end 

Ici, je peux obtenir le résultat souhaité.

Même chose que j'ai implémenté avec les champs de texte. J'ai fait une sous-classe de UITextField:

@interface CustomTextField : UITextField 
{ 
} 
@end 

@implementation CustomTextField 

-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    NSLog(@"good"); 
} 

@end 

Cela fonctionne bien si le champ de texte est à l'intérieur d'une vue normale, mais il échoue lorsque le champ de texte se trouve dans un ScrollView régulier ou mon scrollview personnalisé.

S'il vous plaît me éclairer sur ce

(je fais cela pour atteindre quelque chose comme ça lorsque l'utilisateur appuie longtemps un champ de texte le texte TextField est attribué de Textfield à une étiquette et l'utilisateur peut faire glisser cette étiquette à un autre endroit dans la vue)

Répondre

6

Par défaut, UIScrollView retarde l'envoi d'événements tactiles à ses vues enfant jusqu'à ce qu'il puisse déterminer si le contact est supposé provoquer un défilement. Vous pouvez le prouver en tapant et en maintenant votre champ de texte - touchesBegan tirera après un moment. Pour résoudre ce problème, définissez simplement la propriété delaysContentTouches de votre vue de défilement personnalisée sur NO. Cela peut être fait via Interface Builder en décochant "Retarder les touches de contenu". Dans le code, il suffit de faire quelque chose de semblable à ce qui suit:

_myCustomScrollView.delaysContentTouches = NO; 

La méthode touchesBegan de votre CustomTextField va maintenant le feu immédiatement. Sachez toutefois que les utilisateurs ne pourront plus naviguer dans le CustomScrollView si leur frappe initiale se trouve dans une sous-vue. Avec delaysContentTouches défini sur non, essayez de taper à l'intérieur de votre champ de texte (ou de toute sous-vue d'ailleurs) et de glisser - vous verrez qu'aucun défilement ne se produit. Lorsque le paramètre delayContentTouches est défini sur yes, l'utilisateur peut appuyer et balayer de n'importe où dans les limites du CustomScrollView et le faire défiler.

Si vous voulez le meilleur des deux mondes (les utilisateurs défilant de n'importe où et les sous-vues pouvant répondre aux touches), vous substituez la méthode hitTest dans votre CustomScrollView et envoyez un message à la sous-vue touchée. Voici la mise en œuvre dans le CustomScrollView:

-(UIView *)hitTest:(CGPoint)point withEvent:(UIEvent*)event { 
    UIView *hitView = [super hitTest:point withEvent:event]; 

    if([hitView class] == [CustomTextField class]) { 
     [(CustomTextField *) hitView handleTap:point]; 
    } 

    return hitView; 
} 

Et voici la mise en œuvre de CustomTextField:

@interface CustomTextField : UITextField { 

} 

-(void) handleTap:(CGPoint) point; 

@end 

@implementation CustomTextField 

-(void) handleTap:(CGPoint) point { 
    // Implement your handling code here 
} 

@end 

C'est un hack en ce qu'il est ne gère pas vraiment touches (touchesBegan, touchesEnded, etc.), mais travaux.

+0

Vous avez sauvé ma journée;) – DeZigny

3

I mis en œuvre et un CustomUIScrollView comme une sous-classe de UIScrollView et réenregistrés la méthode touchesBegan:

- (void) touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    if (!self.dragging) 
    { 
     [self.nextResponder touchesBegan:touches withEvent:event]; 
    } 
    else 
    { 
     [super touchesBegan:touches withEvent:event]; 
    } 
} 

En InterfaceBuilder je mets la classe personnalisée de l'objet scrollview à CustomUIScrollView et dans la partie « Touch » I désactivé Touches de contenu annulables.Maintenant, je pourrais utiliser la méthode touchesBegan dans le ViewController de mon UITextField pour laisser le clavier disparaître quand une touche en dehors du clavier est détectée.

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    UITouch *touch = [[event allTouches] anyObject]; 
    if ([myTextField isFirstResponder] && [touch view] != myTextField) 
    { 
     [myTextField resignFirstResponder]; 
    } 
    [super touchesBegan:touches withEvent:event]; 
}