Сохранить изображение в папку с документами, используя Share Extension - PullRequest
0 голосов
/ 25 февраля 2019

Моя цель (помимо обучения написанию расширения приложения для iOS) - предоставить пользователю возможность делиться изображениями с помощью кнопки «Поделиться» из различных приложений, включая «Фотографии», и автоматически переименовывать их.Наконец, я хочу сохранить изображение в папке «документы» приложения для дальнейшего использования.

У меня возникли некоторые проблемы при попытке заставить работать фактическую часть didSelectPost, поскольку кажется, что в отличие от Objective-С примерами, которые я видел, операция loadItem возвращает NSURL вместо UIImage.При попытке скопировать NSUrl в папку с документами моих приложений я получаю сообщение об ошибке:

Ошибка домена = NSCocoaErrorDomain Code = 260 "Файл« IMG_0941.JPG »не может быть открыт, поскольку такого нетфайл."UserInfo = {NSFilePath = file: ///var/mobile/Media/PhotoData/OutgoingTemp/B79263E5-9512-4317-9C5D-817D7EBEFA9A/RenderedPhoto/IMG_0941.JPG, NSUnderlyingError = 0x283fr = NoSense = NoSense = код ошибки 0x283f890NOSфайл или каталог "}}

Это происходит, когда я нажимаю кнопку публикации фотографии в приложении" фотографии ", нажимаю на расширение и затем нажимаю кнопку" опубликовать ".

Я получаю одну и ту же ошибку, независимо от того, работает ли она на симуляторе или реальном устройстве.

Вот мой прогресс, достигнутый вместе:

    override func didSelectPost() {
        // This is called after the user selects Post. Do the upload of contentText and/or NSExtensionContext attachments.
        let inputItem = extensionContext?.inputItems.first as! NSExtensionItem
        let attachment = inputItem.attachments!.first!
        if attachment.hasItemConformingToTypeIdentifier(kUTTypeJPEG as String) {
            attachment.loadItem(forTypeIdentifier: kUTTypeJPEG as String, options: nil) { data, error in
                var image: UIImage?
                if let someUrl = data as? NSURL {
                    do {
                      // a ends up being nil in both of these cases
                      let a = NSData(contentsOfFile: someUrl.absoluteString!)
                      image = UIImage(data: a as! Data)
                      // let a = try Data(contentsOf: someUrl)
                      // image = UIImage(contentsOfFile: someUrl.absoluteString)
                    } catch {
                        print(error)
                    }
                } else if let someImage = data as? UIImage {
                    image = someImage
                }

                if let someImage = image {
                    guard let compressedImagePath = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first?.appendingPathComponent("theimage.jpg", isDirectory: false) else {
                        return
                    }

                    let compressedImageData = someImage.jpegData(compressionQuality: 1)
                    guard (try? compressedImageData?.write(to: compressedImagePath)) != nil else {
                        return
                    }
                } else {
                    print("Bad share data")
                }
            }
        }
        // Inform the host that we're done, so it un-blocks its UI. Note: Alternatively you could call super's -didSelectPost, which will similarly complete the extension context.
        self.extensionContext!.completeRequest(returningItems: [], completionHandler: nil)
    }

Обратите внимание, что я использую переменную imgкак NSURL.Я пытался преобразовать его в UIImage, но это вызывает исключение.

У меня есть еще кое-что, что я хотел бы сделать с изображением, например, прочитать его данные EXIF, но сейчас это то, чтоЯ имею.Любые предложения были бы хорошими, поскольку я действительно изо всех сил пытаюсь обернуть голову и изучить эту среду.

Подобные, но неудачные посты, которые я пробовал, обратите внимание, что они все Цель-C:

Проблема с расширением общего доступа iOS при обмене изображениями из библиотеки фотографий

Совместное использование изображения с расширением общего доступа в ios8

Как добавить приложение вдействие общего листа

[править] Соответствует макету одного из лучших ответов, но безуспешно.

Ответы [ 2 ]

0 голосов
/ 26 февраля 2019

Я просмотрел ваш код, и в нем есть какая-то ошибка.Я исправил это.Замените свой код на него

func share() {
    let inputItem = extensionContext!.inputItems.first! as! NSExtensionItem
    let attachment = inputItem.attachments!.first as! NSItemProvider
    if attachment.hasItemConformingToTypeIdentifier( kUTTypeImage as String) {
        attachment.loadItem(forTypeIdentifier: kUTTypeImage as String, options: [:]) { (data, error) in
            var image: UIImage?
            if let someURl = data as? URL {
                image = UIImage(contentsOfFile: someURl.path)
            }else if let someImage = data as? UIImage {
                image = someImage
            }


            if let someImage = image {
                guard let compressedImagePath = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first?.appendingPathComponent("shareImage.jpg", isDirectory: false) else {
                    return
                }

                let compressedImageData = UIImageJPEGRepresentation(someImage, 1)
                guard (try? compressedImageData?.write(to: compressedImagePath)) != nil else {
                    return
                }

            }else{
                print("bad share data")
            }
        }

    }
}
0 голосов
/ 25 февраля 2019
func getPhotofolder() -> String{
    let fileManager = FileManager.default
    let paths = (NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true)[0] as NSString).appendingPathComponent("hsafetyPhoto")
    if !fileManager.fileExists(atPath: paths){
        try! fileManager.createDirectory(atPath: paths, withIntermediateDirectories: true, attributes: nil)

    }else{
        print("Already dictionary created.")
    }

    return  paths
}



    func saveImageDocumentDirectory(photo : UIImage, photoUrl : String) -> Bool{

     let fileManager = FileManager.default

     let paths =  Utility.getPhotofolder().stringByAppendingPathComponent(pathComponent: photoUrl)
    print("image's path \(paths)")
    if !fileManager.fileExists(atPath: paths){
        print("file already exits \(paths)")
        let imageData = UIImageJPEGRepresentation(photo, 0.5)
        fileManager.createFile(atPath: paths as String, contents: imageData, attributes: nil)

         if !fileManager.fileExists(atPath: paths){
            return false
         }else{
            return true
        }

    }else{
        print(paths)
        let imageData = UIImageJPEGRepresentation(photo, 0.5)
        fileManager.createFile(atPath: paths as String, contents: imageData, attributes: nil)
        if !fileManager.fileExists(atPath: paths){
            return false
        }else{
            return true
        }

    }


}





func showimage(image_name : String) {

let documentsUrl = URL (fileURLWithPath: NSSearchPathForDirectoriesInDomains (.documentDirectory, .userDomainMask, true) [0])

let imgUrl = documentsUrl.appendingPathComponent (image_name)

FileManager.default.fileExists (atPath: imgUrl.path)) {
do
{
     let data = try Data(contentsOf:imgUrl)
     self.imageView.image = UIImage(data:data)

}
catch {
   print(error)
}

} else {

 self.imageView.image = UIImage(named:"default.jpg") //Display any default image 

}}

...