如何在SwiftUI中位于Apple的Files App的文件夹中写入文件? [英] How can I write a file in a folder located at Apple's Files App in SwiftUI?

查看:68
本文介绍了如何在SwiftUI中位于Apple的Files App的文件夹中写入文件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我关注了Swift项目UsingFiles

但是我在SwiftUI项目的Files APP中找不到写入文件.SwiftUI中的代码有什么问题吗?为什么在Files APP中找不到写入文件?

解决方案

正如我已经在评论中发布的那样,您不能以编程方式将文件保存到APP捆绑包之外.您可以使用 UIDocumentInteractionController 并要求用户选择应该将文件写入的位置.

因此,如果您使用的是SwiftUI,这将比常规的Storyboard方法稍微复杂一点,如您在此帖子中所见,因为您需要为 UIDocumentInteractionController 实现 UIViewControllerRepresentable :


  struct DocumentInteractionController:UIViewControllerRepresentable {fileprivate var isExportingDocument:绑定< Bool>fileprivate let viewController = UIViewController()fileprivate让documentInteractionController:UIDocumentInteractionControllerinit(_ isExportingDocument:Binding< Bool>,URL:URL){self.isExportingDocument = isExportingDocumentdocumentInteractionController = .init(url:url)}func makeUIViewController(上下文:UIViewControllerRepresentableContext< DocumentInteractionController>)->UIViewController {viewController}func updateUIViewController(_控制器:UIViewController,上下文:UIViewControllerRepresentableContext< DocumentInteractionController>){如果是isExportingDocument.wrappedValue&&documentInteractionController.delegate == nil {documentInteractionController.uti = documentInteractionController.url?.typeIdentifier ??"public.data,public.content"documentInteractionController.name = documentInteractionController.url?.localizedNamedocumentInteractionController.presentOptionsMenu(来自:controller.view.frame,在:controller.view,动画:true)documentInteractionController.delegate = context.coordinatordocumentInteractionController.presentPreview(动画:true)}}func makeCoordinator()->协调员{.init(self)}} 


及其协调人:

 类协调器:NSObject,UIDocumentInteractionControllerDelegate {让documentInteractionController:DocumentInteractionControllerinit(_控制器:DocumentInteractionController){documentInteractionController =控制器}func documentInteractionControllerViewControllerForPreview(_ controller:UIDocumentInteractionController)->UIViewController {documentInteractionController.viewController}func documentInteractionControllerDidDismissOptionsMenu(_控制器:UIDocumentInteractionController){controller.delegate =零documentInteractionController.isExportingDocument.wrappedValue = false}} 


