1

各行に UITextField を持つ UITableView があります。ユーザーがテーブルビューの外に触れて、テキスト フィールドの選択を解除すると、メソッドを呼び出したいと思います。

ただし、ユーザーがテーブルの別の行を選択した場合、そのようなメソッドを呼び出したくありません。

ありがとう

**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

4 に答える 4

1

考慮すべきことは、UITableView の背後にあるビューでタップ ジェスチャ レコグナイザーを使用することです。UITableView のどこかをクリックしたときに Tap Gesture Recognizer が 起動しないようにするには、 shouldReceiveTouch イベント ( Gesture Recognizerとボタン アクションで詳しく説明) をいじる必要がある場合があります。

于 2012-08-30T13:00:34.297 に答える
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];
}

これが役立つことを願っています。幸せなコーディング:)

于 2012-08-30T13:12:07.040 に答える
0

最初の提案:

私は役に立たなかったので、このシステムがあなたを助けると信じています(私はそれを回避しなければなりませんでした)。2 つのテキストフィールドがあり、1 つが開いている場合、別のフィールドをタップすると、2 つ目のフィールドが取得されます

textFieldDidShouldBeginEditing:

元のものが送信される前に:

textFieldDidEndEditing: // or textFieldShouldEndEditing

プロジェクトにいくつかのログ メッセージを追加してこれを確認します。そうでない場合は、他のメッセージである可能性があります。明らかな無秩序のために私が問題を抱えていたのは1年前のことでした.

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

2 番目の提案:

ユーザーはどこでもビューをタップできますが、(コピー/貼り付けを取得するために) 同じテキストフィールドをタップした場合、閉じたくありません。

  • 「textFieldDidShouldBeginEditing」を取得したときに textField を格納する新しい ivar を作成します。

    __block UITextField *currTextField;

  • タッチイベントを検出するビュー(キーボードを除く)の上に透明なビューを置きます

  • 透過ビューがタッチ イベントを検出したとき、textField が設定されていないか、タッチが元の touchView 内にある場合は、何もしません。

  • タッチが他の場所にあり、currentTextField がある場合は、イベントを転送してから、次のようにブロックを mainQueue にディスパッチします。

    UITextField *lastTextField = currTextField; dispatch_async(dispatch_get_main_queue(), ^{ if(currTextField && currTextField == lastTextField) { [currTextField rejectFirstResponder]; // textField の外側に触れますが、新しいものはありません } } );

于 2012-08-30T12:11:12.247 に答える
0

実際の UITableView 自体でhitTest:withEvent:をオーバーライドする必要があります。レスポンダーチェーンを制御するため、その動作を明示的にオーバーライドしない限り、サブビューは最初にそれを処理する機会を得られないことに注意してください

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

hitTest:withEvent:は、ヒットしたビューをシステムに伝える責任があります。デフォルトでは、UITableView がそれ自体 (またはそのセルの 1 つ) を想定しているため、ユーザーが場所に触れたかどうかを把握する必要があり、ユーザーがテーブルビューの外に触れたかどうかを確認する必要があります。代わりにそのビュー。

変更されたコード:

- (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)イベント
{
    NSLog(@"hitTest");
    UIView *subview = [super hitTest:point withEvent:event];
    if (event.type == UIEventTypeTouches)
    {        
        // タッチする
        NSSet *touches = [イベント allTouches];

        NSLog(@"サブビュー: %@", サブビュー);
        NSLog(@"タッチ: %@", タッチ);
    }
}
于 2012-08-30T11:59:42.553 に答える