0

다음보기 컨트롤러를 푸시하기 전에 블록이 완료되지 않았습니다.블록 전에 완료되지 않았습니다.

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender { 
if ([[segue identifier] isEqualToString:@"ResultsView"]) 
{ 
    [self.spinner startAnimating]; 

    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ 

     NSMutableArray *results = [[NSMutableArray alloc] init]; 
     results = [self generateResults]; 

     dispatch_async(dispatch_get_main_queue(), ^{ 

      [self.spinner stopAnimating]; 

      ResultViewController *controller = [segue destinationViewController]; 
      controller.results = results; 

     }); 
    }); 
} 
} 

이는 generateResults 방법입니다 : 지연 또는 구조 조정 다음과 같은 방법에 대한 어떤 제안 내가 파견 한 후 동기화, 같은 문제를 사용하지 않는 경우, 또는

- (NSMutableArray *)generateResults 
{ 
ALAssetsLibrary *library = [[ALAssetsLibrary alloc] init]; 
__block NSMutableArray *matches = [[NSMutableArray alloc] init]; 

[library enumerateGroupsWithTypes:ALAssetsGroupAll 
         usingBlock:^(ALAssetsGroup *group, BOOL *stop) 
{ 
    if (group) { 
     [group setAssetsFilter:[ALAssetsFilter allPhotos]]; 
     [group enumerateAssetsUsingBlock:^(ALAsset *asset, NSUInteger index, BOOL *stop){ 

      if (asset) 
      { 
       //work done here. 
      } 
     }]; 
    } 
} failureBlock:^(NSError *error) { 
}]; 

return matches; 
} 

는 블록 생성 결과가 너무 늦게 완료되었습니다. 다음보기 컨트롤러가 이미 나타나서 0 개의 찾기를 표시합니다.

+0

변경 (제공 스토리 보드의 푸시보기를 사용하지 않음)와 기능 대체 - (무효) prepareForSegue : (UIStoryboardSegue *) SEGUE 보낸 사람 : (ID) 보낸 사람을. 다른 기능에 의해하지만 같은 것들을 않습니다. 그럼 블록은 일을 할 것입니다. – lee

답변

1

prepareForSegue은 단지 준비로 사용됩니다. 즉, 이 완료되면 segue는을 실행합니다. 따라서 Segue가 발생하기 전에 컨트롤러를 준비해야하는 경우이 작업을 비동기 블록에 넣을 수 없습니다. runloop에 관한 한 prepareForSegue은 즉시 완료합니다.

다음 컨트롤러가 prepareForSegue의 준비 코드에 의존하는 경우 dispatch_async을 사용하면 안됩니다. 대신 generateResults을 주 대기열에서 실행하거나 ResultViewController이 작업을 비동기로 보내고 결과에 따라 자체보기를 업데이트하도록하십시오.

+0

다음보기 컨트롤러가 필요합니다. 메인 큐에서 실행하면 블록은 다음 뷰 컨트롤러가 초기화 된 후에 종료됩니다. 다른 방법이 있습니까? – user3131312

0

해결 방법은 여기 있습니다. 파견을 사용할 필요가 없었습니다. 또는 group == nil 일 때 블록이 완료됩니다. 따라서 단순한 else 문장만으로도 충분합니다.

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender 
{ 
if ([[segue identifier] isEqualToString:@"ResultView"]) 
{ 
    ALAssetsLibrary *library = [[ALAssetsLibrary alloc] init]; 
    __block NSMutableArray *matches = [[NSMutableArray alloc] init]; 

    [library enumerateGroupsWithTypes:ALAssetsGroupAll 
          usingBlock:^(ALAssetsGroup *group, BOOL *stop) 
    { 
     if (group) { 
      [group setAssetsFilter:[ALAssetsFilter allPhotos]]; 
      [group enumerateAssetsUsingBlock:^(ALAsset *asset, NSUInteger index, BOOL *stop){ 

       if (asset) 
       { 

       } 
      }]; 
     } else { 

      ResultsViewController *resultsViewController = [segue destinationViewController]; 
      resultsViewController.results = matches; 
      [resultsViewController.collectionView reloadData]; 
     } 
    } failureBlock:^(NSError *error) { 
    }]; 
} 

} 스토리 보드에

관련 문제