2011-02-01 2 views
1

서브 클래 싱 한 UITableViewSource 있습니다. 그래서 같이 GetCell을 무시하고 내 자신의 서브 클래스 세포를 사용하고 있습니다 :UITableViewDelegate 문제 - RowSelected 잘못된 NSIndexPath 제공

public override UITableViewCell GetCell(UITableView tableView, NSIndexPath indexPath) 
{ 
    MarketItem item=_tableItems[indexPath.Section].Items[indexPath.Row]; 
    MarketCell cell=tableView.DequeueReusableCell(_cellIdentifier) as MarketCell; 

    if (cell==null) 
    { 
     cell=new MarketCell(UITableViewCellStyle.Subtitle,_cellIdentifier,item); 
    } 

    // decorate the cell 
    // ... 

    return cell; 
} 

이 작동하지만 난 내 UITableViewDelegate에서 이벤트를 얻을 때, 인덱스 경로 나에게 잘못된 세포 (AccessoryButtonTapped, WillSelectRow 등 같은 행사)를 가져옵니다.

섹션과 행 번호는 올바른 보이지만 나는

tableView.CellAt(indexPath) 

을 할 때 잘못된 세포를 얻을. (행 및 섹션 번호는 다시 올바른 본다.)

사항을 참고 :

  • 표는 지속적으로 업데이트되는 - 항목은 다음 표 있지만
  • 을 InvokeOnMainThread'd하는 다른 스레드에 도착을 아무것도 다시 주문하거나 내가 'WillSelectRow'를 얻을 때 나는 업데이트를 일시 정지하는 경우
  • 을 삭제, 그것은
  • 대부분의 흥미로운 (하지만 출하 가능한 솔루션을 도움이되지 않습니다 - 지속적으로 행과 섹션 만 추가, 업데이트됩니다) 내가 새 셀을 매번 만들면 DequeueReusableCell을 수행하는 것보다 올바르게 작동합니다.

내 자신의 멍청한 버그라고 생각할 수는 없지만 찾을 수는 없습니다. 어떤 도움이라도 가장 감사하게 받아 들일 것입니다! http://simon.nureality.ca/?p=91

기본적있는 UITableViewCell 하위 클래스하지 않는 대신 "MarketCellController"으로의 UIViewController 하위 클래스 :

+0

의 당신이 table.ReloadData() 테이블의 데이터가 업데이트 될 때마다 호출 있습니까? – Luke

+0

새 행이 추가 된 경우에만 - 기존 셀의 업데이트를 위해 ReloadRows()를 수행하고 있습니다. – vlad259

+0

셀 대기열과 관련있을 수 있습니다. 귀하의 MarketCell 생성자는 새로 생성 된 셀에 _cellIdentifier를 어떻게 할당합니까? – riha

답변

1

당신은에서 입증 된 바와 같이 다른 방법을 시도 할 수 있습니다. 이 사용자 정의 컨트롤러는 표준 UITableViewCell과 사용자 정의 항목을 유지하며 AddSubview()를 통해 사용자 정의 항목을 추가합니다.

필요한 각 셀에 대해 새 컨트롤러를 하나 만들고 사전에 저장하십시오.

트릭 : 셀에 고유 한 태그를 지정하면 연결된 컨트롤러를 사전에서 검색 할 수 있습니다.

빠른 예 :

Dictionary<int,MarketCellController> controllers = new Dictionary<int,MarketCellController>(); 

// ... 

public override UITableViewCell GetCell(UITableView tableView, NSIndexPath indexPath) { 
    UITableViewCell cell = tableView.DequeueReusableCell(_cellIdentifier); 
    MarketCellController cellController; 

    if (cell == null) { 
    cellController = new MarketCellController(); 
    cell = cellController.Cell; 
    controllers.Add(cell.Tag, cellController); 
    } else { 
    cellController = controllers[cell.Tag]; 
    } 

    // Decorate the cell (using Methods of your cellController) 
    // ... 

    return cell; 
} 

