9

I am trying to open from my keyboard extension. I am having custom keyboard and I have add that keyboard from setting. On my custom keyboard there is one button “Show More”, and I want to open my app on this button click.

So I have tried following code :

let context = NSExtensionContext()
 context.open(url! as URL, completionHandler: nil)

 var responder = self as UIResponder?

 while (responder != nil) {

      if responder?.responds(to: Selector("openURL:")) == true {

           responder?.perform(Selector("openURL:"), with: url)
      }
      responder = responder!.next
 }

It is working successfully, but as we know in swift Selector("method_name:") is deprecated and use #selector(classname.methodname(_:)) instead so it is giving warning. And I want to solve that warning. So I have tried as Xcode automatically suggested :

 if responder?.responds(to: #selector(UIApplication.openURL(_:))) == true {

      responder?.perform(#selector(UIApplication.openURL(_:)), with: url)
 }

Also tried :

 if responder?.responds(to: #selector(NSExtensionContext.open(_:))) == true {

      responder?.perform(#selector(NSExtensionContext.open(_:)), with: url)
 }

I have also tried others possible ways, but no luck. If anyone know how to do, please let me know.

I referred this link, Julio Bailon’s answer :

openURL not work in Action Extension

Community
  • 1
  • 1
VRAwesome
  • 4,721
  • 5
  • 27
  • 52

3 Answers3

8

Swift 5.0:

Open Info.plist of hosting app.

  1. Add Url Types -> Item 0 -> Url Schemes -> Item 0 : "yourappname"
  2. Add Url Types -> Item 0 -> Url Schemes -> URL Identifier: "your bundle id"

Go to Keyboard App:

Add following code properly:

@objc func openURL(_ url: URL) {
       return
    }

    func openApp(_ urlstring:String) {

       var responder: UIResponder? = self as UIResponder
       let selector = #selector(openURL(_:))
       while responder != nil {
          if responder!.responds(to: selector) && responder != self {
             responder!.perform(selector, with: URL(string: urlstring)!)
             return
          }
          responder = responder?.next
        }
     }

Call : openApp ("yourappname://your bundle id")

Muge Cevik
  • 235
  • 4
  • 6
  • hi Muge, I'm doing as you say. But it's not working. I'm sure correct to AppName and Bundle Id. What could I have forgotten? – Erkam KUCET Mar 26 '21 at 07:05
  • 1
    Ahh. Okay, I removed derived data and reset the simulator. it's working for me. Thank you @Muge Cevik – Erkam KUCET Mar 26 '21 at 07:36
4

Following code works on Xcode 8.3.3, iOS10, Swift3 without any compiler warnings:

func openUrl(url: URL?) {
    let selector = sel_registerName("openURL:")
    var responder = self as UIResponder?
    while let r = responder, !r.responds(to: selector) {
        responder = r.next
    }
    _ = responder?.perform(selector, with: url)
}
Deniss Fedotovs
  • 1,384
  • 12
  • 22
4
 guard let url = URL(string: UIApplicationOpenSettingsURLString) else { return }
        extensionContext?.open(url, completionHandler: { (success) in
            if !success {
                var responder = self as UIResponder?
                while (responder != nil){
                    let selectorOpenURL = NSSelectorFromString("openURL:")
                    if responder?.responds(to: selectorOpenURL) == true {
                        _ = responder?.perform(selectorOpenURL, with: url)
                    }
                    responder = responder?.next
                }
            }
        })