2012-01-22 3 views
13

UITableView에서 마지막 레코드를 삭제할 때 다음과 같은 오류가 발생합니다. '잘못된 갱신 :마지막 레코드를 삭제할 때 UITableView deleteRowsAtIndexPath 충돌이 발생합니다.

때문에, 이유 캐치되지 않는 예외 'NSInternalInconsistencyException '응용 프로그램 종료 행 무효 수를 섹션 0에 기존 섹션에 포함 된 행의 수를 업데이트 후 (3)해야합니다 업데이트 (1) 이전에 해당 섹션에 포함 된 행의 수와 같거나 그 부분에서 삽입 또는 삭제 된 행 수 ( 1이 삭제됨)를 더한 또는 빼기 옮긴 행 수를 더한 값 또는 빼기 값 또는 섹션 (0은 0으로 이동, 0은 밖으로 이동)이 에서 벗어났습니다. '

목표는 테이블 배열이 비어있는 경우 "레코드를 찾을 수 없음"을 표시하는 것입니다.

이것은 내가 사용하고있는 코드입니다. 테이블 배열에서 마지막 레코드를 삭제하면 응용 프로그램이 충돌합니다. 테이블을 다시로드하고 "No Record Found"레이블을 표시하는 방법은 무엇입니까?

// Customize the number of rows in the table view. 
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { 
    if ([idArray count]==0) { 
     return 3; 
    } 
    else 
    { 
     return [idArray count]; 
    } 
} 

// Customize the appearance of table view cells. 
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { 

    NSLog(@"array count %d",[idArray count]); 
    if ([idArray count] == 0) { 
     static NSString *CellIdentifier = @"Cell"; 

     UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; 
     if (cell == nil) { 
      cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier]; 
     } 
     cell.textLabel.textAlignment = UITextAlignmentCenter; 

     tableView.userInteractionEnabled = NO; 

     self.navigationItem.leftBarButtonItem.enabled = NO; 
     NSUInteger row = [indexPath row]; 

     switch (row) { 
      case 0: 
       cell.textLabel.text = @""; 
       break; 
      case 1: 
       cell.textLabel.text = @""; 
       break; 

      case 2: 
       cell.textLabel.text = @"No Records Found"; 
       break; 


      default: 
       break; 
     }   

     return cell; 
    } 
    else 
    { static NSString *CellIdentifier = @"Cell"; 

     UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; 
     if (cell == nil) { 
      cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier]; 
     } 

     tableView.userInteractionEnabled = YES; 

     self.navigationItem.leftBarButtonItem.enabled = YES; 

     // Set up the cell 
     identify *idItems = [idArray objectAtIndex:indexPath.row]; 

     NSDateFormatter *formatter = [[NSDateFormatter alloc] init]; 
     [formatter setDateFormat:@"dd MMM,yyyy"]; 
     NSString *dateStr = [formatter stringFromDate:idItems.Date]; 
     UIImageView *accDis = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"Arrow.png"]];  
     cell.accessoryView = accDis; 
     self.idTableView.separatorColor = [UIColor colorWithRed:150.0/255.0 green:150.0/255.0 blue:150.0/255.0 alpha:1]; 
     cell.textLabel.textColor = [UIColor blackColor]; 
     cell.textLabel.font = [UIFont boldSystemFontOfSize:18]; 
     cell.textLabel.adjustsFontSizeToFitWidth = YES; 
     cell.detailTextLabel.textColor = [UIColor colorWithRed:100.0/255.0 green:100.0/255.0 blue:100.0/255.0 alpha:1]; 
     cell.detailTextLabel.font = [UIFont italicSystemFontOfSize:16]; 
     cell.detailTextLabel.adjustsFontSizeToFitWidth = YES; 

     NSString *detailText = [NSString stringWithFormat:@"%@ - %@",dateStr,idItems.GeoCode]; 

     if (idItems.Image == NULL) { 
      cell.imageView.image = [UIImage imageNamed:@"icon58x58.png"]; 
     } 
     else 
     { 
     //pass image to fix size 50 X 50 
     //UIImage *newImage = [self postProcessImage:idItems.Image]; 
      cell.imageView.image = idItems.thumb;//newImage; 
     cell.imageView.contentMode=UIViewContentModeScaleAspectFill; 
     } 

     cell.textLabel.text = idItems.TypeName; 
     cell.detailTextLabel.text = detailText; 

     return cell; 
    }  
} 

