Skip to content

Commit

Permalink
Migrating to swift3
Browse files Browse the repository at this point in the history
  • Loading branch information
zhangao0086 committed Sep 18, 2016
1 parent 5575c4b commit 1ae6280
Show file tree
Hide file tree
Showing 21 changed files with 768 additions and 743 deletions.
396 changes: 196 additions & 200 deletions DKCamera/DKCamera.swift

Large diffs are not rendered by default.

94 changes: 47 additions & 47 deletions DKImageManager/DKImageManager.swift
Original file line number Diff line number Diff line change
Expand Up @@ -8,28 +8,28 @@

import Photos

public class DKBaseManager: NSObject {
open class DKBaseManager: NSObject {

private let observers = NSHashTable.weakObjectsHashTable()
private let observers = NSHashTable<AnyObject>.weakObjects()

public func addObserver(object: AnyObject) {
self.observers.addObject(object)
open func addObserver(_ object: AnyObject) {
self.observers.add(object)
}

public func removeObserver(object: AnyObject) {
self.observers.removeObject(object)
open func removeObserver(_ object: AnyObject) {
self.observers.remove(object)
}

public func notifyObserversWithSelector(selector: Selector, object: AnyObject?) {
open func notifyObserversWithSelector(_ selector: Selector, object: AnyObject?) {
self.notifyObserversWithSelector(selector, object: object, objectTwo: nil)
}

public func notifyObserversWithSelector(selector: Selector, object: AnyObject?, objectTwo: AnyObject?) {
open func notifyObserversWithSelector(_ selector: Selector, object: AnyObject?, objectTwo: AnyObject?) {
if self.observers.count > 0 {
dispatch_async(dispatch_get_main_queue(), { () -> Void in
for observer in self.observers.objectEnumerator() {
if observer.respondsToSelector(selector) {
observer.performSelector(selector, withObject: object, withObject: objectTwo)
DispatchQueue.main.async(execute: { () -> Void in
for observer in self.observers.allObjects {
if observer.responds(to: selector) {
_ = observer.perform(selector, with: object, with: objectTwo)
}
}
})
Expand All @@ -44,38 +44,38 @@ public func getImageManager() -> DKImageManager {

public class DKImageManager: DKBaseManager {

public class func checkPhotoPermission(handler: (granted: Bool) -> Void) {
public class func checkPhotoPermission(_ handler: @escaping (_ granted: Bool) -> Void) {
func hasPhotoPermission() -> Bool {
return PHPhotoLibrary.authorizationStatus() == .Authorized
return PHPhotoLibrary.authorizationStatus() == .authorized
}

func needsToRequestPhotoPermission() -> Bool {
return PHPhotoLibrary.authorizationStatus() == .NotDetermined
return PHPhotoLibrary.authorizationStatus() == .notDetermined
}

hasPhotoPermission() ? handler(granted: true) : (needsToRequestPhotoPermission() ?
hasPhotoPermission() ? handler(true) : (needsToRequestPhotoPermission() ?
PHPhotoLibrary.requestAuthorization({ status in
dispatch_async(dispatch_get_main_queue(), { () in
hasPhotoPermission() ? handler(granted: true) : handler(granted: false)
DispatchQueue.main.async(execute: { () in
hasPhotoPermission() ? handler(true) : handler(false)
})
}) : handler(granted: false))
}) : handler(false))
}

static let sharedInstance = DKImageManager()

private let manager = PHCachingImageManager.defaultManager()
private let manager = PHCachingImageManager.default()

private lazy var defaultImageRequestOptions: PHImageRequestOptions = {
let options = PHImageRequestOptions()
options.deliveryMode = .HighQualityFormat
options.resizeMode = .Exact
options.deliveryMode = .highQualityFormat
options.resizeMode = .exact

return options
}()

private lazy var defaultVideoRequestOptions: PHVideoRequestOptions = {
let options = PHVideoRequestOptions()
options.deliveryMode = .MediumQualityFormat
options.deliveryMode = .mediumQualityFormat

return options
}()
Expand All @@ -88,66 +88,66 @@ public class DKImageManager: DKBaseManager {
self.groupDataManager.invalidate()
}

public func fetchImageForAsset(asset: DKAsset, size: CGSize, completeBlock: (image: UIImage?, info: [NSObject : AnyObject]?) -> Void) {
public func fetchImageForAsset(_ asset: DKAsset, size: CGSize, completeBlock: @escaping (_ image: UIImage?, _ info: [AnyHashable: Any]?) -> Void) {
self.fetchImageForAsset(asset, size: size, options: nil, completeBlock: completeBlock)
}

public func fetchImageForAsset(asset: DKAsset, size: CGSize, contentMode: PHImageContentMode, completeBlock: (image: UIImage?, info: [NSObject : AnyObject]?) -> Void) {
public func fetchImageForAsset(_ asset: DKAsset, size: CGSize, contentMode: PHImageContentMode, completeBlock: @escaping (_ image: UIImage?, _ info: [AnyHashable: Any]?) -> Void) {
self.fetchImageForAsset(asset, size: size, options: nil, contentMode: contentMode, completeBlock: completeBlock)
}

public func fetchImageForAsset(asset: DKAsset, size: CGSize, options: PHImageRequestOptions?, completeBlock: (image: UIImage?, info: [NSObject : AnyObject]?) -> Void) {
self.fetchImageForAsset(asset, size: size, options: options, contentMode: .AspectFill, completeBlock: completeBlock)
public func fetchImageForAsset(_ asset: DKAsset, size: CGSize, options: PHImageRequestOptions?, completeBlock: @escaping (_ image: UIImage?, _ info: [AnyHashable: Any]?) -> Void) {
self.fetchImageForAsset(asset, size: size, options: options, contentMode: .aspectFill, completeBlock: completeBlock)
}

public func fetchImageForAsset(asset: DKAsset, size: CGSize, options: PHImageRequestOptions?, contentMode: PHImageContentMode,
completeBlock: (image: UIImage?, info: [NSObject : AnyObject]?) -> Void) {
public func fetchImageForAsset(_ asset: DKAsset, size: CGSize, options: PHImageRequestOptions?, contentMode: PHImageContentMode,
completeBlock: @escaping (_ image: UIImage?, _ info: [AnyHashable: Any]?) -> Void) {
let options = (options ?? self.defaultImageRequestOptions).copy() as! PHImageRequestOptions
self.manager.requestImageForAsset(asset.originalAsset!,
self.manager.requestImage(for: asset.originalAsset!,
targetSize: size,
contentMode: contentMode,
options: options,
resultHandler: { image, info in
if let isInCloud = info?[PHImageResultIsInCloudKey]?.boolValue
where image == nil && isInCloud && self.autoDownloadWhenAssetIsInCloud {
if let isInCloud = (info?[PHImageResultIsInCloudKey] as AnyObject).boolValue
, image == nil && isInCloud && self.autoDownloadWhenAssetIsInCloud {
// var requestCloudOptions = (options ?? self.defaultImageRequestOptions).copy() as! PHImageRequestOptions
// requestCloudOptions.networkAccessAllowed = true
options.networkAccessAllowed = true
options.isNetworkAccessAllowed = true
self.fetchImageForAsset(asset, size: size, options: options, contentMode: contentMode, completeBlock: completeBlock)
} else {
completeBlock(image: image, info: info)
completeBlock(image, info)
}
})
}

public func fetchImageDataForAsset(asset: DKAsset, options: PHImageRequestOptions?, completeBlock: (data: NSData?, info: [NSObject : AnyObject]?) -> Void) {
self.manager.requestImageDataForAsset(asset.originalAsset!,
public func fetchImageDataForAsset(_ asset: DKAsset, options: PHImageRequestOptions?, completeBlock: @escaping (_ data: Data?, _ info: [AnyHashable: Any]?) -> Void) {
self.manager.requestImageData(for: asset.originalAsset!,
options: options ?? self.defaultImageRequestOptions) { (data, dataUTI, orientation, info) in
if let isInCloud = info?[PHImageResultIsInCloudKey]?.boolValue
where data == nil && isInCloud && self.autoDownloadWhenAssetIsInCloud {
if let isInCloud = (info?[PHImageResultIsInCloudKey] as AnyObject).boolValue
, data == nil && isInCloud && self.autoDownloadWhenAssetIsInCloud {
let requestCloudOptions = (options ?? self.defaultImageRequestOptions).copy() as! PHImageRequestOptions
requestCloudOptions.networkAccessAllowed = true
requestCloudOptions.isNetworkAccessAllowed = true
self.fetchImageDataForAsset(asset, options: requestCloudOptions, completeBlock: completeBlock)
} else {
completeBlock(data: data, info: info)
completeBlock(data, info)
}
}
}

public func fetchAVAsset(asset: DKAsset, completeBlock: (avAsset: AVAsset?, info: [NSObject : AnyObject]?) -> Void) {
public func fetchAVAsset(_ asset: DKAsset, completeBlock: @escaping (_ avAsset: AVAsset?, _ info: [AnyHashable: Any]?) -> Void) {
self.fetchAVAsset(asset, options: nil, completeBlock: completeBlock)
}

public func fetchAVAsset(asset: DKAsset, options: PHVideoRequestOptions?, completeBlock: (avAsset: AVAsset?, info: [NSObject : AnyObject]?) -> Void) {
self.manager.requestAVAssetForVideo(asset.originalAsset!,
public func fetchAVAsset(_ asset: DKAsset, options: PHVideoRequestOptions?, completeBlock: @escaping (_ avAsset: AVAsset?, _ info: [AnyHashable: Any]?) -> Void) {
self.manager.requestAVAsset(forVideo: asset.originalAsset!,
options: options ?? self.defaultVideoRequestOptions) { avAsset, audioMix, info in
if let isInCloud = info?[PHImageResultIsInCloudKey]?.boolValue
where avAsset == nil && isInCloud && self.autoDownloadWhenAssetIsInCloud {
if let isInCloud = (info?[PHImageResultIsInCloudKey] as AnyObject).boolValue
, avAsset == nil && isInCloud && self.autoDownloadWhenAssetIsInCloud {
let requestCloudOptions = (options ?? self.defaultVideoRequestOptions).copy() as! PHVideoRequestOptions
requestCloudOptions.networkAccessAllowed = true
requestCloudOptions.isNetworkAccessAllowed = true
self.fetchAVAsset(asset, options: requestCloudOptions, completeBlock: completeBlock)
} else {
completeBlock(avAsset: avAsset, info: info)
completeBlock(avAsset, info)
}
}
}
Expand Down
84 changes: 41 additions & 43 deletions DKImageManager/Data/DKGroupDataManager.swift
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,10 @@ import Photos
@objc
protocol DKGroupDataManagerObserver {

optional func groupDidUpdate(groupId: String)
optional func groupDidRemove(groupId: String)
optional func group(groupId: String, didRemoveAssets assets: [DKAsset])
optional func group(groupId: String, didInsertAssets assets: [DKAsset])
@objc optional func groupDidUpdate(_ groupId: String)
@objc optional func groupDidRemove(_ groupId: String)
@objc optional func group(_ groupId: String, didRemoveAssets assets: [DKAsset])
@objc optional func group(_ groupId: String, didInsertAssets assets: [DKAsset])
}

public class DKGroupDataManager: DKBaseManager, PHPhotoLibraryChangeObserver {
Expand All @@ -27,7 +27,7 @@ public class DKGroupDataManager: DKBaseManager, PHPhotoLibraryChangeObserver {
public var showsEmptyAlbums: Bool = true

deinit {
PHPhotoLibrary.sharedPhotoLibrary().unregisterChangeObserver(self)
PHPhotoLibrary.shared().unregisterChangeObserver(self)
}

public func invalidate() {
Expand All @@ -36,113 +36,111 @@ public class DKGroupDataManager: DKBaseManager, PHPhotoLibraryChangeObserver {
self.groups?.removeAll()
self.groups = nil

PHPhotoLibrary.sharedPhotoLibrary().unregisterChangeObserver(self)
PHPhotoLibrary.shared().unregisterChangeObserver(self)
}

public func fetchGroups(completeBlock: (groups: [String]?, error: NSError?) -> Void) {
public func fetchGroups(_ completeBlock: (_ groups: [String]?, _ error: NSError?) -> Void) {
if let assetGroupTypes = self.assetGroupTypes {
if self.groups != nil {
completeBlock(groups: self.groupIds, error: nil)
completeBlock(self.groupIds, nil)
return
}

var groups: [String : DKAssetGroup] = [:]
var groupIds: [String] = []

for (_, groupType) in assetGroupTypes.enumerate() {
let fetchResult = PHAssetCollection.fetchAssetCollectionsWithType(self.collectionTypeForSubtype(groupType),
for (_, groupType) in assetGroupTypes.enumerated() {
let fetchResult = PHAssetCollection.fetchAssetCollections(with: self.collectionTypeForSubtype(groupType),
subtype: groupType,
options: nil)
fetchResult.enumerateObjectsUsingBlock { object, index, stop in
if let collection = object as? PHAssetCollection {
let assetGroup = DKAssetGroup()
assetGroup.groupId = collection.localIdentifier
self.updateGroup(assetGroup, collection: collection)
if self.showsEmptyAlbums || assetGroup.totalCount > 0 {
groups[assetGroup.groupId] = assetGroup
groupIds.append(assetGroup.groupId)
}
}
}
fetchResult.enumerateObjects({ (collection, idnex, stop) in
let assetGroup = DKAssetGroup()
assetGroup.groupId = collection.localIdentifier
self.updateGroup(assetGroup, collection: collection)
if self.showsEmptyAlbums || assetGroup.totalCount > 0 {
groups[assetGroup.groupId] = assetGroup
groupIds.append(assetGroup.groupId)
}
})
}
self.groups = groups
self.groupIds = groupIds

PHPhotoLibrary.sharedPhotoLibrary().registerChangeObserver(self)
completeBlock(groups: groupIds, error: nil)
PHPhotoLibrary.shared().register(self)
completeBlock(groupIds, nil)
}
}

public func fetchGroupWithGroupId(groupId: String) -> DKAssetGroup {
public func fetchGroupWithGroupId(_ groupId: String) -> DKAssetGroup {
return self.groups![groupId]!
}

public func fetchGroupThumbnailForGroup(groupId: String, size: CGSize, options: PHImageRequestOptions, completeBlock: (image: UIImage?, info: [NSObject : AnyObject]?) -> Void) {
public func fetchGroupThumbnailForGroup(_ groupId: String, size: CGSize, options: PHImageRequestOptions, completeBlock: @escaping (_ image: UIImage?, _ info: [AnyHashable: Any]?) -> Void) {
let group = self.fetchGroupWithGroupId(groupId)
if group.fetchResult.count == 0 {
completeBlock(image: nil, info: nil)
completeBlock(nil, nil)
return
}

let latestAsset = DKAsset(originalAsset:group.fetchResult.firstObject as! PHAsset)
let latestAsset = DKAsset(originalAsset:group.fetchResult.firstObject!)
latestAsset.fetchImageWithSize(size, options: options, completeBlock: completeBlock)
}

public func fetchAssetWithGroup(group: DKAssetGroup, index: Int) -> DKAsset {
let asset = DKAsset(originalAsset:group.fetchResult[index] as! PHAsset)
public func fetchAssetWithGroup(_ group: DKAssetGroup, index: Int) -> DKAsset {
let asset = DKAsset(originalAsset:group.fetchResult[index])
return asset
}

// MARK: - Private methods

private func collectionTypeForSubtype(subtype: PHAssetCollectionSubtype) -> PHAssetCollectionType {
return subtype.rawValue < PHAssetCollectionSubtype.SmartAlbumGeneric.rawValue ? .Album : .SmartAlbum
private func collectionTypeForSubtype(_ subtype: PHAssetCollectionSubtype) -> PHAssetCollectionType {
return subtype.rawValue < PHAssetCollectionSubtype.smartAlbumGeneric.rawValue ? .album : .smartAlbum
}

private func updateGroup(group: DKAssetGroup, collection: PHAssetCollection) {
private func updateGroup(_ group: DKAssetGroup, collection: PHAssetCollection) {
group.groupName = collection.localizedTitle
self.updateGroup(group, fetchResult: PHAsset.fetchAssetsInAssetCollection(collection, options: self.assetFetchOptions))
self.updateGroup(group, fetchResult: PHAsset.fetchAssets(in: collection, options: self.assetFetchOptions))
group.originalCollection = collection
}

private func updateGroup(group: DKAssetGroup, fetchResult: PHFetchResult) {
private func updateGroup(_ group: DKAssetGroup, fetchResult: PHFetchResult<PHAsset>) {
group.fetchResult = fetchResult
group.totalCount = group.fetchResult.count
}

// MARK: - PHPhotoLibraryChangeObserver methods

public func photoLibraryDidChange(changeInstance: PHChange) {
public func photoLibraryDidChange(_ changeInstance: PHChange) {
for group in self.groups!.values {
if let changeDetails = changeInstance.changeDetailsForObject(group.originalCollection) {
if let changeDetails = changeInstance.changeDetails(for: group.originalCollection) {
if changeDetails.objectWasDeleted {
self.groups![group.groupId] = nil
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.groupDidRemove(_:)), object: group.groupId)
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.groupDidRemove(_:)), object: group.groupId as AnyObject?)
continue
}

if let objectAfterChanges = changeDetails.objectAfterChanges as? PHAssetCollection {
self.updateGroup(self.groups![group.groupId]!, collection: objectAfterChanges)
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.groupDidUpdate(_:)), object: group.groupId)
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.groupDidUpdate(_:)), object: group.groupId as AnyObject?)
}
}

if let changeDetails = changeInstance.changeDetailsForFetchResult(group.fetchResult) {
if let changeDetails = changeInstance.changeDetails(for: group.fetchResult) {
if let removedIndexes = changeDetails.removedIndexes {
var removedAssets = [DKAsset]()
removedIndexes.enumerateIndexesUsingBlock({ index, stop in
(removedIndexes as NSIndexSet).enumerate({ index, stop in
removedAssets.append(self.fetchAssetWithGroup(group, index: index))
})
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.group(_:didRemoveAssets:)), object: group.groupId, objectTwo: removedAssets)
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.group(_:didRemoveAssets:)), object: group.groupId as AnyObject?, objectTwo: removedAssets as AnyObject?)
}
self.updateGroup(group, fetchResult: changeDetails.fetchResultAfterChanges)

if changeDetails.insertedObjects.count > 0 {
var insertedAssets = [DKAsset]()
for insertedAsset in changeDetails.insertedObjects {
insertedAssets.append(DKAsset(originalAsset: insertedAsset as! PHAsset))
insertedAssets.append(DKAsset(originalAsset: insertedAsset))
}
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.group(_:didInsertAssets:)), object: group.groupId, objectTwo: insertedAssets)
self.notifyObserversWithSelector(#selector(DKGroupDataManagerObserver.group(_:didInsertAssets:)), object: group.groupId as AnyObject?, objectTwo: insertedAssets as AnyObject?)
}
}
}
Expand Down
Loading

0 comments on commit 1ae6280

Please sign in to comment.