이 결국 서브 클래스 UITableViewCells와 큐 해제 문제를 회피 할 수있다.

편집 :

난 그냥 마음에 다른 뭔가를했다 : 당신은 당신 MarketCell 생성자에 항목을 assinging 것으로 보인다. 그러나 대기 행렬에있는 셀에는 이전 항목 세트가 있으므로 대기열에서 제거한 후 새 항목으로 재설정해야합니다.

생성자의 항목 매개 변수를 제거하십시오 (어쨌든 덮어 씁니다) 대신 공용 속성 (또는 설정자)을 만듭니다. 이를 사용하여 셀을 가져온 후에 올바른 항목을 할당합니다 (대기열에 추가되거나 새로 생성 된 경우와 관계없이).해야 할 일 :

MarketCell cell = tableView.DequeueReusableCell(_cellIdentifier) as MarketCell; 
if (cell == null) { 
    cell = new MarketCell(UITableViewCellStyle.Subtitle, _cellIdentifier); 
} 

// Assign the correct item 
cell.Item = item; 
// or (whatever you like more): 
// cell.SetItem(item); 

// Decorate the cell 
// ... 

return cell; 

동일한 방법으로 cellController를 사용할 수도 있습니다. 셀을 대기열에서 제거했는지 또는 새 셀로 가져 왔는지에 관계없이 항상 다른 셀과 다를 수있는 셀의 모든 항목을 재설정해야합니다.

BTW : 셀을 UITableViewCellStyle.Subtitle로 하드 코딩하면 생성자에서이를 생략하고 MarketCell 클래스에 하드 코딩 할 수 있습니다.

cellController 접근법의 가치는 다음과 같습니다. 사용자 정의 데이터 및 동작에서 UITableViewCell을 분리하여 멋진 분리 레이어를 얻습니다. 셀 컨트롤러는 테이블 셀처럼 작동 할 필요가 없습니다.)

+0

정말 재미있어 보여요. 감사합니다. 감사합니다! – vlad259

+0

나는 그것을 좋아하지만 자신의 세포를 추적하는 데 이점이 어디 있는지 확실하지 않습니까? (그게 내가해야 할 일이고 잘 작동합니다.) – vlad259

+0

제가 그것에 대해 더 많이 알게되면서, 나는 당신의 해결책을 점점 더 좋아합니다. 감사! – vlad259

0

이것은 Xamarin에서 여전히 문제가있는 것처럼 보입니다. @ vlad259에 의해 게시 된 링크는 불행하게도 오래 동안 사라졌습니다. 그리고이 '버그'가 오늘 저를 조금씩 괴롭 힙니다. 이유가 무엇인지 알지 못합니다. 원인을 추적하기 위해 UITableViewSource 구현을 고정 행 수를 반환하고 셀 레이블에 행 번호를 할당하는 방식으로 줄였습니다. ..

버그는 구체적으로 화면을로드하고 첫 번째 오프 스크린 셀로 스크롤합니다 (즉, 테이블이 10 개의 셀을 렌더링 할 수 있다면 스크롤하여 11 번째 화면이 나타남) RowSelected 이벤트에서 거의 임의의 Row 인덱스를 가져옵니다.

나는 이것에 대한 몇 가지 해결책을 발견했다. 이 상수를 반환 될지라도 -

솔루션은

이 버그는 내가 정의 행의 높이를 반환 GetHeightForRow를 오버라이드 (override) 한 경우 명시 보인다. 필요하지 않은 경우 ... 재정의하지 마십시오.

솔루션 B는

이는 버그 구체적 NSIndexPath 인수를 취하는 DequeueReusableCell (S) 내에 있음을 보인다.

사용

UITableView.DequeueReusableCell(NSString)

대신

UITableView.DequeueReusableCell(NSString, NSIndexPath)

관련 문제