feat: add photo library permission checking
This commit is contained in:
parent
597fc3fa1a
commit
51c01066d3
|
@ -27,6 +27,10 @@
|
|||
"title": "Sign out",
|
||||
"message": "Are you sure you want to sign out?",
|
||||
"confirm": "Sign Out"
|
||||
},
|
||||
"save_photo_failure": {
|
||||
"title": "Save Photo Failure",
|
||||
"message": "Please enable photo libaray access permission to save photo."
|
||||
}
|
||||
},
|
||||
"controls": {
|
||||
|
@ -55,7 +59,8 @@
|
|||
"find_people": "Find people to follow",
|
||||
"manually_search": "Manually search instead",
|
||||
"skip": "Skip",
|
||||
"report_user": "Report %s"
|
||||
"report_user": "Report %s",
|
||||
"settings": "Settings"
|
||||
},
|
||||
"status": {
|
||||
"user_reblogged": "%s reblogged",
|
||||
|
@ -411,4 +416,4 @@
|
|||
"text_placeholder": "Type or paste additional comments"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -31,6 +31,12 @@ internal enum L10n {
|
|||
/// Publish Failure
|
||||
internal static let title = L10n.tr("Localizable", "Common.Alerts.PublishPostFailure.Title")
|
||||
}
|
||||
internal enum SavePhotoFailure {
|
||||
/// Please enable photo libaray access permission to save photo.
|
||||
internal static let message = L10n.tr("Localizable", "Common.Alerts.SavePhotoFailure.Message")
|
||||
/// Save Photo Failure
|
||||
internal static let title = L10n.tr("Localizable", "Common.Alerts.SavePhotoFailure.Title")
|
||||
}
|
||||
internal enum ServerError {
|
||||
/// Server Error
|
||||
internal static let title = L10n.tr("Localizable", "Common.Alerts.ServerError.Title")
|
||||
|
@ -94,6 +100,8 @@ internal enum L10n {
|
|||
internal static let savePhoto = L10n.tr("Localizable", "Common.Controls.Actions.SavePhoto")
|
||||
/// See More
|
||||
internal static let seeMore = L10n.tr("Localizable", "Common.Controls.Actions.SeeMore")
|
||||
/// Settings
|
||||
internal static let settings = L10n.tr("Localizable", "Common.Controls.Actions.Settings")
|
||||
/// Share
|
||||
internal static let share = L10n.tr("Localizable", "Common.Controls.Actions.Share")
|
||||
/// Share %@
|
||||
|
|
|
@ -171,8 +171,18 @@ extension StatusTableViewCellDelegate where Self: StatusProvider {
|
|||
guard let attachment = attachment, let url = URL(string: attachment.url) else { return nil }
|
||||
return self.context.photoLibraryService.saveImage(url: url)
|
||||
}
|
||||
.sink(receiveCompletion: { _ in
|
||||
// do nothing
|
||||
.switchToLatest()
|
||||
.sink(receiveCompletion: { [weak self] completion in
|
||||
guard let self = self else { return }
|
||||
switch completion {
|
||||
case .failure(let error):
|
||||
guard let error = error as? PhotoLibraryService.PhotoLibraryError,
|
||||
case .noPermission = error else { return }
|
||||
let alertController = SettingService.openSettingsAlertController(title: L10n.Common.Alerts.SavePhotoFailure.title, message: L10n.Common.Alerts.SavePhotoFailure.message)
|
||||
self.coordinator.present(scene: .alertController(alertController: alertController), from: self, transition: .alertController(animated: true, completion: nil))
|
||||
case .finished:
|
||||
break
|
||||
}
|
||||
}, receiveValue: { _ in
|
||||
// do nothing
|
||||
})
|
||||
|
|
|
@ -5,6 +5,8 @@
|
|||
"Common.Alerts.PublishPostFailure.Message" = "Failed to publish the post.
|
||||
Please check your internet connection.";
|
||||
"Common.Alerts.PublishPostFailure.Title" = "Publish Failure";
|
||||
"Common.Alerts.SavePhotoFailure.Message" = "Please enable photo libaray access permission to save photo.";
|
||||
"Common.Alerts.SavePhotoFailure.Title" = "Save Photo Failure";
|
||||
"Common.Alerts.ServerError.Title" = "Server Error";
|
||||
"Common.Alerts.SignOut.Confirm" = "Sign Out";
|
||||
"Common.Alerts.SignOut.Message" = "Are you sure you want to sign out?";
|
||||
|
@ -30,6 +32,7 @@ Please check your internet connection.";
|
|||
"Common.Controls.Actions.Save" = "Save";
|
||||
"Common.Controls.Actions.SavePhoto" = "Save photo";
|
||||
"Common.Controls.Actions.SeeMore" = "See More";
|
||||
"Common.Controls.Actions.Settings" = "Settings";
|
||||
"Common.Controls.Actions.Share" = "Share";
|
||||
"Common.Controls.Actions.ShareUser" = "Share %@";
|
||||
"Common.Controls.Actions.SignIn" = "Sign In";
|
||||
|
|
|
@ -208,8 +208,17 @@ extension MediaPreviewViewController: MediaPreviewImageViewControllerDelegate {
|
|||
switch viewController.viewModel.item {
|
||||
case .status(let meta):
|
||||
context.photoLibraryService.saveImage(url: meta.url)
|
||||
.sink { _ in
|
||||
// do nothing
|
||||
.sink { [weak self] completion in
|
||||
guard let self = self else { return }
|
||||
switch completion {
|
||||
case .failure(let error):
|
||||
guard let error = error as? PhotoLibraryService.PhotoLibraryError,
|
||||
case .noPermission = error else { return }
|
||||
let alertController = SettingService.openSettingsAlertController(title: L10n.Common.Alerts.SavePhotoFailure.title, message: L10n.Common.Alerts.SavePhotoFailure.message)
|
||||
self.coordinator.present(scene: .alertController(alertController: alertController), from: self, transition: .alertController(animated: true, completion: nil))
|
||||
case .finished:
|
||||
break
|
||||
}
|
||||
} receiveValue: { _ in
|
||||
// do nothing
|
||||
}
|
||||
|
|
|
@ -8,12 +8,21 @@
|
|||
import os.log
|
||||
import UIKit
|
||||
import Combine
|
||||
import Photos
|
||||
import AlamofireImage
|
||||
|
||||
final class PhotoLibraryService: NSObject {
|
||||
|
||||
}
|
||||
|
||||
extension PhotoLibraryService {
|
||||
|
||||
enum PhotoLibraryError: Error {
|
||||
case noPermission
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
extension PhotoLibraryService {
|
||||
|
||||
func saveImage(url: URL) -> AnyPublisher<UIImage, Error> {
|
||||
|
@ -21,6 +30,11 @@ extension PhotoLibraryService {
|
|||
let notificationFeedbackGenerator = UINotificationFeedbackGenerator()
|
||||
|
||||
return Future<UIImage, Error> { promise in
|
||||
guard PHPhotoLibrary.authorizationStatus(for: .addOnly) != .denied else {
|
||||
promise(.failure(PhotoLibraryError.noPermission))
|
||||
return
|
||||
}
|
||||
|
||||
ImageDownloader.default.download(URLRequest(url: url), completion: { [weak self] response in
|
||||
guard let self = self else { return }
|
||||
switch response.result {
|
||||
|
|
|
@ -171,3 +171,19 @@ final class SettingService {
|
|||
}
|
||||
|
||||
}
|
||||
|
||||
extension SettingService {
|
||||
|
||||
static func openSettingsAlertController(title: String, message: String) -> UIAlertController {
|
||||
let alertController = UIAlertController(title: title, message: message, preferredStyle: .alert)
|
||||
let settingAction = UIAlertAction(title: L10n.Common.Controls.Actions.settings, style: .default) { _ in
|
||||
guard let url = URL(string: UIApplication.openSettingsURLString) else { return }
|
||||
UIApplication.shared.open(url, options: [:], completionHandler: nil)
|
||||
}
|
||||
alertController.addAction(settingAction)
|
||||
let cancelAction = UIAlertAction(title: L10n.Common.Controls.Actions.cancel, style: .cancel, handler: nil)
|
||||
alertController.addAction(cancelAction)
|
||||
return alertController
|
||||
}
|
||||
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue