从小部件单击启动 ViewController 的问题

Posted

技术标签:

【中文标题】从小部件单击启动 ViewController 的问题【英文标题】:Problems starting ViewController from a widget click 【发布时间】:2021-11-05 18:55:56 【问题描述】:

我有一个小部件,并希望在单击它时打开一个特定的 ViewController。我已阅读有关该主题的所有文档和问题,但无法弄清楚为什么它不起作用。单击小部件时,它始终会打开默认的 ViewController。

这是 WidgetView 的代码。

struct WidgetAdapter : View 

    let entry: TimeLine.Entry
    @Environment(\.widgetFamily) var family

    @ViewBuilder
    var body: some View 
        switch family 
        case .systemSmall:
            SmallView(...).widgetURL(URL(string: "fcv://open_activity"))
        case .systemMedium:
            MediumView(...).widgetURL(URL(string: "fcv://open_activity"))
        default:
            LargeView(...).widgetURL(URL(string: "fcv://open_activity"))
        
    

这里是管理 URL 的 AppDelegate 方法。

func application(_ application: UIApplication, open
                    url: URL, options: [UIApplication.OpenURLOptionsKey : Any] = [:]) -> Bool 
    if url.scheme == "fcv"
        let storyboard = UIStoryboard(name: "Main", bundle: nil)
        let vc = storyboard.instantiateViewController(withIdentifier: "WidgetActivity") as! WidgetActivityController
        self.window?.rootViewController = vc
        self.window?.makeKeyAndVisible()
    
    return true

我还尝试为 SceneDelegate 实现相应的方法,我将 url 方案添加到项目信息中的 URL 类型中,我将 LSApplicationQueriesSchemes 项添加到 info.plist,使用 Link 而不是 .widgetURL ...一次也不行。我也认为 AppDelegate 中的方法没有被调用,但是,我检查了可能发生的情况并且它们没有发生。

任何帮助将不胜感激。

【问题讨论】:

【参考方案1】:

我通过找到当前的rootViewController 并推送我需要的视图解决了同样的问题:

let rootViewController = window!.rootViewController as! UINavigationController
let mainStoryboard = UIStoryboard(name: "Main", bundle: nil)let profileViewController = mainStoryboard.instantiateViewController(withIdentifier: "MainVC") as! CombinedMainVC
rootViewController.pushViewController(profileViewController, animated: false)

在我的情况下总是UINavigationController,所以我push是一个新的VC,在你的情况下你可以present它。

我在AppDelegate 中使用了相同的方法,因此您的if 语句可能存在问题。您在哪里为小部件 URL 设置方案?也许你可以检查 URL 字符串:

if url.absoluteString.prefix(3) == "fcv"  

【讨论】:

感谢您的回答。但没有解决问题。正如我所说,AppDelegate 方法甚至没有被调用。 我发现,即使我的应用程序不使用 SceneDelegate,它也可以在 ios 13 上运行。我把它运行在 iOS 14 上并调用了该方法。然后,你的回答就像魅力一样!谢谢。 对于那些将来访问这个问题的人。您的应用可能在 SceneDelegate 中而不是在 AppDelegate 中管理 URL。

以上是关于从小部件单击启动 ViewController 的问题的主要内容,如果未能解决你的问题,请参考以下文章

如何从小部件扩展导航到 UIKit viewController?

如果活动在后台运行,则无需通过启动器即可从小部件恢复现有活动

从小部件打开应用程序时返回堆栈导航不起作用

Android:从小部件打开错误的活动

从小部件启动对话框无法正常工作

从小部件的父级访问坐标