简体   繁体   中英

How to handle events (Touch Up Inside/Outside) for UItableViewCell with a text field?

I have a custom UITableViewCell which has a text field inside it. I have created it using IB and have a custom class with it.

Now, my issue is that I want to setup the text field so that during text entry if the user clicks outside the text field (without hitting the return/done key on the keypad), the field resigns first responder. I understand, that do that I need to handle the Touch Up Inside Event. However my tableview class never receives this event even though I have done the connections. I am assuming that its because its not subclass of UIcontrol, which I cant make it as it needs to be UITableViewCel.

So whats the solution?? How do I receive these events??

Header File:

#import <UIKit/UIKit.h>

@interface MMSingleTextFieldCell : UITableViewCell <UITextFieldDelegate>

// Properties
@property (weak, nonatomic) IBOutlet UITextField *singleTextField;
// Methods
- (IBAction)eventTouchUpOutside:(id)sender;
- (IBAction)eventTouchUpInside:(id)sender;
@end

Class File:

#import "MMSingleTextFieldCell.h"

@implementation MMSingleTextFieldCell

@synthesize singleTextField;


- (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
{
    self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
    if (self) {
        // Initialization code
    }
    return self;
}

- (void)setSelected:(BOOL)selected animated:(BOOL)animated
{
    [super setSelected:selected animated:animated];

    // Configure the view for the selected state
}


- (IBAction)eventTouchUpOutside:(id)sender {
    [singleTextField resignFirstResponder];
}

- (IBAction)eventTouchUpInside:(id)sender {
    [singleTextField resignFirstResponder];

}

I have just recently open sourced a project on Github that should make this all relatively easy to do. It includes a class that can be easily inserted into a cell and a sample project demonstrating its capabilities.

If you look in RootTableViewController's viewDidLoadMethod you will see that I am adding a gesture recognizer:

    self.tapGestureRecognizer = [[UITapGestureRecognizer alloc] initWithTarget:self
                                                                        action:@selector(dismissKeyboard)];
    _tapGestureRecognizer.delegate = self;
    _tapGestureRecognizer.cancelsTouchesInView = NO;
    [self.tableView addGestureRecognizer:_tapGestureRecognizer];

Add the dismiss keyboard method:

    - (void)dismissKeyboard {
        [_textField resignFirstResponder];
    }

Add a gesture recognizer callback (in RootTableViewController):

//see: http://stackoverflow.com/questions/7195661/why-is-uigesturerecognizer-being-called-on-my-textfield-clear-button
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch
{
    if([touch.view isKindOfClass:[UITextField class]] ||
       [touch.view isKindOfClass:[UIButton class]])
    {
        return NO;
    }
    return YES;
}

Of course, this means you have to make RootTableViewController adhere to the UIGestureRecognizerDelegate protocol (in the header file):

@interface RootTableViewController : UITableViewController<SATextFieldDelegate, UIGestureRecognizerDelegate>

If you want the user to scroll the table view and dismiss the keyboard implement the following table view delegate callback:

- (void)scrollViewWillBeginDragging:(UIScrollView *)activeScrollView {
    if (_textField.isFirstResponder) {
        [self dismissKeyboard];
    }
}

I believe this is the function you want.

 -(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event{
      if (_textField.isFirstResponder) {
         [self dismissKeyboard];
      }
  }

Try this:

1) Implement the UIGestureRecognizerDelegate protocol

2) In viewDidLoad for example, create the following

    UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc]
                                   initWithTarget:self
                                   action:@selector(hideKeyboard:)];

    tap.delegate = self;
    [self.view addGestureRecognizer:tap];

3) Now, implement the method from protocol from 1

-(BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch{
    // Use this for allow some control to receive his natural tap event. You can use tap.cancelsTouchesInView = NO; in the 2 step instead of this, try both of then and choose on your own.
    if (touch.view == <some control>) {
        //NSLog(@"NO");
        return NO;
    }
    //NSLog(@"YES");

    return YES;
}

4) finally, implement the callback for tap

-(void) hideKeyboard:(id)sender{

    if (<your edit text>.isEditing) {
        [<your edit text> resignFirstResponder];
    }
}

I hope this will help, or at least point you to the right direction

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM