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?
This answer is entirely based on the earlier answer by lilunxp. If you like my answer please also like that answer.
I think the accepted answer is an overkill for what the OP wants. My understanding is that the OP simply wants to be able to write a file from the app, and have that file be visible and accessible from within Apple's Files app. That is very easy to do.
The all important thing is to do exactly what the answer from lilunxp says to do: "Try add 'Application supports iTunes file sharing' and 'Supports opening documents in place' to 'info.plist'. And change them value to true". That seems crystal clear, but just in case, here's a screenshot from Xcode 15.2 that shows how: just add the bottom two lines.
The OP already has the right code, but let me repeat it here and embellish a little by also creating subdirectories that the user can browse from Apple's Files app. This is the entire code needed:
import SwiftUI
struct ContentView: View {
var body: some View {
VStack {
Button("Make files user can access outside this app") {
makeFilesThatUserCanAccessOutsideThisApp()
}
}
.padding()
}
}
func makeFilesThatUserCanAccessOutsideThisApp() {
guard let docFolder = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first else {
fatalError()
}
let contents = "Some text..."
let mySOFileNameA = "MySOFileA.txt"
let mySOFileNameB = "MySOFileB.txt"
let mySOFolderUrl = docFolder.appendingPathComponent("MySOFolder")
do {
// write one file at the top level:
try contents.write(to: docFolder.appendingPathComponent(mySOFileNameA), atomically: true, encoding: .utf8)
// write two files into the subdirectory (after first creating the subdirectory if necessary):
try FileManager.default.createDirectory(at: mySOFolderUrl, withIntermediateDirectories: true, attributes: nil)
try contents.write(to: mySOFolderUrl.appendingPathComponent(mySOFileNameA), atomically: true, encoding: .utf8)
try contents.write(to: mySOFolderUrl.appendingPathComponent(mySOFileNameB), atomically: true, encoding: .utf8)
}
catch {
fatalError(error.localizedDescription)
}
}
Now the rest is just a matter of opening Apple's Files app, then selecting Browse > On My iPhone. This is what it looks like in iOS 17.3:
Both views are from Apple's Files app. The left view shows a "folder" for my app (I called it My SO App). The system automatically creates this "top level folder": notice in the code above that it was only necessary to use FileManager.default.createDirectory
to create the subdirectory. The right view shows the contents of the top level folder. As expected it shows a file and a subdirectory (that contains two items). The user is able to open these text files, and easily "share it to other people or send the written file by email" as the OP expressed in a comment.
I used UIActivityViewController to save a file on my phone. It's simple and works.
import SwiftUI
struct ContentView: View {
var body: some View {
Button(action: wirtieFile) {
Image(systemName: "square.and.arrow.up")
}
}
func wirtieFile() -> Void{
let file = "test.txt"
let dir = NSURL(fileURLWithPath: NSTemporaryDirectory()).appendingPathComponent(file)
let contents = "test..."
do {
try contents.write(to: dir!, atomically: true, encoding: .utf8)
} catch {
print(error.localizedDescription)
}
var filesToShare = [Any]()
filesToShare.append(dir!)
let av = UIActivityViewController(activityItems: filesToShare, applicationActivities: nil)
UIApplication.shared.windows.first?.rootViewController?.present(av, animated: true, completion: nil)
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With