1 // Copyright 2015-present 650 Industries. All rights reserved. 2 3 import React 4 5 @objc 6 class DevMenuAppInstance: DevMenuRCTAppDelegate { 7 static private var CloseEventName = "closeDevMenu" 8 static private var OpenEventName = "openDevMenu" 9 10 private let manager: DevMenuManager 11 12 13 init(manager: DevMenuManager) { 14 self.manager = manager 15 16 super.init() 17 self.createBridgeAndSetAdapter(launchOptions: nil) 18 } 19 20 init(manager: DevMenuManager, bridge: RCTBridge) { 21 self.manager = manager 22 23 super.init() 24 25 self.bridge = bridge 26 } 27 28 /** 29 Sends an event to JS triggering the animation that collapses the dev menu. 30 */ sendCloseEventnull31 public func sendCloseEvent() { 32 bridge?.enqueueJSCall("RCTDeviceEventEmitter.emit", args: [DevMenuAppInstance.CloseEventName]) 33 } 34 sendOpenEventnull35 public func sendOpenEvent() { 36 bridge?.enqueueJSCall("RCTDeviceEventEmitter.emit", args: [DevMenuAppInstance.OpenEventName]) 37 } 38 39 // MARK: RCTAppDelegate 40 41 // swiftlint:disable implicitly_unwrapped_optional sourceURLnull42 override func sourceURL(for bridge: RCTBridge!) -> URL! { 43 #if DEBUG 44 if let packagerHost = jsPackagerHost() { 45 return RCTBundleURLProvider.jsBundleURL( 46 forBundleRoot: "index", 47 packagerHost: packagerHost, 48 enableDev: true, 49 enableMinification: false) 50 } 51 #endif 52 return jsSourceUrl() 53 } 54 extraModulesnull55 override func extraModules(for bridge: RCTBridge!) -> [RCTBridgeModule]! { 56 var modules: [RCTBridgeModule] = [DevMenuLoadingView.init()] 57 modules.append(DevMenuRCTDevSettings.init()) 58 return modules 59 } 60 bridgenull61 override func bridge(_ bridge: RCTBridge!, didNotFindModule moduleName: String!) -> Bool { 62 return moduleName == "DevMenu" 63 } 64 // swiftlint:enable implicitly_unwrapped_optional 65 66 // MARK: private 67 jsSourceUrlnull68 private func jsSourceUrl() -> URL? { 69 return DevMenuUtils.resourcesBundle()?.url(forResource: "EXDevMenuApp.ios", withExtension: "js") 70 } 71 jsPackagerHostnull72 private func jsPackagerHost() -> String? { 73 // Return `nil` if resource doesn't exist in the bundle. 74 guard let packagerHostPath = DevMenuUtils.resourcesBundle()?.path(forResource: "dev-menu-packager-host", ofType: nil) else { 75 return nil 76 } 77 // Return `nil` if the content is not a valid URL. 78 guard let content = try? String(contentsOfFile: packagerHostPath, encoding: String.Encoding.utf8).trimmingCharacters(in: CharacterSet.newlines), 79 let url = URL(string: content) else { 80 return nil 81 } 82 return url.absoluteString 83 } 84 } 85