现在,您可以创建DocumentInteraction视图及其预览:

  struct DocumentInteraction:查看{@State私有var isExportingDocument = falsevar body:some View {VStack {Button(导出文档"){self.isExportingDocument = true}.background(DocumentInteractionController($ isExportingDocument,url:Bundle.main.url(forResource:"sample",withExtension:"pdf")!))}}}struct DocumentInteraction_Previews:PreviewProvider {静态var预览:一些视图{DocumentInteraction()}} 


您还将需要那些帮助者:

 扩展URL {var typeIdentifier:字符串?{(尝试?resourceValues(forKeys:[.typeIdentifierKey]))?. typeIdentifier}var localizedName:字符串?{(尝试?resourceValues(forKeys:[.localizedNameKey]))?. localizedName}} 


示例项目

I followed the Swift project UsingFiles github and its video to write files in my SwiftUI project. The project UsingFiles can write files to Files APP and then the writing files can be seen in the Files APP. But I followed the code as following, the files cannot be seen in Files APP.

let file = "\(UUID().uuidString).txt"
let contents = "Some text..."

let dir = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first!
let fileURL = dir.appendingPathComponent(file)

do {
    try contents.write(to: fileURL, atomically: false, encoding: .utf8)
}
catch {
    print("Error: \(error)")
}

The UsingFiles writing files is file:///Users/fmac/Library/Developer/CoreSimulator/Devices/11111111-881E-488A-9571-E61B83EB6062/data/Containers/Data/Application/11111111-AF89-4B15-B3B5-E13A63A19F8D/Documents/E018F056-83EA-4D70-87C4-16F755AA404A.txt.

My writing files is file:///Users/fmac/Library/Developer/CoreSimulator/Devices/11111111-881E-488A-9571-E61B83EB6062/data/Containers/Data/Application/11111111-B191-4ACD-98B1-004E619C2EC7/Documents/C9E0F52E-040F-4647-94A3-88E0DA171AB5.txt

I can find the writing files of UsingFiles in the directory UsingFiles as following:

But I cannot find the writing file in Files APP in my SwiftUI project. Is there something wrong of the code in SwiftUI? Why I cannot find the writing file in Files APP?

解决方案

As I have already posted in comments you can NOT programmatically save a file out of your APP Bundle. You can use a UIDocumentInteractionController and ask the user to choose the location where the file is supposed to be written.

So if you are working with SwiftUI this gets a bit more complicated than the regular Storyboard approach as you can see in this post because you need to implement UIViewControllerRepresentable for UIDocumentInteractionController:


struct DocumentInteractionController: UIViewControllerRepresentable {

    fileprivate var isExportingDocument: Binding<Bool>
    fileprivate let viewController = UIViewController()
    fileprivate let documentInteractionController: UIDocumentInteractionController

    init(_ isExportingDocument: Binding<Bool>, url: URL) {
        self.isExportingDocument = isExportingDocument
        documentInteractionController = .init(url: url)
    }

    func makeUIViewController(context: UIViewControllerRepresentableContext<DocumentInteractionController>) -> UIViewController { viewController }

    func updateUIViewController(_ controller: UIViewController, context: UIViewControllerRepresentableContext<DocumentInteractionController>) {
        if isExportingDocument.wrappedValue && documentInteractionController.delegate == nil {
            documentInteractionController.uti = documentInteractionController.url?.typeIdentifier ?? "public.data, public.content"
            documentInteractionController.name = documentInteractionController.url?.localizedName
            documentInteractionController.presentOptionsMenu(from: controller.view.frame, in: controller.view, animated: true)
            documentInteractionController.delegate = context.coordinator
            documentInteractionController.presentPreview(animated: true)
        }
    }

    func makeCoordinator() -> Coordintor { .init(self) }
}


And its Coordinator:

class Coordintor: NSObject, UIDocumentInteractionControllerDelegate {
    let documentInteractionController: DocumentInteractionController
    init(_ controller: DocumentInteractionController) {
        documentInteractionController = controller
    }
    func documentInteractionControllerViewControllerForPreview(_ controller: UIDocumentInteractionController) -> UIViewController { documentInteractionController.viewController }

    func documentInteractionControllerDidDismissOptionsMenu(_ controller: UIDocumentInteractionController) {
        controller.delegate = nil
        documentInteractionController.isExportingDocument.wrappedValue = false
    }
}


Now you can create your DocumentInteraction View and its previews:

struct DocumentInteraction: View {
    @State private var isExportingDocument = false
    var body: some View {
        VStack {
            Button("Export Document") { self.isExportingDocument = true }
            .background(DocumentInteractionController($isExportingDocument,
                url: Bundle.main.url(forResource: "sample", withExtension: "pdf")!))
        }
    }
}

struct DocumentInteraction_Previews: PreviewProvider {
    static var previews: some View { DocumentInteraction() }
}


You will need those helpers as well:

extension URL {
    var typeIdentifier: String? { (try? resourceValues(forKeys: [.typeIdentifierKey]))?.typeIdentifier }
    var localizedName: String? { (try? resourceValues(forKeys: [.localizedNameKey]))?.localizedName }
}


Sample project

这篇关于如何在SwiftUI中位于Apple的Files App的文件夹中写入文件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