본문 바로가기

Swift

fetchKeyAssetsInAssetCollection vs fetchAssetsInAssetCollection

모르면 몸이 고생한다더니 내가 딱 그짝이다.

근본없는 코딩의 목적지가 바로 이것이 아닌가 싶기도 하다.


내 아이폰의 Burst 앨범에는 수 백 개의 고속연사사진들이 있다.

이 고속연사사진을 가져오고 싶어서 열심히 구글링하고 짜집기 한 끝에 아래 코드 중 주석 //1. 에 해당하는 코드를 만들어내었다.

그런데 이 코드를 사용하면 매번 이상하게 최근 3개의 사진만 조회되는 것이다. 같은 날 많이 찍은 것이 있어도 최근 3개만 조회가 되는 것이었다.


이 원인을 메소드를 잘 못 써서 그랬다고는 전혀 생각치 못하고 PHFetchOptions을 줘야 한다고 생각했다.

처음에는 PHFetchOption의 사용법도 몰라서 또 며칠 헤매었다. 그러다가 sorting하는 법까지는 알아냈는데 predicate하는 법은 알아내지 못 했다. 문법적으로 오류는 없는데 실행시키면 selecter를 알 수 없다는 에러만 계속 날 뿐이었다.


오류가 계속 나길래 포기하는 심정에서 stackOverFlow 사이트를 검색하다가 애플에서 제공하는 Example app using Photos framework 링크를 발견하고 들어가보았더니..!! 무려 샘플 앱과 소스까지 만들어서 제공하는 것이었다.


이 앱 소스를 다운받아 확인하니 내가 짠 코드보다 훨씬 간단했다. 게다가 옵션도 사용하지 않았다. 그런데도 모든 사진을 잘 가져오는 것이었다. 미치고 팔짝 뛸 노릇이었다.


위 그림처럼 똑같은 코드(사실은 똑같아 보이는 코드 ㅡ,.ㅡ;;)인데 결과가 다르게 나왔다.


아무튼 이상한 것은 내가 짰던 코드와 애플이 제공하는 샘플 코드의 다른 점을 도저히 찾을 수 없었던 것이다. 결국은 아래 코드와 같이 새로 프로젝트를 만들어서 돌려봐도 결과가 다르길래 한 글자 한 글자 꼼꼼하게 확인해보았더니 웬걸!! 이 글 제목처럼 메소드 이름에서 아주 살짝 다른 부분이 있다는 것을 발견했다.


정말 허무하다!!


나중에 PHAsset 설명을 잘 읽다 보니 알게 된 것인데 PHAsset은 기본으로 모든 사진을 리턴한다고 적혀있었다. ㅋ


결론:

fetchKeyAssetsInAssetCollection - 설명은 애매모호하게 나오지만 Burst Album의 경우 최근 3개의 사진만 Fetch한다.

fetchAssetsInAssetCollection - 모든 사진을 Fetch한다.



import UIKit
import Photos

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        
        // 1. 구글링하여 짜집기한 코드
        let burstAlbum: PHFetchResult = PHAssetCollection.fetchAssetCollectionsWithType(.SmartAlbum, subtype: .SmartAlbumBursts, options: nil)
        let collection: PHAssetCollection = (burstAlbum.firstObject as! PHAssetCollection)
        let burstImages: PHFetchResult = PHAsset.fetchKeyAssetsInAssetCollection(collection, options: nil)!
        print("burstImages.count = \(burstImages.count)")
        
        // 2. 애플에서 제공하는 샘플 코드
        let smartAlbums: PHFetchResult = PHAssetCollection.fetchAssetCollectionsWithType(.SmartAlbum, subtype: .SmartAlbumBursts, options: nil)
        //PHCollection *collection = smartAlbums[0];
        let assetCollection: PHAssetCollection = (smartAlbums.firstObject as! PHAssetCollection)
        let assetsFetchResult: PHFetchResult = PHAsset.fetchAssetsInAssetCollection(assetCollection, options: nil)
        print("assetsFetchResult.count=\(assetsFetchResult.count)")
    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }
}


뭐 덕분에 FetchOptions, sortDescriptor, predicate에 대해서 좀 알게 되었으니 뭐 완전 헛짓거리는 아니었지만 꽤 먼 거리를 돌아왔다.