- (void)tableView:(UITableView *)tv commitEditingStyle:(UITableViewCellEditingStyle)editingStyle 
    forRowAtIndexPath:(NSIndexPath *)indexPath { 

    if(editingStyle == UITableViewCellEditingStyleDelete) { 

     if ([idArray count] >=1) 
     { 
      [idTableView beginUpdates]; 

      //Get the object to delete from the array. 
      identifyObject = [appDelegate.idArray objectAtIndex:indexPath.row]; 

      //Delete the object from the table. 
      [self.idTableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; 
      [appDelegate removeID:identifyObject]; 

      if ([idArray count] == 0) { 
       [self.idTableView insertRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; 
      } 
      [idTableView endUpdates]; 
     } 
    } 
} 
+0

하는 줄에 응용 프로그램 충돌을합니까? 무슨 콘솔 로그? – sergio

+0

크래시 로그를 보내주십시오. 편집 : 아, 아니. 그것을 발견. –

+0

Thanks Updated Crash log – Desmond

답변

14

문제는 뷰에서 수행 된 작업이 데이터 원본과 일치해야한다는 것입니다. 테이블에 하나의 레코드가 있고이를 제거합니다. tableview는 이제 데이터 소스에 0 레코드가 포함될 것으로 예상하지만 "레코드가 없습니다"로직으로 인해 실제로 값 3을 반환하므로 일관성 오류와 충돌이 발생합니다.

if ([idArray count] == 0) { 
    [self.idTableView insertRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; 
} 
내가 마지막 행이 삭제 될 때이 테이블에 "레코드가 발견되지"행을 삽입 의도 가정

하지만 "아니오 기록 이후 발견

버그는이 부분이 될 것 같다 "실제로 세 개의 행에 걸쳐,이 같은 대신 여기에 세 개의 행을 삽입해야합니다

if ([idArray count] == 0) { 
    [self.idTableView insertRowsAtIndexPaths:[NSArray arrayWithObjects: 
    [NSIndexPath indexPathForRow:0 inSection:indexPath.section], 
    [NSIndexPath indexPathForRow:1 inSection:indexPath.section], 
    [NSIndexPath indexPathForRow:2 inSection:indexPath.section], 
    nil] withRowAnimation:UITableViewRowAnimationFade]; 
} 

당신이 그러나 정신을 소유, 나는 다른 접근 방식을 제안 할 수 있습니다? 테이블과 데이터 소스를 동기화 상태로 유지하는 대신 표시 목적으로 만 존재하는 위의 3 행의 데이터를 저글링하면서 왜 UILabel을 뷰 계층 구조 (테이블 뷰의 앞 또는 뒤쪽)에 삽입하지 않고 " 레코드가 발견되지 않음 "을 표시하고 테이블에 데이터가 있는지 여부에 따라 표시/숨기기를할까요? 그렇게하면 데이터 원본 논리를 사용하지 않고도 위치와 모양을 정확하게 제어 할 수 있습니다. 행을 삭제 다루는

+0

감사합니다. nick. 나는 밖으로 시도 할 것이다 – Desmond

+0

그래서 ... 그것은 작동 했습니까? –

+0

그것은 특정 연장에서 작동합니다, 마지막 행은 제거 ...하지만 재미있는 버그를 보여줍니다. 나는 UR을 보여줄 것을 권유하고 UILABEL은 기록이 없다는 것을 알게된다. – Desmond

10

일반 규칙은 다음과 같습니다 행의 애니메이션 그래서 예를 들면

와 모델

  1. 거래
  2. 거래 :

    - (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath { 
    
        if (editingStyle == UITableViewCellEditingStyleDelete) { 
         NSInteger row = [indexPath row]; 
    
         [yourModel removeObjectAtIndex:row]; // you need to update your model 
    
         [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; 
        } 
    } 
    

    지금의 제 생각에는 올바른 코드는 다음과 같을 수 있습니다 (나는 당신을 안내 할 몇 가지 코멘트를 썼다).

    - (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath { 
    
        if (editingStyle == UITableViewCellEditingStyleDelete) { 
         //Get the object to delete from the array. 
         identifyObject = [appDelegate.idArray objectAtIndex:indexPath.row]; 
         [appDelegate removeID:identifyObject]; // update model first 
    
         // now you can check model count and do what you want 
         if ([appDelegate.idArray count] == 0) // I think you mean appDelegate.idArray 
         { 
          // do what you want 
          // with [self.idTableView insertRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; 
         } 
    
         else 
         { 
          [self.idTableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; 
         } 
        } 
    } 
    

    희망이 있습니다.

2

"행 없음"경고에 셀을 사용하는 것과 동일한 접근 방식을 사용하고있었습니다.나를 위해

,이 일 :

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath { 

if (editingStyle == UITableViewCellEditingStyleDelete) { 

    [favs removeObjectAtIndex:indexPath.section]; 

    if ([favs count] == 0) { 
     [tableView reloadRowsAtIndexPaths:[[NSArray alloc]initWithObjects:indexPath, nil] withRowAnimation:UITableViewRowAnimationFade]; 
     [tableView setEditing:NO animated:YES]; 

     // Remove Edit bar button item 
     self.navigationItem.rightBarButtonItem = nil; 
    } 
    else { 
     // Animate the deletion from the table. 
     [tableView deleteRowsAtIndexPaths:[[NSArray alloc]initWithObjects:indexPath, nil] withRowAnimation:UITableViewRowAnimationFade]; 
    } 
} 

}

+0

고마워, 그것은 나를 위해 아름답게 일했다 ... –

관련 문제