Home > OS >  SwiftUI's application(_ openFile:) never called when opening a file from Finder
SwiftUI's application(_ openFile:) never called when opening a file from Finder

Time:06-24

I have a single window macOS application built using SwiftUI. The application exports a new type identifier and registers itself as Editor for that Document type.

Expected behavior: When double-clicking a file of that type I expect the app to launch (if not running) and for my AppDelegate application(_ openFile:) method to be called with the path to the file.

Actual behavior: The app launches but openFile is never called. If the app is already running a new main window is created which I also don't want, and again openFile is never called.

Info.plist:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>CFBundleDocumentTypes</key>
    <array>
        <dict>
            <key>CFBundleTypeName</key>
            <string>Launch Tester File</string>
            <key>CFBundleTypeRole</key>
            <string>Editor</string>
            <key>LSHandlerRank</key>
            <string>Default</string>
            <key>LSItemContentTypes</key>
            <array>
                <string>com.mrrsoftware.ltfile</string>
            </array>
        </dict>
    </array>
    <key>UTExportedTypeDeclarations</key>
    <array>
        <dict>
            <key>UTTypeConformsTo</key>
            <array>
                <string>public.json</string>
            </array>
            <key>UTTypeDescription</key>
            <string>Launch Tester File</string>
            <key>UTTypeIcons</key>
            <dict/>
            <key>UTTypeIdentifier</key>
            <string>com.mrrsoftware.ltfile</string>
            <key>UTTypeTagSpecification</key>
            <dict>
                <key>public.filename-extension</key>
                <array>
                    <string>ltfile</string>
                </array>
            </dict>
        </dict>
    </array>
</dict>
</plist>

App file:

import SwiftUI

@main
struct LaunchTesterApp: App {
    @NSApplicationDelegateAdaptor private var appDeletate : MyAppDelegate
    var body: some Scene {
        WindowGroup {
            ContentView()
        }
        .commands {
            CommandGroup(replacing: .newItem, addition: { })
        }
    }
}

class MyAppDelegate: NSObject, NSApplicationDelegate, ObservableObject {
    func applicationWillFinishLaunching(_ notification: Notification) {
        print("WillFinishLaunching")
    }
    
    func applicationDidFinishLaunching(_ notification: Notification) {
        print("DidFinishLaunching")
        NSWindow.allowsAutomaticWindowTabbing = false
    }
    
    func application(_ sender: NSApplication, openFile filename: String) -> Bool {
        print( "AppDelegate openFile: \(filename)")
        return true
    }
}

How can I get the app to call my AppDelegate application(_ openFile:) method instead of opening a new window?

CodePudding user response:

Use instead

class AppDelegate: NSObject, NSApplicationDelegate {
    func application(_ application: NSApplication, open urls: [URL]) {
        print(">> \(urls)")
    }

Tested with Xcode 13.4 / macOS 12.4

  • Related