99 lines
3.2 KiB
Swift
99 lines
3.2 KiB
Swift
//
|
|
// PhotosService.swift
|
|
// Swipe That Pic
|
|
//
|
|
// Created by Amine Bou on 27/07/2024.
|
|
//
|
|
|
|
import Foundation
|
|
import Photos
|
|
import UIKit
|
|
import SwiftData
|
|
import SwiftUI
|
|
|
|
class PhotosService: ObservableObject {
|
|
var notKept: PHFetchResult<PHAsset> = PHFetchResult()
|
|
@Published var one: PHAsset?
|
|
var modelContainer: ModelContainer
|
|
|
|
init(modelContainer: ModelContainer) {
|
|
self.modelContainer = modelContainer
|
|
}
|
|
|
|
var imageCachingManager = PHCachingImageManager()
|
|
|
|
@MainActor func fetchNotKeptPhotos() {
|
|
PHPhotoLibrary.requestAuthorization(for: .readWrite) { status in
|
|
switch status {
|
|
case .authorized:
|
|
self.fetchNotKeptPhotosAuthorized()
|
|
break;
|
|
@unknown default:
|
|
fatalError()
|
|
}
|
|
}
|
|
}
|
|
|
|
@MainActor func fetchNotKeptPhotosAuthorized() {
|
|
imageCachingManager.allowsCachingHighQualityImages = false
|
|
let fetchOptions = PHFetchOptions()
|
|
fetchOptions.includeHiddenAssets = false
|
|
do {
|
|
let items = try self.modelContainer.mainContext.fetch(FetchDescriptor<Item>())
|
|
if (items.count > 0) {
|
|
fetchOptions.predicate = NSPredicate(format: "NOT localIdentifier IN %@",
|
|
argumentArray: [items.map {$0.localIdentfier}])
|
|
}
|
|
} catch {
|
|
print("Can't get model")
|
|
}
|
|
fetchOptions.sortDescriptors = [
|
|
NSSortDescriptor(key: "creationDate", ascending: false)
|
|
]
|
|
DispatchQueue.main.async {
|
|
self.notKept = PHAsset.fetchAssets(with: .image, options: fetchOptions)
|
|
if (self.notKept.count > 0) {
|
|
self.one = self.notKept.object(at: Int.random(in: 0..<self.notKept.count))
|
|
} else {
|
|
self.one = nil
|
|
}
|
|
}
|
|
}
|
|
|
|
func fetchImage(
|
|
byLocalIdentifier localId: String,
|
|
targetSize: CGSize = PHImageManagerMaximumSize,
|
|
contentMode: PHImageContentMode = .default
|
|
) async throws -> UIImage? {
|
|
let results = PHAsset.fetchAssets(
|
|
withLocalIdentifiers: [localId],
|
|
options: nil
|
|
)
|
|
guard let asset = results.firstObject else {
|
|
fatalError("No asset")
|
|
}
|
|
let options = PHImageRequestOptions()
|
|
options.deliveryMode = .opportunistic
|
|
options.resizeMode = .fast
|
|
options.isNetworkAccessAllowed = true
|
|
options.isSynchronous = true
|
|
return try await withCheckedThrowingContinuation { [weak self] continuation in
|
|
/// Use the imageCachingManager to fetch the image
|
|
self?.imageCachingManager.requestImage(
|
|
for: asset,
|
|
targetSize: targetSize,
|
|
contentMode: contentMode,
|
|
options: options,
|
|
resultHandler: { image, info in
|
|
/// image is of type UIImage
|
|
if let error = info?[PHImageErrorKey] as? Error {
|
|
continuation.resume(throwing: error)
|
|
return
|
|
}
|
|
continuation.resume(returning: image)
|
|
}
|
|
)
|
|
}
|
|
}
|
|
}
|