swift - 如何处理拖到 SwiftUI 中的停靠图标上?
问题描述
我已经设置了一个 SwiftUI 应用程序,该应用程序似乎接受拖放到停靠图标上的图像,但我无法弄清楚在我的应用程序代码中处理拖放图像的位置。
如何处理将图像(或任何特定文件)拖放到 SwiftUI 应用程序的停靠图标上?
背景
使用使用 NSApplication 的旧式 Swift 代码,处理应用程序停靠图标上的文件删除可以分两步完成:
- 在 Info.plist 的 CFBundleDocumentTypes 中注册要接受的类型。
- 在你的 NSApplicationDelegate 上实现application:openFile:(可能还有 application:openFiles:)。
这在一个单独的问题中简洁地记录了下来。
在 Swift UI 中创建应用程序委托(不起作用)
不过,SwiftUI 应用默认不提供应用委托。要实现这些功能,您必须做一些额外的工作:
创建一个实现
NSObject
和NSApplicationDelegate
(或UIApplicationDelegate
)的类:// or NSApplicationDelegate class AppDelegate: NSObject, UIApplicationDelegate { // ... }
在您的
@main
App
实现中,设置委托:... : App { // or @NSApplicationDelegateAdaptor @UIApplicationDelegateAdaptor(AppDelegate.self) var appDelegate
您现在可以实现应用程序委托方法!例如,这将在您的应用启动时打印:
func applicationWillFinishLaunching(_ notification: Notification) {
print("App Delegate loaded!")
}
但是实现 openFile 函数不起作用:
func application(_ sender: NSApplication, openFile filename: String) -> Bool {
print("test", filename)
return false
}
func application(_ sender: NSApplication, openFiles filenames: [String]) {
print("another test", filenames)
}
将文件拖到应用程序上时,这些都不会打印出来。
场景代表?
这似乎是将 AppDelegate 功能分离到 SceneDelegate 中的一些工作的结果:
对于那些可能对此感到头疼的人来说,由于 appdelegate 的功能分离,现在在场景委托中调用了等效的功能。 等效的函数是 scene(_ scene: openURLContexts:)。我还没有研究是否可以“选择退出”,但出于我的目的,没有理由不采用新行为
— m_bedwell on application(open: options:) 没有被调用(强调)
但是没有明显的方法可以访问我们的代码的 SceneDelegate(这甚至可能不适用于 macOS?)。有一个很有希望的类似问题。
有没有更好的办法?
解决方案
在 SwiftUI 中有一种非常简单的方法可以处理拖放到 Dock 图标上!
更新您的 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>CFBundleTypeName</key> <string>Image files</string> <key>CFBundleTypeRole</key> <string>Viewer</string> <key>LSHandlerRank</key> <string>Default</string> <key>LSItemContentTypes</key> <array> <string>public.image</string> </array> </dict> </plist>
在您
body
的中App
,使用onOpenURL:var body: some Scene { WindowGroup { ContentView() .onOpenURL { (url) in // Handle url here } } }
— ianivs(如何使用新的 SwiftUI @main 启动处理 URL 回调?)
推荐阅读
- php - How to use filter_input with array?
- python - 熊猫索引作为标题出现
- html - What is the default browser form behavior for POST method?
- aws-step-functions - 能够映射到 Step Functions 中的单独任务 ARN?
- postgresql - UNION ALL 参数化 postgres
- c# - 正则表达式用 \\ 替换问题
- ssis - 在 SSIS 中映射新字段
- reactjs - 使用 GitLab CI 时如何解决“达到文件观察者数量的系统限制”问题?
- python - 如何在数组中返回不在上下阈值之间的值?
- javascript - SQLSTATE[23000]: Integrity constraint violation: 1048 laravel 5.7