我怎么知道UITableView什么时候失去焦点?

时间:2012-08-30 11:44:50

标签: ios

我有一个UITableView,每行有一个UITextField。当用户触摸tableview外部,取消选择文本字段时,我想调用一个方法。

但是,如果用户选择表的另一行,我不想调用此方法。

感谢

** alloc_iNit的代码**:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";

    CMTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) {
        cell = [[[CMTableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
    }

    [[cell textField] setTag:[indexPath row]];
    [[cell textField] setDelegate:self];

    NSString *tagName = [tagsDisplayName objectAtIndex:[indexPath row]];
    [[cell textField] setText:tagName];

    return cell;
}

4 个答案:

答案 0 :(得分:1)

需要考虑的是在UITableView后面的视图上使用Tap Gesture识别器。您可能必须使用shouldReceiveTouch事件(在Gesture recognizer and button actions中详细说明),以便在您单击UITableView中的某个位置时阻止Tap Gesture Recognizer触发。

答案 1 :(得分:0)

您必须在实际的UITableView本身上覆盖 hitTest:withEvent:。请记住,它控制了响应者链,因此子视图不会有机会首先处理它,除非我们明确地覆盖了这种行为

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

hitTest:withEvent:负责告诉系统哪个视图被命中,默认情况下UITableView会假定自己(或其中一个单元格),因此您必须弄清楚用户是否触摸了位置,如果用户触摸了tableview之外,那么返回该视图。

修改后的代码:

- (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event
{ 
    NSLog(@"hitTest");
    UIView *subview = [super hitTest:point withEvent:event];
    if (event.type == UIEventTypeTouches) 
    {        
        // get touches
        NSSet *touches = [event allTouches];

        NSLog(@"subview: %@", subview);
        NSLog(@"touches: %@", touches);
    }
}

答案 2 :(得分:0)

第一个建议:

我相信系统会帮助你,因为它对我没有帮助(我必须解决它)。如果您有两个文本字段,并且您打开了一个文本字段,则点击另一个文本字段,然后第二个文本字段

textFieldDidShouldBeginEditing:

在发送原始文件之前:

textFieldDidEndEditing: // or textFieldShouldEndEditing

向项目中添加几条日志消息以验证这一点,如果不是这样,则可能是其他消息。一年前,由于明显的混乱,我遇到了一个问题。

2012-08-30 09:22:40.528 Searcher[22053:f803] SHOULD BEGIN // first tap on first textField
2012-08-30 09:22:40.534 Searcher[22053:f803] BEGIN
2012-08-30 09:22:42.168 Searcher[22053:f803] SHOULD BEGIN // second tap on second TF
2012-08-30 09:22:42.168 Searcher[22053:f803] SHOULD END
2012-08-30 09:22:42.170 Searcher[22053:f803] END

第二个建议:

用户可以在任何地方点按视图,但是如果他们点击相同的文本字段(以获得复制/粘贴),则您不想解雇。

  • 创建一个新的ivar,当它获得'textFieldDidShouldBeginEditing'时存储textField:

    __阻止UITextField * currTextField;

  • 在检测触摸事件的视图(键盘除外)上放置透明视图

  • 当透明视图看到触摸事件时,如果没有设置textField或触摸在原始touchView内,则不执行任何操作

  • 如果触摸位于其他任何位置,并且有一个currentTextField,则转发该事件,然后按如下方式将一个块发送到mainQueue:

    UITextField * lastTextField = currTextField; dispatch_async(dispatch_get_main_queue(), ^ {   if(currTextField&& currTextField == lastTextField){     [currTextField resignFirstResponder]; //触摸textField外部,但没有新的   } });

答案 3 :(得分:0)

-(void)textFieldDidBeginEditing:(UITextField *)textField
{   
    if(activeTextField) //declare it in .h file
        [self textFieldDidEndEditing:activeTextField];

    activeTextField = textField;

    CGRect textViewRect = [tableView convertRect:activeTextField.bounds fromView:activeTextField];

    [tableView scrollRectToVisible:textViewRect animated:NO]; //if u want to add scroll to that cell
} 


- (void)textFieldDidEndEditing:(UITextField *)textField
{
    activeTextField = nil;
}

然后你可以使用touchesBegan

-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
    [activeTextField resignFirstResponder];
}
希望这个有所帮助。快乐的编码:)