2013-05-06 5 views
0

이미지를 네트워크에 액세스하는 멋진 기능을 구축하려고합니다. 웹에서 찾았다면이를 캐시 시스템에 저장합니다. 이미지가 이미 캐시에 저장된 경우이를 반환합니다. 이 함수는 getImageFromCache이라고하고 캐시에 있으면 이미지를 반환하고, 그렇지 않으면 네트워크로 이동하여 가져옵니다.UIImages NSURLs 및 스레드

코드는 다음과 같습니다

UIImageView* backgroundTiles = [[UIImageView alloc] initWithImage[self getImageFromCache:@"http://www.example.com/1.jpg"]]; 

을 지금, 나는 때문에 네트워크 트래픽으로 인해 큰 지연 시간의 스레드를 사용하여로 이동하고있다. 따라서 웹에서 결과를 얻기 전에 임시 이미지를 표시하는 이미지가 필요합니다.

내가 알고 싶은 것은이 함수 (getImageFromCache)에 의해 UIImageView에 추가되는 많은 이미지가 순차적으로 액세스되는 것을 어떻게 추적 할 수 있는지 알고 싶습니다. 이 질문에 직접 대답하지

-(UIImage*)getImageFromCache:(NSString*)forURL{ 

    __block NSError* error = nil; 
    __block NSData *imageData; 
    __block UIImage* tmpImage; 

    if(forURL==nil) return nil; 

    if(![self.imagesCache objectForKey:forURL]) 
    { 
     // Setting a temporary image until we start getting results 
     tmpImage = [UIImage imageNamed:@"noimage.png"]; 

     NSURL *imageURL = [NSURL URLWithString:forURL]; 
     dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^{ 
      imageData = [NSData dataWithContentsOfURL:imageURL options:NSDataReadingUncached error:&error]; 
      if(imageData) 
      { 
       NSLog(@"Thread fetching image URL:%@",imageURL); 
       dispatch_async(dispatch_get_main_queue(), ^{ 
        tmpImage = [UIImage imageWithData:imageData]; 
        if(tmpImage) 
        { 
         [imagesCache setObject:tmpImage forKey:forURL]; 
        } 
        else 
         // Couldn't build an image of this data, probably bad URL 
         [imagesCache setObject:[UIImage imageNamed:@"imageNotFound.png"] forKey:forURL]; 
        }); 
      } 
      else 
       // Couldn't build an image of this data, probably bad URL 
       [imagesCache setObject:[UIImage imageNamed:@"imageNotFound.png"] forKey:forURL]; 

     }); 

    } 
    else 
     return [imagesCache objectForKey:forURL]; 

    return tmpImage; 
} 
+0

실제 문제는 무엇입니까? – matt

+0

웹에서 돌아온 이미지를 관리하는 방법을 모르겠습니다. – Ted

+0

코드는 이미지를 사전에 표시하는 것을 보여줍니다. 그것은 그들을 관리하고 있습니다. 다시 나는 묻는다, 무엇이 문제인가? – matt

답변

1

,하지만 당신은 백그라운드 스레드에서 (비동기 적으로 일을 다운로드 GCD를 사용할 필요가 없다는 것을 알고있다 :

뭔가 그냥 작동하지 않습니다)? 그냥 NSURLConnection과 그 대리자 메서드를 사용하십시오. 모든 코드는 주 스레드에 있지만 실제 연결 및 다운로드는 백그라운드에서 발생합니다. 을하고있다 MyDownloader과 서브 클래스 MyImageDownloader에 대한 부분, 아래로

http://www.apeth.com/iOSBook/ch37.html#_http_requests

스크롤 :

은 (그리고 사실 나는 당신을 위해 모든 돌봐 클래스, MyDownloader를 작성했습니다 정확히 여기에서해야 할 일들이 있습니다. 또한 다운로드가 완료되면 알림을 사용하여 이미지를 필요로하는 테이블 뷰에 이미지 뷰를 포함하는 행을 다시로드하라는 메시지를 표시하는 다음 코드를 확인하십시오 방금 도착했습니다.)

0

백그라운드 스레드에서 다운로드가 완료되고 캐시에 이미지를 저장하면 NSNotificationCenter을 사용하여 알림을 게시하여 앱의 다른 부분에 캐시가 업데이트되었음을 ​​알리는 것이 좋습니다.

이것은 이미지 뷰를 관리하는 앱 중 어느 부분이 addObserverForName 메서드를 사용하는 알림에 관심이 있다고 가정합니다. 그런 알림을 받으면 캐시에서 이미지를 다시 검색하고 적절할 경우 이미지보기를 업데이트하려고 시도 할 수 있습니다.

이미지보기의 수에 따라 알림의 이미지 URL (예 : userInfo 사전)을 통과 한 다음 새로 고침 대신 새로 고쳐야하는 이미지보기를 결정할 수 있습니다 그들 모두.

나는 또한 dispatch_async 호출을 제거하는 것이 좋습니다 것이라고 덧붙여 야합니다. 캐시 객체에 동기화를 추가해야 할 수도 있지만 메인 스레드와 다운로드 스레드에서 안전하게 액세스 할 수 있도록 할 필요는 있지만, 그럴 필요는 없습니다.

1

처음부터 건물을 잘 만들었지 만 모든 작업을 저장하려면 교체가 필요합니다. SDWebImage 웹에서 오는 원격 이미지를 지원하는 라이브러리이며 모든 기능을 갖추고 있습니다. 임시 이미지, 비동기로드 , 캐싱 등 당신이 필요하다고 했어