why is my function called twice?
I have a swipe recognizer attached to cells in my table view
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
//swipe recognition
UISwipeGestureRecognizer *g = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:@selector(cellWasSwiped:)];
[cell addGestureRecognizer:g];
开发者_JS百科 [g release];
}
// Configure the cell...
[[cell textLabel] setText:[NSString stringWithFormat:@" number %d", indexPath.row]];
return cell;
}
and the swipe function is
- (void)cellWasSwiped:(UIGestureRecognizer *)g {
NSLog(@"sunt in cellWasSwiped");
swipeViewController *svc = [[swipeViewController alloc]init];
[self.navigationController pushViewController:svc animated:YES];
[svc release];
}
and by introducing breakpoints i see that my swipe function is called 2 times and there are two identical view controllers pushed on my navigation controller. Why is my swipe function called twice when i swipe a cell?
Your cellWasSwiped
can be called multiple times on change of UIGestureRecognizer
state. You need to check property state
, it will be UIGestureRecognizerStateEnded
when user finished his action. It's also good to check for states UIGestureRecognizerStateFailed
and UIGestureRecognizerStateCancelled
.
I had that same specific problem with swiping in a table cell. My recognizer method was called twice with state UIGestureRecognizerStateEnded.
I worked around it as follows:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *CellIdentifier = @"CellIdentifier";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
//... create cell
//... create swipe recognizer (in my case attached to cell's contentView)
}
for (UIGestureRecognizer* g in cell.contentView.gestureRecognizers)
g.enabled = YES;
}
and then
-(void) cellWasSwiped: (UIGestureRecognizer*) recognizer {
if (recognizer.state != UIGestureRecognizerStateEnded)
return;
if (recognizer.enabled == NO)
return;
recognizer.enabled = NO;
//... handle the swipe
//... update whatever model classes used for keeping track of the cells
// Let the table refresh
[theTable reloadData];
}
Instead of adding the gesture recognizer to the cell directly, you can add it to the tableview in viewDidLoad
.
In the cellWasSwiped
-Method you can determine the affected IndexPath and cell as follows:
-(void)cellWasSwiped:(UIGestureRecognizer *)gestureRecognizer {
if (gestureRecognizer.state == UIGestureRecognizerStateEnded) {
CGPoint swipeLocation = [gestureRecognizer locationInView:self.tableView];
NSIndexPath *swipedIndexPath = [self.tableView indexPathForRowAtPoint:swipeLocation];
UITableViewCell* swipedCell = [self.tableView cellForRowAtIndexPath:swipedIndexPath];
// ...
}
}
精彩评论