0

일부 제품을 표시하기 위해 UICollectionView을 사용하고 있습니다. 사용자 정의 UICollectionViewCell에는 사용자 정의 UIScrollView이 있으며 사용자가 빠른 미리보기를 수행 할 수있는 일부 이미지가 있습니다. UICollectionView가 왜 didSelectItemAtIndexPath를 호출하지 않고 스크롤합니까?

은 내가 아래 방법 관련 접촉을 오버라이드 (override)의 UICollectionViewCellUIScrollView에서 탭 제스처를 전달하려면 :

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    if (!self.dragging) { 
     NSLog(@"Began ==>"); 
     [self.nextResponder touchesBegan:touches withEvent:event]; 
    } 
    else { 
     [super touchesBegan:touches withEvent:event]; 
    } 
} 

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    if (!self.dragging) { 
     NSLog(@"Moved ==>"); 
     [self.nextResponder touchesMoved:touches withEvent:event]; 
    } 
    else { 
     [super touchesMoved:touches withEvent:event]; 
    } 

} 

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    if (!self.dragging) { 
     NSLog(@"Ended ==>"); 
     [self.nextResponder touchesEnded:touches withEvent:event]; 
    } 
    else { 
     [super touchesEnded:touches withEvent:event]; 
    } 
} 

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    if (!self.dragging) { 
     NSLog(@"Cancelled ==>"); 
     [self.nextResponder touchesCancelled:touches withEvent:event]; 
    } 
    else { 
     [super touchesCancelled:touches withEvent:event]; 
    } 
} 

는 때때로 어떤 경우에는 작동하지 않습니다. 예를 들어 UICollectionView이 처음로드 될 때 didSelectItemAtIndexPath 메서드를 호출 할 때 호출 할 수 있지만 일부 스크롤 또는 탭 후에 메서드가 더 이상 호출되지 않으면 UICollectionView을 다시로드하려고해도 여전히 작동하지 않습니다.

UICollectionViewCell의 터치 방법으로 메시지를 기록하려고 시도하면 & 이벤트가 전달됩니다. 그러나 이 UICollectionView 인 이유는 셀이 제스처를 받으면 호출 되었습니까?

조언을 주시면 감사하겠습니다.

업데이트 : 1. UICollectionViewCell이 nib 파일에서로드됩니다.

답변

0

실제로는 self.dragging의 이해 때문입니다. 탭 제스처를 전달하는 올바른 방법은 다음과 같습니다.

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    [self.nextResponder touchesBegan:touches withEvent:event]; 
} 

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    [self.nextResponder touchesMoved:touches withEvent:event]; 
} 

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    if (!self.dragging) { 
     [self.nextResponder touchesEnded:touches withEvent:event]; 
    } 
    else { 
     [super touchesEnded:touches withEvent:event]; 
    } 
} 

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    [self.nextResponder touchesCancelled:touches withEvent:event]; 
} 
0

특정 개체를 타겟팅하는 경우 nextResponder를 사용하는 것은 좋지 않습니다. 방금 목격 한대로 응답 체인이 변경 될 수 있으며 예상 한 개체를 항상 얻을 수있는 것은 아닙니다. 왜 이런 일이 일어나는지는 여러 가지 이유가있을 수 있지만 어쨌든이 상황에서보다 신뢰할 수있는 방법을 사용해야합니다. UIScrollView 이후

당신은 당신이이 일을 할 때 염두에 뷰 계층 구조를 유지하기 위해 필요 세포에 도달하기 위해 수퍼의 수퍼를 호출 할 수 있습니다 [self.superview touchesMoved:touched withEvent:event]; 당신이 당신의 superview에 이벤트를 직접 전달할 수 UICollectionViewCell의 하위 뷰입니다.

또한 사용자 상호 작용을 가로 채기 위해 터치를 사용하지 않는 것이 좋습니다. UIGestureRecognizers를 사용하는 것이 훨씬 더 일관성있는 기능을 제공 할 것을 권장합니다.

+0

나는'self.superview'를 사용하려고합니다. 그것은 또한 신뢰할 수 없습니다. 실제로 제스처가 셀로 전달됩니다. 그러나 didselect 메서드는 호출되지 않습니다. 아주 이상한. – chancyWu

1

항상 super 메소드를 호출해야합니다.

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event { 
    [super touchesBegan:touches withEvent:event]; 
    NSLog(@"Began ==>"); 
} 

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event { 
    [super touchesMoved:touches withEvent:event]; 
    NSLog(@"Moved ==>"); 
} 

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event { 
    [super touchesEnded:touches withEvent:event]; 
    NSLog(@"Ended ==>"); 
} 

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event { 
    [super touchesCancelled:touches withEvent:event]; 
    NSLog(@"Cancelled ==>"); 
} 
+0

고마워요. 내 말은, 내가 알았지 만, 너는 나를 확인하게 만들었고, 나는 약간의 스크롤을 한 후에 무작위로 나의 터치 핸들링을 죽인 'touchesCancelled' 슈퍼 콜을 놓치고 있었다. 아마도 터치가 반쯤 처리 된 상태 였을 것입니다. – Echelon