Updating to MacOS 12, in Objective C, I get the above warning regarding changing kUTTypeJPEG to UTTypeJPEG in two places The old code still works but even after the @import UniformTypeIdentifiers changing kUTTypeJPEG to UTTypeJPEG with various types, e.g. CFString, CFStringRef, and that UTTYPE doesn't bridge???, etc. (I am obviously clueless about this) I get the compiler warnings to go away but then the program crashes.
How do I fix these? Something to do with ARC or bridging???
CGImageDestinationRef destinationRef = CGImageDestinationCreateWithURL((__bridge CFURLRef)theURL, (NSString *)kUTTypeJPEG, 1, NULL);
NSDictionary *imageSourceCreationOptions = [NSDictionary dictionaryWithObjectsAndKeys:
kUTTypeJPEG,(NSString *)kCGImageSourceTypeIdentifierHint,
(NSNumber *)kCFBooleanTrue, (NSString *)kCGImageSourceShouldCache,
(NSNumber *)kCFBooleanTrue, (NSString *)kCGImageSourceShouldAllowFloat,
nil];
Uniform Type Identifiers
RSS for tagThe Uniform Type Identifiers framework provides a collection of common types, and maps them to MIME and file types.
Posts under Uniform Type Identifiers tag
14 Posts
Sort by:
Post
Replies
Boosts
Views
Activity
I have a need to list all known audio/image file types in a planned app.
What I have known so far:
images
.apng
.avi, .avif
.gif
.jpg, .jpeg, .jfif, .pjpeg, .pjp
.png
.svg
.webp
audio
.aif
.cda
.mid, .midi
.mp3
.mpa
.ogg
.wav
.wma
What are the missing ones?
Per the docs, NSImage.imageTypes returns a list UTI's, something like below:
com.adobe.pdf
com.apple.pict
com.adobe.encapsulated-postscript
public.jpeg
public.png
com.compuserve.gif
com.canon.tif-raw-image
...
What I need is get file extensions of a UTI. For example, public.jpeg picture file may have several file extensions, say .jpg,.jpeg,.jfif.
Does Cocoa provide any API to query for this information?
Hello,
I'm wondering if there is a way to programmatically write a series of UIImages into an APNG, similar to what the code below does for GIFs (credit: https://github.com/AFathi/ARVideoKit/tree/swift_5). I've tried implementing a similar solution but it doesn't seem to work. My code is included below
I've also done a lot of searching and have found lots of code for displaying APNGs, but have had no luck with code for writing them.
Any hints or pointers would be appreciated.
func generate(gif images: [UIImage], with delay: Float, loop count: Int = 0, _ finished: ((_ status: Bool, _ path: URL?) -> Void)? = nil) {
currentGIFPath = newGIFPath
gifQueue.async {
let gifSettings = [kCGImagePropertyGIFDictionary as String : [kCGImagePropertyGIFLoopCount as String : count]]
let imageSettings = [kCGImagePropertyGIFDictionary as String : [kCGImagePropertyGIFDelayTime as String : delay]]
guard let path = self.currentGIFPath else { return }
guard let destination = CGImageDestinationCreateWithURL(path as CFURL, __UTTypeGIF as! CFString, images.count, nil)
else { finished?(false, nil); return }
//logAR.message("\(destination)")
CGImageDestinationSetProperties(destination, gifSettings as CFDictionary)
for image in images {
if let imageRef = image.cgImage {
CGImageDestinationAddImage(destination, imageRef, imageSettings as CFDictionary)
}
}
if !CGImageDestinationFinalize(destination) {
finished?(false, nil); return
} else {
finished?(true, path)
}
}
}
My adaptation of the above code for APNGs (doesn't work; outputs empty file):
func generateAPNG(images: [UIImage], delay: Float, count: Int = 0) {
let apngSettings = [kCGImagePropertyPNGDictionary as String : [kCGImagePropertyAPNGLoopCount as String : count]]
let imageSettings = [kCGImagePropertyPNGDictionary as String : [kCGImagePropertyAPNGDelayTime as String : delay]]
guard let destination = CGImageDestinationCreateWithURL(outputURL as CFURL, UTType.png.identifier as CFString, images.count, nil)
else { fatalError("Failed") }
CGImageDestinationSetProperties(destination, apngSettings as CFDictionary)
for image in images {
if let imageRef = image.cgImage {
CGImageDestinationAddImage(destination, imageRef, imageSettings as CFDictionary)
}
}
}
Hi, I am working on an iOS app that has a custom document type that can be shared with other devices through Airdrop, iMessages, etc. The app should appear in the "Open In..." menu upon receiving the file however, currently it gets directed straight to the files app. I got this feature to work in a previous iteration of the app in iOS 16 but it no longer works with iOS 17. The feature is also broken with the previous iteration in iOS 17. I have defined the custom document type under both Documents Type and Exported Type Identifiers. I have attached a copy of the info.plist below. My question is how can you make your app appear under the list of apps shown in the "Open In..." menu that appears when receiving files for a custom file type.
<plist version="1.0">
<dict>
<key>CFBundleDocumentTypes</key>
<array>
<dict>
<key>CFBundleTypeIconSystemGenerated</key>
<integer>1</integer>
<key>CFBundleTypeName</key>
<string>RecordingList</string>
<key>CFBundleTypeRole</key>
<string>Editor</string>
<key>LSHandlerRank</key>
<string>Owner</string>
<key>LSItemContentTypes</key>
<array>
<string>com.nikodittmar.MyRaceTimer.recordinglist</string>
</array>
</dict>
</array>
<key>UTExportedTypeDeclarations</key>
<array>
<dict>
<key>UTTypeConformsTo</key>
<array>
<string>public.data</string>
</array>
<key>UTTypeDescription</key>
<string>RecordingList</string>
<key>UTTypeIcons</key>
<dict/>
<key>UTTypeIdentifier</key>
<string>com.nikodittmar.MyRaceTimer.recordinglist</string>
<key>UTTypeTagSpecification</key>
<dict>
<key>public.filename-extension</key>
<array>
<string>recordinglist</string>
</array>
</dict>
</dict>
</array>
<key>UTImportedTypeDeclarations</key>
<array>
<dict>
<key>UTTypeConformsTo</key>
<array>
<string>public.plain-text</string>
</array>
<key>UTTypeDescription</key>
<string>CSV</string>
<key>UTTypeIcons</key>
<dict/>
<key>UTTypeIdentifier</key>
<string>public.comma-separated-values-text</string>
<key>UTTypeTagSpecification</key>
<dict>
<key>public.filename-extension</key>
<array>
<string>csv</string>
</array>
<key>public.mime-type</key>
<array>
<string>text/csv</string>
</array>
</dict>
</dict>
</array>
</dict>
</plist>
import UniformTypeIdentifiers
extension UTType {
static var recordingList: UTType { UTType(exportedAs: "com.nikodittmar.MyRaceTimer.recordinglist") }
}
Thanks.
Hi and thank you in advance for the support. I’m working on a project that allows users to drag and drop files into and out of my app using the Drag and Drop API. From my understanding, dropping a file into the app requires the file to be an NSItemProvider to be eligible for a drop - like this:
func onDrop(of: [UTType], is Targeted: Binding<Bool>?, perform: ([NSItemProvider]) -> Bool) -> some View
and dragging a file out of the app requires the same:
func onDrag (() -> NSItemProvider) -> some View
The only success I’ve had with this is actually specifying the subtype of NSItemProvider the app will be receiving via drop, or dragging away - like this:
/*Example view with drop modifier*/
ScrollView {
Text(“Dropped text”)
.onDrag {
handleDragAway(for: text)
}
}
.onDrop(of: [UTType.text.identifier], isTargeted: nil) { providers in
handleDrop(providers: providers)
}
/*Handle drop of item NSItemProvider conforming to plain text*/
func handleDropInto(providers: [NSItemProvider]) -> Bool {
var didHandle = false
for provider in providers {
if provider.hasItemConformingToTypeIdentifier(UTType.plainText.identifier) {
_ = provider.loadObject(ofClass: String.self) { string, _ in
DispatchQueue.main.async {
if let string = string {
self.handlePlainText(text: string)
didHandle = true
}
}
}
} else {
didHandle = false
}
return didHandle
}
}
/*Handle dragging the item away*/
func handleDragAway(for text: String) -> NSItemProvider {
return NSItemProvider(object: text as NSString)
}
Essentially this code, albeit incomplete, gets the idea across. Drag text into the view, display the text, drag it out. Now, all the documentation I can find says you can rinse and repeat for basically any file type (with some processing) that conforms to NSItemProvider. Here is my question: what if I don’t want to specify file type - what if I just want to tell the app, the user is dragging in some file that conforms to NSItemProvider, don’t worry about its type. Display “File” to show the user they have successfully dropped a file into the view, but don’t do any with the file (this could be implemented later). Then, the user can drag that file away, conforming to NSItemProvider, and wherever they drag it can deal with its file type. Here is an implementation of this idea:
import SwiftUI
import UniformTypeIdentifiers
struct BoardItem {
let id: UUID
let provider: NSItemProvider
}
struct BoardItemView: View {
var body: some View {
Text("File")
.frame(width: 100, height: 100)
.border(Color.black)
}
}
struct BoardView: View {
@State private var boardItems: [BoardItem] = []
var body: some View {
ScrollView {
ForEach(boardItems, id: \.id) { item in
BoardItemView()
.onDrag {
return item.provider
}
}
}
.onDrop(of: [UTType.item.identifier], isTargeted: nil) { providers in
providers.forEach { provider in
let newItem = BoardItem(id: UUID(), provider: provider)
DispatchQueue.main.async {
boardItems.append(newItem)
}
}
return true
}
.frame(maxWidth: .infinity, maxHeight: .infinity)
}
}
The code compiles and runs easily on iPadOS or visionOS. The user can drop anything into the view, “File” appears on screen, and the user can even grab the text (that represents the file). However, dragging the object into a new app does not work. There is no green “+” element to verify the object is droppable anywhere, and attempting to drop it anywhere results in a red console message in Xcode saying
Cannot retrieve a strong reference to PBItemCollection.
Does anyone know how to fix the functionality and the error?
I appreciate you engaging in a long post, thank you!
For the fields listed below, what are the recommended or typical values such that (1) my app can open, edit, and save any ".txt" file and (2) such that other text viewing/editing apps can open the files created by my app? If it matters, my app can view, create, edit, and save UTF-8 text.
Document Types fields Name and Types and all the fields for Imported Type Identifiers. And any other important fields or other things that I should set.
Also, if I upload my app to the App Store and make a mistake on some or all of these, will I be able to correct them?
My knowledge in this area is close to zero, so I'm hoping for minimal technical information, just simple answers if such are possible. I hope you understand.
I'm struggling to create a simple document app on macOS that can open a directory (and display content found there).
I created a new project in Xcode 15 using the "Document App" template and then just changed the readableContentTypes var like this:
struct DocumentDemoDocument: FileDocument {
//...
static var readableContentTypes: [UTType] { [.directory, .folder] }```
//...
}
But, when I run that app and choose File->Open..., the Open button is still grayed out when a directory is selected. What did I miss here?
I'm developing an application that is supposed:
to open .3mf file (and other file types), and
to provide Quick Look thumbnails for this file format.
Because of (2) I need to add UTIs into my app Info.plist (and to my thumbnailing appex Info.plist). So the app's Info.plist changes are:
into CFBundleDocumentTypes key of 3mf file type adding my custom UTI like this:
<key>LSItemContentTypes</key>
<array>
<string>com.prusa3d.slic3r.3mf</string>
</array>
Creating UTExportedTypeDeclarations section with UTI metadata for given file type like this:
<key>UTExportedTypeDeclarations</key>
<array>
...
<dict>
<key>UTTypeIdentifier</key>
<string>com.prusa3d.slic3r.3mf</string>
<key>UTTypeConformsTo</key>
<array>
<string>public.zip-archive</string>
</array>
<key>UTTypeDescription</key>
<string>3MF</string>
<key>UTTypeIcons</key>
<dict/>
<key>UTTypeTagSpecification</key>
<dict>
<key>public.filename-extension</key>
<array>
<string>3mf</string>
</array>
</dict>
</dict>
...
</array>
Unfortunately this is not working as I've installed Shapr3D app, which registers the same file extension with own different UTI ID like this:
<key>UTImportedTypeDeclarations</key>
<array>
...
<dict>
<key>UTTypeConformsTo</key>
<array>
<string>public.data</string>
</array>
<key>UTTypeDescription</key>
<string>3MF</string>
<key>UTTypeIconFiles</key>
<array>
<string>document-icon-64x64.png</string>
<string>document-icon-320x320.png</string>
</array>
<key>UTTypeIdentifier</key>
<string>com.shapr3d.3d-manufacturing.3mf</string>
<key>UTTypeTagSpecification</key>
<dict>
<key>public.filename-extension</key>
<string>3mf</string>
</dict>
</dict>
...
</array>
So my question is: How can I handle this UTI ID/file extension conflict?
So far I came up with following bad but working solution:
Uninstall the conflicting application,
Use the same UTI ID.
I say "bad solutions" because:
The (1) is user hostile/unacceptable approach,
the (2) is fragile approach, as there are other applications that may register same file extension with different UTI ID (the .3mf sort of universal file format for 3D manufacturing the other apps are using too).
Hello! I've been trying to create a custom USDZ viewer using the Vision Pro. Basically, I want to be able to load in a file and have a custom control system I can use to transform, playback animations, etc.
I'm getting stuck right at the starting line however. As far as I can tell, the only way to access the file system through SwiftUI is to use the DocumentGroup struct to bring up the view. This requires implementing a file type through the FileDocument protocol.
All of the resources I'm finding use text files as their example, so I'm unsure of how to implement USDZ files. Here is the FileDocument I've built so far:
import SwiftUI
import UniformTypeIdentifiers
import RealityKit
struct CoreUsdzFile: FileDocument {
// we only support .usdz files
static var readableContentTypes = [UTType.usdz]
// make empty by default
var content: ModelEntity = .init()
// initializer to create new, empty usdz files
init(initialContent: ModelEntity = .init()){
content = initialContent
}
// import or read file
init(configuration: ReadConfiguration) throws {
if let data = configuration.file.regularFileContents {
// convert file content to ModelEntity?
content = ModelEntity.init(mesh: data)
} else {
throw CocoaError(.fileReadCorruptFile)
}
}
// save file wrapper
func fileWrapper(configuration: WriteConfiguration) throws -> FileWrapper {
let data = Data(content)
return FileWrapper(regularFileWithContents: data)
}
}
My errors are on conversion of the file data into a ModelEntity and the reverse. I'm not sure if ModelEntity is the correct typing here, but as far as I can tell .usdz files are imported as ModelEntities.
Any help is much appreciated!
Dylan
Good afternoon! Dear developers, I ask you for help, we do not understand how to deal with this error:
Error start method: Optional(WireGuardKit.WireGuardAdapterError.cannotLocateTunnelFileDescriptor)
We use the Wire guard library to open a VPN tunnel. But we do not understand where to get the TunnelFileDescriptor , we ask you to help
I have a document app built using SwiftData because frankly I'm too lazy to learn how to use FileDocument. The app's title is "Artsheets," and I'm using a document type that my app owns: com.wannafedor4.ArtsheetsDoc. The exported type identifier has these values:
Description: Artsheets Document
Identifier: com.wannafedor4.ArtsheetsDoc
Conforms to: com.apple.package
Reference URL: (none)
Extensions: artsheets
MIME Types: (none)
And the code:
ArtsheetsApp.swift
import SwiftUI
import SwiftData
@main
struct ArtsheetsApp: App {
var body: some Scene {
DocumentGroup(editing: Sheet.self, contentType: .package) {
EditorView()
}
}
}
Document.swift
import SwiftUI
import SwiftData
import UniformTypeIdentifiers
@Model
final class Sheet {
var titleKey: String
@Relationship(deleteRule: .cascade) var columns: [Column]
init(titleKey: String, columns: [Column]) {
self.titleKey = titleKey
self.columns = columns
}
}
@Model
final class Column: Identifiable {
var titlekey: String
var text: [String]
init(titlekey: String, text: [String]) {
self.titlekey = titlekey
self.text = text
}
}
extension UTType {
static var artsheetsDoc = UTType(exportedAs: "com.wannafedor4.artsheetsDoc")
}
I compiling for my iPhone 13 works, but then when creating a document I get this error:
Failed to create document. Error: Error Domain=com.apple.DocumentManager Code=2 "No location available to save “Untitled”." UserInfo={NSLocalizedDescription=No location available to save “Untitled”., NSLocalizedRecoverySuggestion=Enable at least one location to be able to save documents.}
In one of our apps (not sandboxed) the user can choose a file that matches one of the following UTTypes using an NSOpenPanel:
UTTypeApplicationBundle
UTTypeUnixExecutable
UTTypeShellScript
The selected file will then be launched under certain circumstances. This works pretty well but from time to time we see internal support tickets where people complain because the selected file is not executed. This only affects files of type UTTypeUnixExecutable and UTTypeShellScript for which the Unix permissions are incorrect. They are therefore not executable.
I would now like to check in the app whether the selected file is executable. With app bundles this works without any problems with isExecutableFileAtPath:, but with the other file types this does not work. What is the recommended way to test this for the other files? Is there a better way than checking the POSIX permissions (and owner/group)? Thanks.
My app exports a custom file type identifier for a file that it exports to share between other users of the same app. However in the list of apps in UIActivityViewController view, my app is listed far off screen. How can I make my app which owns the file type appear first in the list, instead of seeing many irrelevant apps that can't actually open my file?
Plist snippets:
<key>CFBundleDocumentTypes</key>
<array>
<dict>
<key>CFBundleTypeName</key>
<string>My Custom App File</string>
<key>LSHandlerRank</key>
<string>Owner</string>
<key>LSItemContentTypes</key>
<array>
<string>abc.myapp.myextension</string>
</array>
</dict>
</array>
<key>UTExportedTypeDeclarations</key>
<array>
<dict>
<key>UTTypeConformsTo</key>
<array>
<string>public.content</string>
<string>public.data</string>
</array>
<key>UTTypeDescription</key>
<string>My Custom App File</string>
<key>UTTypeIconFiles</key>
<array/>
<key>UTTypeIdentifier</key>
<string>abc.myapp.myextension</string>
<key>UTTypeTagSpecification</key>
<dict>
<key>public.filename-extension</key>
<array>
<string>myextension</string>
</array>
<key>public.mime-type</key>
<array>
<string>application/octet-stream</string>
</array>
</dict>
</dict>
</array>