react-native-altibbi 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (150) hide show
  1. package/LICENSE +20 -0
  2. package/README.md +190 -0
  3. package/android/build.gradle +104 -0
  4. package/android/gradle.properties +5 -0
  5. package/android/src/main/AndroidManifest.xml +3 -0
  6. package/android/src/main/AndroidManifestNew.xml +2 -0
  7. package/android/src/main/java/com/altibbi/AltibbiModule.kt +18 -0
  8. package/android/src/main/java/com/altibbi/AltibbiPackage.kt +18 -0
  9. package/android/src/main/java/com/altibbi/OTCustomAudioDevice.java +1146 -0
  10. package/android/src/main/java/com/altibbi/OTPublisherLayout.java +61 -0
  11. package/android/src/main/java/com/altibbi/OTPublisherViewManager.java +30 -0
  12. package/android/src/main/java/com/altibbi/OTRN.java +101 -0
  13. package/android/src/main/java/com/altibbi/OTScreenCapturer.java +120 -0
  14. package/android/src/main/java/com/altibbi/OTSessionManager.java +1281 -0
  15. package/android/src/main/java/com/altibbi/OTSubscriberLayout.java +68 -0
  16. package/android/src/main/java/com/altibbi/OTSubscriberViewManager.java +30 -0
  17. package/android/src/main/java/com/altibbi/Socket.kt +294 -0
  18. package/android/src/main/java/com/altibbi/SocketEventEmitter.kt +25 -0
  19. package/android/src/main/java/com/altibbi/utils/EventUtils.java +189 -0
  20. package/android/src/main/java/com/altibbi/utils/Utils.java +135 -0
  21. package/ios/Altibbi-Bridging-Header.h +6 -0
  22. package/ios/Altibbi.mm +10 -0
  23. package/ios/Altibbi.swift +4 -0
  24. package/ios/OTCustomAudioDriver.swift +696 -0
  25. package/ios/OTPublisher.m +16 -0
  26. package/ios/OTPublisherManager.swift +21 -0
  27. package/ios/OTPublisherView.swift +28 -0
  28. package/ios/OTRN.swift +27 -0
  29. package/ios/OTScreenCapture.h +27 -0
  30. package/ios/OTScreenCapture.m +171 -0
  31. package/ios/OTSessionManager.m +127 -0
  32. package/ios/OTSessionManager.swift +866 -0
  33. package/ios/OTSubscriber.m +15 -0
  34. package/ios/OTSubscriberManager.swift +21 -0
  35. package/ios/OTSubscriberView.swift +29 -0
  36. package/ios/OpenTokReactNative.h +13 -0
  37. package/ios/OpenTokReactNative.m +13 -0
  38. package/ios/SocketReactNative.m +38 -0
  39. package/ios/SocketReactNative.swift +276 -0
  40. package/ios/Utils/EventUtils.swift +143 -0
  41. package/ios/Utils/Utils.swift +126 -0
  42. package/lib/commonjs/connection.js +200 -0
  43. package/lib/commonjs/connection.js.map +1 -0
  44. package/lib/commonjs/data.js +12 -0
  45. package/lib/commonjs/data.js.map +1 -0
  46. package/lib/commonjs/index.js +275 -0
  47. package/lib/commonjs/index.js.map +1 -0
  48. package/lib/commonjs/scoket.js +245 -0
  49. package/lib/commonjs/scoket.js.map +1 -0
  50. package/lib/commonjs/service.js +21 -0
  51. package/lib/commonjs/service.js.map +1 -0
  52. package/lib/commonjs/types.js +2 -0
  53. package/lib/commonjs/types.js.map +1 -0
  54. package/lib/commonjs/video/OT.js +57 -0
  55. package/lib/commonjs/video/OT.js.map +1 -0
  56. package/lib/commonjs/video/OTError.js +17 -0
  57. package/lib/commonjs/video/OTError.js.map +1 -0
  58. package/lib/commonjs/video/OTPublisher.js +171 -0
  59. package/lib/commonjs/video/OTPublisher.js.map +1 -0
  60. package/lib/commonjs/video/OTSession.js +205 -0
  61. package/lib/commonjs/video/OTSession.js.map +1 -0
  62. package/lib/commonjs/video/OTSubscriber.js +185 -0
  63. package/lib/commonjs/video/OTSubscriber.js.map +1 -0
  64. package/lib/commonjs/video/contexts/OTContext.js +11 -0
  65. package/lib/commonjs/video/contexts/OTContext.js.map +1 -0
  66. package/lib/commonjs/video/helpers/OTHelper.js +92 -0
  67. package/lib/commonjs/video/helpers/OTHelper.js.map +1 -0
  68. package/lib/commonjs/video/helpers/OTPublisherHelper.js +117 -0
  69. package/lib/commonjs/video/helpers/OTPublisherHelper.js.map +1 -0
  70. package/lib/commonjs/video/helpers/OTSessionHelper.js +206 -0
  71. package/lib/commonjs/video/helpers/OTSessionHelper.js.map +1 -0
  72. package/lib/commonjs/video/helpers/OTSubscriberHelper.js +121 -0
  73. package/lib/commonjs/video/helpers/OTSubscriberHelper.js.map +1 -0
  74. package/lib/commonjs/video/index.js +42 -0
  75. package/lib/commonjs/video/index.js.map +1 -0
  76. package/lib/commonjs/video/views/OTPublisherView.js +26 -0
  77. package/lib/commonjs/video/views/OTPublisherView.js.map +1 -0
  78. package/lib/commonjs/video/views/OTSubscriberView.js +25 -0
  79. package/lib/commonjs/video/views/OTSubscriberView.js.map +1 -0
  80. package/lib/module/connection.js +180 -0
  81. package/lib/module/connection.js.map +1 -0
  82. package/lib/module/data.js +6 -0
  83. package/lib/module/data.js.map +1 -0
  84. package/lib/module/index.js +12 -0
  85. package/lib/module/index.js.map +1 -0
  86. package/lib/module/scoket.js +235 -0
  87. package/lib/module/scoket.js.map +1 -0
  88. package/lib/module/service.js +14 -0
  89. package/lib/module/service.js.map +1 -0
  90. package/lib/module/types.js +2 -0
  91. package/lib/module/types.js.map +1 -0
  92. package/lib/module/video/OT.js +49 -0
  93. package/lib/module/video/OT.js.map +1 -0
  94. package/lib/module/video/OTError.js +10 -0
  95. package/lib/module/video/OTError.js.map +1 -0
  96. package/lib/module/video/OTPublisher.js +162 -0
  97. package/lib/module/video/OTPublisher.js.map +1 -0
  98. package/lib/module/video/OTSession.js +195 -0
  99. package/lib/module/video/OTSession.js.map +1 -0
  100. package/lib/module/video/OTSubscriber.js +175 -0
  101. package/lib/module/video/OTSubscriber.js.map +1 -0
  102. package/lib/module/video/contexts/OTContext.js +4 -0
  103. package/lib/module/video/contexts/OTContext.js.map +1 -0
  104. package/lib/module/video/helpers/OTHelper.js +82 -0
  105. package/lib/module/video/helpers/OTHelper.js.map +1 -0
  106. package/lib/module/video/helpers/OTPublisherHelper.js +110 -0
  107. package/lib/module/video/helpers/OTPublisherHelper.js.map +1 -0
  108. package/lib/module/video/helpers/OTSessionHelper.js +195 -0
  109. package/lib/module/video/helpers/OTSessionHelper.js.map +1 -0
  110. package/lib/module/video/helpers/OTSubscriberHelper.js +112 -0
  111. package/lib/module/video/helpers/OTSubscriberHelper.js.map +1 -0
  112. package/lib/module/video/index.js +7 -0
  113. package/lib/module/video/index.js.map +1 -0
  114. package/lib/module/video/views/OTPublisherView.js +18 -0
  115. package/lib/module/video/views/OTPublisherView.js.map +1 -0
  116. package/lib/module/video/views/OTSubscriberView.js +17 -0
  117. package/lib/module/video/views/OTSubscriberView.js.map +1 -0
  118. package/lib/typescript/src/connection.d.ts +40 -0
  119. package/lib/typescript/src/connection.d.ts.map +1 -0
  120. package/lib/typescript/src/data.d.ts +7 -0
  121. package/lib/typescript/src/data.d.ts.map +1 -0
  122. package/lib/typescript/src/index.d.ts +12 -0
  123. package/lib/typescript/src/index.d.ts.map +1 -0
  124. package/lib/typescript/src/scoket.d.ts +100 -0
  125. package/lib/typescript/src/scoket.d.ts.map +1 -0
  126. package/lib/typescript/src/service.d.ts +9 -0
  127. package/lib/typescript/src/service.d.ts.map +1 -0
  128. package/lib/typescript/src/types.d.ts +22 -0
  129. package/lib/typescript/src/types.d.ts.map +1 -0
  130. package/package.json +178 -0
  131. package/react-native-altibbi.podspec +46 -0
  132. package/src/connection.ts +255 -0
  133. package/src/data.ts +21 -0
  134. package/src/index.tsx +80 -0
  135. package/src/scoket.ts +365 -0
  136. package/src/service.ts +20 -0
  137. package/src/types.ts +22 -0
  138. package/src/video/OT.js +65 -0
  139. package/src/video/OTError.js +14 -0
  140. package/src/video/OTPublisher.js +193 -0
  141. package/src/video/OTSession.js +168 -0
  142. package/src/video/OTSubscriber.js +148 -0
  143. package/src/video/contexts/OTContext.js +5 -0
  144. package/src/video/helpers/OTHelper.js +91 -0
  145. package/src/video/helpers/OTPublisherHelper.js +122 -0
  146. package/src/video/helpers/OTSessionHelper.js +233 -0
  147. package/src/video/helpers/OTSubscriberHelper.js +125 -0
  148. package/src/video/index.js +13 -0
  149. package/src/video/views/OTPublisherView.js +19 -0
  150. package/src/video/views/OTSubscriberView.js +18 -0
@@ -0,0 +1,866 @@
1
+ //
2
+ // OTSessionManager.swift
3
+ // OpenTokReactNative
4
+ //
5
+ // Created by Manik Sachdeva on 1/12/18.
6
+ // Copyright © 2018 Facebook. All rights reserved.
7
+ //
8
+
9
+ import Foundation
10
+
11
+ @objc(OTSessionManager)
12
+ class OTSessionManager: RCTEventEmitter {
13
+
14
+ var jsEvents: [String] = [];
15
+ var componentEvents: [String] = [];
16
+ var logLevel: Bool = false;
17
+
18
+ deinit {
19
+ OTRN.sharedState.subscriberStreams.removeAll();
20
+ OTRN.sharedState.sessions.removeAll();
21
+ OTRN.sharedState.sessionConnectCallbacks.removeAll();
22
+ OTRN.sharedState.sessionDisconnectCallbacks.removeAll();
23
+ OTRN.sharedState.isPublishing.removeAll();
24
+ OTRN.sharedState.publishers.removeAll();
25
+ OTRN.sharedState.subscribers.removeAll();
26
+ OTRN.sharedState.publisherDestroyedCallbacks.removeAll();
27
+ OTRN.sharedState.publisherStreams.removeAll();
28
+ OTRN.sharedState.streamObservers.removeAll();
29
+ OTRN.sharedState.connections.removeAll();
30
+ }
31
+
32
+ override static func requiresMainQueueSetup() -> Bool {
33
+ return true;
34
+ }
35
+
36
+ @objc override func supportedEvents() -> [String] {
37
+ let allEvents = EventUtils.getSupportedEvents();
38
+ return allEvents + jsEvents
39
+ }
40
+
41
+ @objc func initSession(_ apiKey: String, sessionId: String, sessionOptions: Dictionary<String, Any>) -> Void {
42
+ let enableStereoOutput: Bool = Utils.sanitizeBooleanProperty(sessionOptions["enableStereoOutput"] as Any);
43
+ if enableStereoOutput == true {
44
+ let customAudioDevice = OTCustomAudioDriver()
45
+ OTAudioDeviceManager.setAudioDevice(customAudioDevice)
46
+ }
47
+ let settings = OTSessionSettings();
48
+ settings.connectionEventsSuppressed = Utils.sanitizeBooleanProperty(sessionOptions["connectionEventsSuppressed"] as Any);
49
+ // Note: IceConfig is an additional property not supported at the moment. We need to add a sanitize function
50
+ // to validate the input from settings.iceConfig.
51
+ // settings.iceConfig = sessionOptions["iceConfig"];
52
+ settings.proxyURL = Utils.sanitizeStringProperty(sessionOptions["proxyUrl"] as Any);
53
+ settings.ipWhitelist = Utils.sanitizeBooleanProperty(sessionOptions["ipWhitelist"] as Any);
54
+ settings.iceConfig = Utils.sanitizeIceServer(sessionOptions["customServers"] as Any, sessionOptions["transportPolicy"] as Any, sessionOptions["includeServers"] as Any);
55
+ OTRN.sharedState.sessions.updateValue(OTSession(apiKey: apiKey, sessionId: sessionId, delegate: self, settings: settings)!, forKey: sessionId);
56
+ }
57
+
58
+ @objc func connect(_ sessionId: String, token: String, callback: @escaping RCTResponseSenderBlock) -> Void {
59
+ var error: OTError?
60
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
61
+ let errorInfo = EventUtils.createErrorMessage("Error connecting to session. Could not find native session instance")
62
+ callback([errorInfo]);
63
+ return
64
+ }
65
+ session.connect(withToken: token, error: &error)
66
+ if let err = error {
67
+ self.dispatchErrorViaCallback(callback, error: err)
68
+ } else {
69
+ OTRN.sharedState.sessionConnectCallbacks[sessionId] = callback;
70
+ }
71
+ }
72
+
73
+ @objc func initPublisher(_ publisherId: String, properties: Dictionary<String, Any>, callback: @escaping RCTResponseSenderBlock) -> Void {
74
+ DispatchQueue.main.async {
75
+ let publisherProperties = OTPublisherSettings()
76
+ publisherProperties.videoTrack = Utils.sanitizeBooleanProperty(properties["videoTrack"] as Any);
77
+ publisherProperties.audioTrack = Utils.sanitizeBooleanProperty(properties["audioTrack"] as Any);
78
+ if let audioBitrate = properties["audioBitrate"] as? Int {
79
+ publisherProperties.audioBitrate = Int32(audioBitrate);
80
+ }
81
+ publisherProperties.cameraFrameRate = Utils.sanitizeFrameRate(properties["frameRate"] as Any);
82
+ publisherProperties.cameraResolution = Utils.sanitizeCameraResolution(properties["resolution"] as Any);
83
+ publisherProperties.enableOpusDtx = Utils.sanitizeBooleanProperty(properties["enableDtx"] as Any);
84
+ publisherProperties.name = properties["name"] as? String;
85
+ publisherProperties.videoCapture?.videoContentHint = Utils.convertVideoContentHint(properties["videoContentHint"] as Any)
86
+ OTRN.sharedState.publishers.updateValue(OTPublisher(delegate: self, settings: publisherProperties)!, forKey: publisherId);
87
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else {
88
+ let errorInfo = EventUtils.createErrorMessage("There was an error creating the native publisher instance")
89
+ callback([errorInfo]);
90
+ return
91
+ }
92
+ if let videoSource = properties["videoSource"] as? String, videoSource == "screen" {
93
+ guard let screenView = RCTPresentedViewController()?.view else {
94
+ let errorInfo = EventUtils.createErrorMessage("There was an error setting the videoSource as screen")
95
+ callback([errorInfo]);
96
+ if let scalableScreenshare = properties["scalableScreenshare"] as? Bool {
97
+ publisherProperties.scalableScreenshare = scalableScreenshare;
98
+ }
99
+ return
100
+ }
101
+ publisher.videoType = .screen;
102
+ publisher.videoCapture = OTScreenCapture(view: (screenView))
103
+ } else if let cameraPosition = properties["cameraPosition"] as? String {
104
+ publisher.cameraPosition = cameraPosition == "front" ? .front : .back;
105
+ }
106
+ publisher.audioFallbackEnabled = Utils.sanitizeBooleanProperty(properties["audioFallbackEnabled"] as Any);
107
+ publisher.publishAudio = Utils.sanitizeBooleanProperty(properties["publishAudio"] as Any);
108
+ publisher.publishVideo = Utils.sanitizeBooleanProperty(properties["publishVideo"] as Any);
109
+ publisher.publishCaptions = Utils.sanitizeBooleanProperty(properties["publishCaptions"] as Any);
110
+ publisher.audioLevelDelegate = self;
111
+ publisher.rtcStatsReportDelegate = self;
112
+ callback([NSNull()]);
113
+ }
114
+ }
115
+
116
+ @objc func publish(_ sessionId: String, publisherId: String, callback: RCTResponseSenderBlock) -> Void {
117
+ var error: OTError?
118
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else {
119
+ let errorInfo = EventUtils.createErrorMessage("Error publishing. Could not find native publisher instance")
120
+ callback([errorInfo]);
121
+ return
122
+ }
123
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
124
+ let errorInfo = EventUtils.createErrorMessage("Error connecting to session. Could not find native session instance")
125
+ callback([errorInfo]);
126
+ return
127
+ }
128
+ session.publish(publisher, error: &error)
129
+ if let err = error {
130
+ dispatchErrorViaCallback(callback, error: err)
131
+ } else {
132
+ callback([NSNull()])
133
+ }
134
+ }
135
+
136
+ @objc func subscribeToStream(_ streamId: String, sessionId: String, properties: Dictionary<String, Any>, callback: @escaping RCTResponseSenderBlock) -> Void {
137
+ var error: OTError?
138
+ DispatchQueue.main.async {
139
+ guard let stream = OTRN.sharedState.subscriberStreams[streamId] else {
140
+ let errorInfo = EventUtils.createErrorMessage("Error subscribing. Could not find native stream for subscriber.")
141
+ callback([errorInfo]);
142
+ return
143
+ }
144
+ guard let subscriber = OTSubscriber(stream: stream, delegate: self) else {
145
+ let errorInfo = EventUtils.createErrorMessage("Error subscribing. Could not create subscriber.")
146
+ callback([errorInfo]);
147
+ return
148
+ }
149
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
150
+ let errorInfo = EventUtils.createErrorMessage("Error subscribing to stream. Could not find native session instance")
151
+ callback([errorInfo]);
152
+ return
153
+ }
154
+ OTRN.sharedState.subscribers.updateValue(subscriber, forKey: streamId)
155
+ subscriber.networkStatsDelegate = self;
156
+ subscriber.audioLevelDelegate = self;
157
+ subscriber.captionsDelegate = self;
158
+ session.subscribe(subscriber, error: &error)
159
+ subscriber.subscribeToAudio = Utils.sanitizeBooleanProperty(properties["subscribeToAudio"] as Any);
160
+ subscriber.subscribeToVideo = Utils.sanitizeBooleanProperty(properties["subscribeToVideo"] as Any);
161
+ subscriber.subscribeToCaptions = Utils.sanitizeBooleanProperty(properties["subscribeToCaptions"] as Any);
162
+ subscriber.preferredFrameRate = Utils.sanitizePreferredFrameRate(properties["preferredFrameRate"] as Any);
163
+ subscriber.preferredResolution = Utils.sanitizePreferredResolution(properties["preferredResolution"] as Any);
164
+ if let audioVolume = properties["audioVolume"] as? Double {
165
+ subscriber.audioVolume = audioVolume;
166
+ }
167
+ subscriber.rtcStatsReportDelegate = self;
168
+ if let err = error {
169
+ self.dispatchErrorViaCallback(callback, error: err)
170
+ } else {
171
+ callback([NSNull(), streamId])
172
+ }
173
+ }
174
+ }
175
+
176
+ @objc func removeSubscriber(_ streamId: String, callback: @escaping RCTResponseSenderBlock) -> Void {
177
+ DispatchQueue.main.async {
178
+ OTRN.sharedState.streamObservers.removeValue(forKey: streamId);
179
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else {
180
+ self.removeStream(streamId)
181
+ callback([NSNull()])
182
+ return
183
+ }
184
+ subscriber.view?.removeFromSuperview();
185
+ subscriber.delegate = nil;
186
+ self.removeStream(streamId)
187
+ callback([NSNull()])
188
+ }
189
+
190
+ }
191
+
192
+ @objc func disconnectSession(_ sessionId: String, callback: @escaping RCTResponseSenderBlock) -> Void {
193
+ var error: OTError?
194
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
195
+ let errorInfo = EventUtils.createErrorMessage("Error disconnecting from session. Could not find native session instance")
196
+ callback([errorInfo]);
197
+ return
198
+ }
199
+ session.disconnect(&error)
200
+ if let err = error {
201
+ dispatchErrorViaCallback(callback, error: err)
202
+ } else {
203
+ OTRN.sharedState.sessionDisconnectCallbacks[sessionId] = callback;
204
+ }
205
+ }
206
+
207
+ @objc func publishAudio(_ publisherId: String, pubAudio: Bool) -> Void {
208
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else { return }
209
+ publisher.publishAudio = pubAudio;
210
+ }
211
+
212
+ @objc func publishVideo(_ publisherId: String, pubVideo: Bool) -> Void {
213
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else { return }
214
+ publisher.publishVideo = pubVideo;
215
+ }
216
+
217
+ @objc func getRtcStatsReport(_ publisherId: String) -> Void {
218
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else { return }
219
+ publisher.getRtcStatsReport()
220
+ }
221
+
222
+ @objc func subscribeToAudio(_ streamId: String, subAudio: Bool) -> Void {
223
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else { return }
224
+ subscriber.subscribeToAudio = subAudio;
225
+ }
226
+
227
+ @objc func subscribeToVideo(_ streamId: String, subVideo: Bool) -> Void {
228
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else { return }
229
+ subscriber.subscribeToVideo = subVideo;
230
+ }
231
+
232
+ @objc func subscribeToCaptions(_ streamId: String, subCaptions: Bool) -> Void {
233
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else { return }
234
+ subscriber.subscribeToCaptions = subCaptions;
235
+ }
236
+
237
+ @objc func setPreferredResolution(_ streamId: String, resolution: NSDictionary) -> Void {
238
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else { return }
239
+ subscriber.preferredResolution = Utils.sanitizePreferredResolution(resolution);
240
+ }
241
+
242
+ @objc func setPreferredFrameRate(_ streamId: String, frameRate: Float) -> Void {
243
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else { return }
244
+ subscriber.preferredFrameRate = Utils.sanitizePreferredFrameRate(frameRate);
245
+ }
246
+
247
+ @objc func setAudioVolume(_ streamId: String, audioVolume: Double) -> Void {
248
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else { return }
249
+ subscriber.audioVolume = audioVolume;
250
+ }
251
+
252
+ @objc func getSubscriberRtcStatsReport(_ streamId: String) -> Void {
253
+ guard let subscriber = OTRN.sharedState.subscribers[streamId] else { return }
254
+ subscriber.getRtcStatsReport()
255
+ }
256
+
257
+ @objc func changeCameraPosition(_ publisherId: String, cameraPosition: String) -> Void {
258
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else { return }
259
+ publisher.cameraPosition = cameraPosition == "front" ? .front : .back;
260
+ }
261
+
262
+ @objc func changeVideoContentHint(_ publisherId: String, videoContentHint: String) -> Void {
263
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else { return }
264
+ publisher.videoCapture?.videoContentHint = Utils.convertVideoContentHint(videoContentHint);
265
+ }
266
+
267
+ @objc func setNativeEvents(_ events: Array<String>) -> Void {
268
+ for event in events {
269
+ if (!self.jsEvents.contains(event)) {
270
+ self.jsEvents.append(event);
271
+ }
272
+ }
273
+ }
274
+
275
+ @objc func setJSComponentEvents(_ events: Array<String>) -> Void {
276
+ for event in events {
277
+ self.componentEvents.append(event);
278
+ }
279
+ }
280
+
281
+ @objc func removeJSComponentEvents(_ events: Array<String>) -> Void {
282
+ for event in events {
283
+ if let i = self.componentEvents.index(of: event) {
284
+ self.componentEvents.remove(at: i)
285
+ }
286
+ }
287
+ }
288
+
289
+ @objc func sendSignal(_ sessionId: String, signal: Dictionary<String, String>, callback: RCTResponseSenderBlock ) -> Void {
290
+ var error: OTError?
291
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
292
+ let errorInfo = EventUtils.createErrorMessage("Error sending signal. Could not find native session instance")
293
+ callback([errorInfo]);
294
+ return
295
+ }
296
+ if let connectionId = signal["to"] {
297
+ let connection = OTRN.sharedState.connections[connectionId]
298
+ session.signal(withType: signal["type"], string: signal["data"], connection: connection, error: &error)
299
+ } else {
300
+ let connection: OTConnection? = nil
301
+ session.signal(withType: signal["type"], string: signal["data"], connection: connection, error: &error)
302
+ }
303
+ if let err = error {
304
+ dispatchErrorViaCallback(callback, error: err)
305
+ } else {
306
+ callback([NSNull()])
307
+ }
308
+ }
309
+
310
+ @objc func destroyPublisher(_ publisherId: String, callback: @escaping RCTResponseSenderBlock) -> Void {
311
+ DispatchQueue.main.async {
312
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else { callback([NSNull()]); return }
313
+ var error: OTError?
314
+ if let isPublishing = OTRN.sharedState.isPublishing[publisherId] {
315
+ if (isPublishing) {
316
+ if let sessionId = publisher.session?.sessionId {
317
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
318
+ let errorInfo = EventUtils.createErrorMessage("Error destroying publisher. Could not find native session instance")
319
+ callback([errorInfo]);
320
+ return
321
+ }
322
+ if (session.sessionConnectionStatus.rawValue == 1) {
323
+ session.unpublish(publisher, error: &error)
324
+ }
325
+ }
326
+ }
327
+ }
328
+ guard let err = error else {
329
+ OTRN.sharedState.publisherDestroyedCallbacks[publisherId] = callback;
330
+ return
331
+ }
332
+ self.dispatchErrorViaCallback(callback, error: err)
333
+ }
334
+ }
335
+
336
+ @objc func setVideoTransformers(_ publisherId: String, videoTransformers: Array<Any>) -> Void {
337
+ guard let publisher = OTRN.sharedState.publishers[publisherId] else {
338
+ return // To do -- handle error
339
+ }
340
+ var nativeTransformers: [OTVideoTransformer] = [];
341
+
342
+ for transformer in videoTransformers {
343
+ guard let transformerDictionary = transformer as? [String: String] else {
344
+ return // To do -- handle error
345
+ }
346
+ guard let transformerName = transformerDictionary["name"], let transformerProperties = transformerDictionary["properties"] else {
347
+ return // To do -- handle error
348
+ }
349
+ guard let nativeTransformer = OTVideoTransformer(
350
+ name: transformerName,
351
+ properties: transformerProperties
352
+ ) else {
353
+ return // To do -- handle error
354
+ }
355
+ nativeTransformers.append(nativeTransformer)
356
+ }
357
+ publisher.videoTransformers = nativeTransformers
358
+ }
359
+
360
+ @objc func removeNativeEvents(_ events: Array<String>) -> Void {
361
+ for event in events {
362
+ if let i = self.jsEvents.index(of: event) {
363
+ self.jsEvents.remove(at: i)
364
+ }
365
+ }
366
+ }
367
+
368
+ @objc func getSessionInfo(_ sessionId: String, callback: RCTResponseSenderBlock) -> Void {
369
+ guard let session = OTRN.sharedState.sessions[sessionId] else { callback([NSNull()]); return }
370
+ var sessionInfo: Dictionary<String, Any> = EventUtils.prepareJSSessionEventData(session);
371
+ sessionInfo["connectionStatus"] = session.sessionConnectionStatus.rawValue;
372
+ callback([sessionInfo]);
373
+ }
374
+
375
+ @objc func getSessionCapabilities(_ sessionId: String, callback: RCTResponseSenderBlock) -> Void{
376
+ guard let session = OTRN.sharedState.sessions[sessionId] else { callback([NSNull()]); return }
377
+ var sessionCapabilities: Dictionary<String, Any> = [:];
378
+ sessionCapabilities["canPublish"] = session.capabilities?.canPublish;
379
+ // Bug in OT iOS SDK. This is set to false, but it should be true:
380
+ sessionCapabilities["canSubscribe"] = true;
381
+ sessionCapabilities["canForceMute"] = session.capabilities?.canForceMute;
382
+ callback([sessionCapabilities]);
383
+ }
384
+
385
+ @objc func reportIssue(_ sessionId: String, callback: RCTResponseSenderBlock) -> Void{
386
+ guard let session = OTRN.sharedState.sessions[sessionId] else { callback([NSNull()]); return }
387
+ var issueId:NSString? = ""
388
+ session.reportIssue(&issueId)
389
+ callback([issueId! as NSString])
390
+ }
391
+
392
+ // The OpenTok iOS SDK does not implement a getVideoCodecs method, because iOS
393
+ // supported all supported codecs. But we will implement it here so that the
394
+ // OT.getVideoCodecs() method can be called cross-platform.
395
+ @objc func getSupportedCodecs(_ resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void{
396
+ var supportedCodecs: Dictionary<String, Any> = [:];
397
+ supportedCodecs["videoDecoderCodecs"] = ["H.264", "VP8"];
398
+ supportedCodecs["videoEncoderCodecs"] = ["H.264", "VP8"];
399
+ resolve(supportedCodecs)
400
+ }
401
+
402
+ @objc func forceMuteAll(_ sessionId: String, excludedStreamIds: NSArray, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void{
403
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
404
+ reject("event_failure", "Session ID not found", nil)
405
+ return
406
+ }
407
+ return resolve(true);
408
+ }
409
+
410
+ @objc func forceMuteStream(_ sessionId: String, streamId: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void{
411
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
412
+ reject("event_failure", "Session ID not found", nil);
413
+ return
414
+ }
415
+ guard let stream = OTRN.sharedState.subscriberStreams[streamId] else {
416
+ reject("event_failure", "Stream ID not found", nil);
417
+ return
418
+ }
419
+ var error: OTError?
420
+ session.forceMuteStream(stream, error: &error)
421
+ if let error = error {
422
+ reject("event_failure", error.localizedDescription, nil);
423
+ return;
424
+ }
425
+ resolve(true);
426
+ }
427
+
428
+ @objc func disableForceMute(_ sessionId: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void{
429
+ guard let session = OTRN.sharedState.sessions[sessionId] else {
430
+ reject("event_failure", "Session not found.", nil);
431
+ return
432
+ }
433
+ var error: OTError?
434
+ session.disableForceMute(&error)
435
+ if let error = error {
436
+ reject("event_failure", error.localizedDescription, nil);
437
+ return;
438
+ }
439
+ resolve(true);
440
+ }
441
+
442
+ @objc func enableLogs(_ logLevel: Bool) -> Void {
443
+ self.logLevel = logLevel;
444
+ }
445
+
446
+ func resetPublisher(_ publisherId: String, publisher: OTPublisher) -> Void {
447
+ publisher.view?.removeFromSuperview()
448
+ OTRN.sharedState.isPublishing[publisherId] = false;
449
+ }
450
+
451
+ func removeStream(_ streamId: String) -> Void {
452
+ OTRN.sharedState.subscribers.removeValue(forKey: streamId)
453
+ OTRN.sharedState.subscriberStreams.removeValue(forKey: streamId)
454
+ }
455
+
456
+ func emitEvent(_ event: String, data: Any) -> Void {
457
+ if (self.bridge != nil && (self.jsEvents.contains(event) || self.componentEvents.contains(event))) {
458
+ self.sendEvent(withName: event, body: data);
459
+ }
460
+ }
461
+
462
+ func checkAndEmitStreamPropertyChangeEvent(_ streamId: String, changedProperty: String, oldValue: Any, newValue: Any, isPublisherStream: Bool) {
463
+ guard let stream = isPublisherStream ? OTRN.sharedState.publisherStreams[streamId] : OTRN.sharedState.subscriberStreams[streamId] else { return }
464
+ let streamInfo: Dictionary<String, Any> = EventUtils.prepareJSStreamEventData(stream);
465
+ let eventData: Dictionary<String, Any> = EventUtils.prepareStreamPropertyChangedEventData(changedProperty, oldValue: oldValue, newValue: newValue, stream: streamInfo);
466
+ self.emitEvent("\(stream.session.sessionId):\(EventUtils.sessionPreface)streamPropertyChanged", data: eventData)
467
+ }
468
+
469
+ func dispatchErrorViaCallback(_ callback: RCTResponseSenderBlock, error: OTError) {
470
+ let errorInfo = EventUtils.prepareJSErrorEventData(error);
471
+ callback([errorInfo]);
472
+ }
473
+
474
+ func setStreamObservers(stream: OTStream, isPublisherStream: Bool) {
475
+ let hasVideoObservation: NSKeyValueObservation = stream.observe(\.hasVideo, options: [.old, .new]) { object, change in
476
+ guard let oldValue = change.oldValue else { return }
477
+ guard let newValue = change.newValue else { return }
478
+ self.checkAndEmitStreamPropertyChangeEvent(stream.streamId, changedProperty: "hasVideo", oldValue: oldValue, newValue: newValue, isPublisherStream: isPublisherStream)
479
+ }
480
+ let hasAudioObservation: NSKeyValueObservation = stream.observe(\.hasAudio, options: [.old, .new]) { object, change in
481
+ guard let oldValue = change.oldValue else { return }
482
+ guard let newValue = change.newValue else { return }
483
+ self.checkAndEmitStreamPropertyChangeEvent(stream.streamId, changedProperty: "hasAudio", oldValue: oldValue, newValue: newValue, isPublisherStream: isPublisherStream)
484
+ }
485
+ let videoDimensionsObservation: NSKeyValueObservation = stream.observe(\.videoDimensions, options: [.old, .new]) { object, change in
486
+ guard let oldValue = change.oldValue else { return }
487
+ guard let newValue = change.newValue else { return }
488
+ self.checkAndEmitStreamPropertyChangeEvent(stream.streamId, changedProperty: "videoDimensions", oldValue: oldValue, newValue: newValue, isPublisherStream: isPublisherStream)
489
+ }
490
+ let videoTypeObservation: NSKeyValueObservation = stream.observe(\.videoType, options: [.old, .new]) { object, change in
491
+ guard let oldValue = change.oldValue else { return }
492
+ guard let newValue = change.newValue else { return }
493
+ self.checkAndEmitStreamPropertyChangeEvent(stream.streamId, changedProperty: "videoType", oldValue: oldValue, newValue: newValue, isPublisherStream: isPublisherStream)
494
+ }
495
+ OTRN.sharedState.streamObservers.updateValue([hasAudioObservation, hasVideoObservation, videoDimensionsObservation, videoTypeObservation], forKey: stream.streamId)
496
+ }
497
+
498
+ func printLogs(_ message: String) {
499
+ if (logLevel) {
500
+ print(message)
501
+ }
502
+ }
503
+ }
504
+
505
+ extension OTSessionManager: OTSessionDelegate {
506
+ func sessionDidConnect(_ session: OTSession) {
507
+ guard let callback = OTRN.sharedState.sessionConnectCallbacks[session.sessionId] else { return }
508
+ callback([NSNull()])
509
+ let sessionInfo = EventUtils.prepareJSSessionEventData(session);
510
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)sessionDidConnect", data: sessionInfo);
511
+ printLogs("OTRN: Session connected")
512
+ }
513
+
514
+ func sessionDidDisconnect(_ session: OTSession) {
515
+ let sessionInfo = EventUtils.prepareJSSessionEventData(session);
516
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)sessionDidDisconnect", data: sessionInfo);
517
+ guard let callback = OTRN.sharedState.sessionDisconnectCallbacks[session.sessionId] else { return }
518
+ callback([NSNull()]);
519
+ session.delegate = nil;
520
+ OTRN.sharedState.sessions.removeValue(forKey: session.sessionId);
521
+ OTRN.sharedState.sessionDisconnectCallbacks.removeValue(forKey: session.sessionId);
522
+ OTRN.sharedState.sessionConnectCallbacks.removeValue(forKey: session.sessionId);
523
+ printLogs("OTRN: Session disconnected")
524
+ }
525
+
526
+ func session(_ session: OTSession, connectionCreated connection: OTConnection) {
527
+ OTRN.sharedState.connections.updateValue(connection, forKey: connection.connectionId)
528
+ var connectionInfo = EventUtils.prepareJSConnectionEventData(connection);
529
+ connectionInfo["sessionId"] = session.sessionId;
530
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)connectionCreated", data: connectionInfo)
531
+ printLogs("OTRN Session: A connection was created \(connection.connectionId)")
532
+ }
533
+ func session(_ session: OTSession, connectionDestroyed connection: OTConnection) {
534
+ OTRN.sharedState.connections.removeValue(forKey: connection.connectionId)
535
+ var connectionInfo = EventUtils.prepareJSConnectionEventData(connection);
536
+ connectionInfo["sessionId"] = session.sessionId;
537
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)connectionDestroyed", data: connectionInfo)
538
+ printLogs("OTRN Session: A connection was destroyed")
539
+ }
540
+
541
+ func session(_ session: OTSession, archiveStartedWithId archiveId: String, name: String?) {
542
+ var archiveInfo: Dictionary<String, String> = [:];
543
+ archiveInfo["archiveId"] = archiveId;
544
+ archiveInfo["name"] = name;
545
+ archiveInfo["sessionId"] = session.sessionId;
546
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)archiveStartedWithId", data: archiveInfo)
547
+ printLogs("OTRN Session: Archive started with \(archiveId)")
548
+ }
549
+
550
+ func session(_ session: OTSession, archiveStoppedWithId archiveId: String) {
551
+ var archiveInfo: Dictionary<String, String> = [:];
552
+ archiveInfo["archiveId"] = archiveId;
553
+ archiveInfo["name"] = "";
554
+ archiveInfo["sessionId"] = session.sessionId;
555
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)archiveStoppedWithId", data: archiveInfo);
556
+ printLogs("OTRN Session: Archive stopped with \(archiveId)")
557
+ }
558
+
559
+ func sessionDidBeginReconnecting(_ session: OTSession) {
560
+ let sessionInfo = EventUtils.prepareJSSessionEventData(session);
561
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)sessionDidBeginReconnecting", data: sessionInfo)
562
+ printLogs("OTRN Session: Session did begin reconnecting")
563
+ }
564
+
565
+ func sessionDidReconnect(_ session: OTSession) {
566
+ let sessionInfo = EventUtils.prepareJSSessionEventData(session);
567
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)sessionDidReconnect", data: sessionInfo)
568
+ printLogs("OTRN Session: Session reconnected")
569
+ }
570
+
571
+ func session(_ session: OTSession, streamCreated stream: OTStream) {
572
+ OTRN.sharedState.subscriberStreams.updateValue(stream, forKey: stream.streamId)
573
+ let streamInfo: Dictionary<String, Any> = EventUtils.prepareJSStreamEventData(stream)
574
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)streamCreated", data: streamInfo)
575
+ setStreamObservers(stream: stream, isPublisherStream: false)
576
+ printLogs("OTRN: Session streamCreated \(stream.streamId)")
577
+ }
578
+
579
+ func session(_ session: OTSession, streamDestroyed stream: OTStream) {
580
+ let streamInfo: Dictionary<String, Any> = EventUtils.prepareJSStreamEventData(stream);
581
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)streamDestroyed", data: streamInfo)
582
+ printLogs("OTRN: Session streamDestroyed: \(stream.streamId)")
583
+ }
584
+
585
+ func session(_ session: OTSession, didFailWithError error: OTError) {
586
+ let errorInfo: Dictionary<String, Any> = EventUtils.prepareJSErrorEventData(error);
587
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)didFailWithError", data: errorInfo)
588
+ printLogs("OTRN: Session Failed to connect: \(error.localizedDescription)")
589
+ }
590
+
591
+ func session(_ session: OTSession, receivedSignalType type: String?, from connection: OTConnection?, with string: String?) {
592
+ var signalData: Dictionary<String, Any> = [:];
593
+ signalData["type"] = type;
594
+ signalData["data"] = string;
595
+ signalData["connectionId"] = connection?.connectionId;
596
+ signalData["sessionId"] = session.sessionId;
597
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)signal", data: signalData)
598
+ printLogs("OTRN: Session signal received")
599
+ }
600
+
601
+ func session(_ session: OTSession, info muteForced: OTMuteForcedInfo) {
602
+ var muteForcedInfo: Dictionary<String, Any> = [:];
603
+ muteForcedInfo["active"] = muteForced.active;
604
+ self.emitEvent("\(session.sessionId):\(EventUtils.sessionPreface)muteFoced", data: muteForcedInfo)
605
+ printLogs("OTRN Session: Session muteForced - active: \(muteForced.active)")
606
+ }
607
+ }
608
+
609
+ extension OTSessionManager: OTPublisherDelegate {
610
+ func publisher(_ publisher: OTPublisherKit, streamCreated stream: OTStream) {
611
+ OTRN.sharedState.publisherStreams.updateValue(stream, forKey: stream.streamId)
612
+ OTRN.sharedState.subscriberStreams.updateValue(stream, forKey: stream.streamId)
613
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
614
+ if (publisherId.count > 0) {
615
+ OTRN.sharedState.isPublishing[publisherId] = true;
616
+ let streamInfo: Dictionary<String, Any> = EventUtils.prepareJSStreamEventData(stream);
617
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)streamCreated", data: streamInfo);
618
+ setStreamObservers(stream: stream, isPublisherStream: true)
619
+ }
620
+ printLogs("OTRN: Publisher Stream created")
621
+ }
622
+
623
+ func publisher(_ publisher: OTPublisherKit, streamDestroyed stream: OTStream) {
624
+ OTRN.sharedState.streamObservers.removeValue(forKey: stream.streamId)
625
+ OTRN.sharedState.publisherStreams.removeValue(forKey: stream.streamId)
626
+ OTRN.sharedState.subscriberStreams.removeValue(forKey: stream.streamId)
627
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
628
+ OTRN.sharedState.isPublishing[publisherId] = false;
629
+ if (publisherId.count > 0) {
630
+ OTRN.sharedState.isPublishing[publisherId] = false;
631
+ let streamInfo: Dictionary<String, Any> = EventUtils.prepareJSStreamEventData(stream);
632
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)streamDestroyed", data: streamInfo);
633
+ }
634
+ OTRN.sharedState.publishers[publisherId] = nil;
635
+ OTRN.sharedState.isPublishing[publisherId] = nil;
636
+ guard let callback = OTRN.sharedState.publisherDestroyedCallbacks[publisherId] else {
637
+ printLogs("OTRN: Publisher Stream destroyed")
638
+ return
639
+ };
640
+ callback([NSNull()]);
641
+ printLogs("OTRN: Publisher Stream destroyed")
642
+ }
643
+
644
+ func publisher(_ publisher: OTPublisherKit, didFailWithError error: OTError) {
645
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
646
+ if (publisherId.count > 0) {
647
+ let errorInfo: Dictionary<String, Any> = EventUtils.prepareJSErrorEventData(error);
648
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)didFailWithError", data: errorInfo)
649
+ }
650
+ printLogs("OTRN: Publisher failed: \(error.localizedDescription)")
651
+ }
652
+
653
+ func muteForced(_ publisher: OTPublisherKit) {
654
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
655
+ if (publisherId.count > 0) {
656
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)muteForced", data: [NSNull()]);
657
+ }
658
+ printLogs("OTRN: Publisher mute forced")
659
+ }
660
+ }
661
+
662
+ extension OTSessionManager: OTPublisherKitAudioLevelDelegate {
663
+ func publisher(_ publisher: OTPublisherKit, audioLevelUpdated audioLevel: Float) {
664
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
665
+ if (publisherId.count > 0) {
666
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)audioLevelUpdated", data: audioLevel)
667
+ }
668
+ }
669
+ }
670
+
671
+ extension OTSessionManager: OTPublisherKitRtcStatsReportDelegate {
672
+ func publisher(_ publisher: OTPublisherKit, rtcStatsReport stats: [OTPublisherRtcStats]) {
673
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
674
+ if (publisherId.count > 0) {
675
+ let statsArray: [Dictionary<String, Any>] = EventUtils.preparePublisherRtcStats(stats);
676
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)rtcStatsReport", data: statsArray)
677
+ }
678
+ }
679
+ }
680
+
681
+ extension OTSessionManager: OTPublisherKitNetworkStatsDelegate {
682
+ func publisher(_ publisher: OTPublisherKit, audioNetworkStatsUpdated stats: [OTPublisherKitAudioNetworkStats]) {
683
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
684
+ if (publisherId.count > 0) {
685
+ let statsArray: [Dictionary<String, Any>] = EventUtils.preparePublisherAudioNetworkStats(stats);
686
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)audioNetworkStats", data: statsArray)
687
+ }
688
+ }
689
+
690
+ func publisher(_ publisher: OTPublisherKit, videoNetworkStatsUpdated stats: [OTPublisherKitVideoNetworkStats]) {
691
+ let publisherId = Utils.getPublisherId(publisher as! OTPublisher);
692
+ if (publisherId.count > 0) {
693
+ let statsArray: [Dictionary<String, Any>] = EventUtils.preparePublisherVideoNetworkStats(stats);
694
+ self.emitEvent("\(publisherId):\(EventUtils.publisherPreface)videoNetworkStats", data: statsArray)
695
+ }
696
+ }
697
+ }
698
+
699
+ extension OTSessionManager: OTSubscriberDelegate {
700
+ func subscriberDidConnect(toStream subscriberKit: OTSubscriberKit) {
701
+ if let stream = subscriberKit.stream {
702
+ let streamInfo: Dictionary<String, Any> = EventUtils.prepareJSStreamEventData(stream);
703
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidConnect", data: streamInfo);
704
+ } else {
705
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidConnect", data: [NSNull()]);
706
+ }
707
+ printLogs("OTRN: Subscriber connected")
708
+ }
709
+
710
+ func subscriber(_ subscriber: OTSubscriberKit, didFailWithError error: OTError) {
711
+ var subscriberInfo: Dictionary<String, Any> = [:];
712
+ subscriberInfo["error"] = EventUtils.prepareJSErrorEventData(error);
713
+ guard let stream = subscriber.stream else {
714
+ self.emitEvent("\(EventUtils.subscriberPreface)didFailWithError", data: subscriberInfo)
715
+ return;
716
+ }
717
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
718
+ self.emitEvent("\(EventUtils.subscriberPreface)didFailWithError", data: subscriberInfo)
719
+ printLogs("OTRN: Subscriber failed: \(error.localizedDescription)")
720
+ }
721
+ }
722
+
723
+ extension OTSessionManager: OTSubscriberKitNetworkStatsDelegate {
724
+ func subscriber(_ subscriber: OTSubscriberKit, videoNetworkStatsUpdated stats: OTSubscriberKitVideoNetworkStats) {
725
+ var subscriberInfo: Dictionary<String, Any> = [:];
726
+ subscriberInfo["videoStats"] = EventUtils.prepareSubscriberVideoNetworkStatsEventData(stats);
727
+ guard let stream = subscriber.stream else {
728
+ self.emitEvent("\(EventUtils.subscriberPreface)videoNetworkStatsUpdated", data: subscriberInfo);
729
+ return;
730
+ }
731
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
732
+ self.emitEvent("\(EventUtils.subscriberPreface)videoNetworkStatsUpdated", data: subscriberInfo);
733
+ }
734
+
735
+ func subscriber(_ subscriber: OTSubscriberKit, audioNetworkStatsUpdated stats: OTSubscriberKitAudioNetworkStats) {
736
+ var subscriberInfo: Dictionary<String, Any> = [:];
737
+ subscriberInfo["audioStats"] = EventUtils.prepareSubscriberAudioNetworkStatsEventData(stats);
738
+ guard let stream = subscriber.stream else {
739
+ self.emitEvent("\(EventUtils.subscriberPreface)audioNetworkStatsUpdated", data: subscriberInfo);
740
+ return
741
+ }
742
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
743
+ self.emitEvent("\(EventUtils.subscriberPreface)audioNetworkStatsUpdated", data: subscriberInfo);
744
+ }
745
+
746
+ func subscriberVideoEnabled(_ subscriber: OTSubscriberKit, reason: OTSubscriberVideoEventReason) {
747
+ var subscriberInfo: Dictionary<String, Any> = [:];
748
+ subscriberInfo["reason"] = Utils.convertOTSubscriberVideoEventReasonToString(reason);
749
+ guard let stream = subscriber.stream else {
750
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoEnabled", data: subscriberInfo);
751
+ return;
752
+ }
753
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
754
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoEnabled", data: subscriberInfo);
755
+ printLogs("OTRN: subscriberVideoEnabled")
756
+ }
757
+
758
+ func subscriberVideoDisabled(_ subscriber: OTSubscriberKit, reason: OTSubscriberVideoEventReason) {
759
+ var subscriberInfo: Dictionary<String, Any> = [:];
760
+ subscriberInfo["reason"] = Utils.convertOTSubscriberVideoEventReasonToString(reason);
761
+ guard let stream = subscriber.stream else {
762
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDisabled", data: subscriberInfo);
763
+ return;
764
+ }
765
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
766
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDisabled", data: subscriberInfo);
767
+ printLogs("OTRN: subscriberVideoDisabled")
768
+ }
769
+
770
+ func subscriberVideoDisableWarning(_ subscriber: OTSubscriberKit) {
771
+ var subscriberInfo: Dictionary<String, Any> = [:];
772
+ guard let stream = subscriber.stream else {
773
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDisableWarning", data: subscriberInfo);
774
+ return;
775
+ }
776
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
777
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDisableWarning", data: subscriberInfo);
778
+ printLogs("OTRN: subscriberVideoDisableWarning")
779
+ }
780
+
781
+ func subscriberVideoDisableWarningLifted(_ subscriber: OTSubscriberKit) {
782
+ var subscriberInfo: Dictionary<String, Any> = [:];
783
+ guard let stream = subscriber.stream else {
784
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDisableWarningLifted", data: subscriberInfo);
785
+ return;
786
+ }
787
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
788
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDisableWarningLifted", data: subscriberInfo);
789
+ printLogs("OTRN: subscriberVideoDisableWarningLifted")
790
+ }
791
+
792
+ func subscriberVideoDataReceived(_ subscriber: OTSubscriber) {
793
+ var subscriberInfo: Dictionary<String, Any> = [:];
794
+ guard let stream = subscriber.stream else {
795
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDataReceived", data: subscriberInfo);
796
+ return
797
+ }
798
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
799
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberVideoDataReceived", data: subscriberInfo);
800
+ }
801
+
802
+ func subscriberDidReconnect(toStream subscriber: OTSubscriberKit) {
803
+ var subscriberInfo: Dictionary<String, Any> = [:];
804
+ guard let stream = subscriber.stream else {
805
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidReconnect", data: subscriberInfo);
806
+ printLogs("OTRN: subscriberDidReconnect")
807
+ return;
808
+ };
809
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
810
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidReconnect", data: subscriberInfo);
811
+ printLogs("OTRN: subscriberDidReconnect")
812
+ }
813
+
814
+ func subscriberDidDisconnect(fromStream subscriberKit: OTSubscriberKit) {
815
+ var subscriberInfo: Dictionary<String, Any> = [:];
816
+ guard let stream = subscriberKit.stream else {
817
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidDisconnect", data: subscriberInfo);
818
+ printLogs("OTRN: subscriberDidDisconnect")
819
+ return;
820
+ };
821
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
822
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidDisconnect", data: subscriberInfo);
823
+ printLogs("OTRN: Subscriber disconnected")
824
+ }
825
+
826
+ }
827
+
828
+ extension OTSessionManager: OTSubscriberKitAudioLevelDelegate {
829
+ func subscriber(_ subscriber: OTSubscriberKit, audioLevelUpdated audioLevel: Float) {
830
+ var subscriberInfo: Dictionary<String, Any> = [:];
831
+ subscriberInfo["audioLevel"] = audioLevel;
832
+ guard let stream = subscriber.stream else {
833
+ self.emitEvent("\(EventUtils.subscriberPreface)audioLevelUpdated", data: subscriberInfo);
834
+ return;
835
+ }
836
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
837
+ self.emitEvent("\(EventUtils.subscriberPreface)audioLevelUpdated", data: subscriberInfo);
838
+ }
839
+ }
840
+
841
+ extension OTSessionManager: OTSubscriberKitRtcStatsReportDelegate {
842
+ func subscriber(_ subscriber: OTSubscriberKit, rtcStatsReport stats: String) {
843
+ var subscriberInfo: Dictionary<String, Any> = [:];
844
+ subscriberInfo["jsonArrayOfReports"] = stats;
845
+ guard let stream = subscriber.stream else {
846
+ self.emitEvent("\(EventUtils.subscriberPreface)rtcStatsReport", data: subscriberInfo);
847
+ return;
848
+ }
849
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
850
+ self.emitEvent("\(EventUtils.subscriberPreface)rtcStatsReport", data: subscriberInfo)
851
+ }
852
+ }
853
+
854
+ extension OTSessionManager: OTSubscriberKitCaptionsDelegate {
855
+ func subscriber(_ subscriber: OTSubscriberKit, caption text: String, isFinal isFinal: Bool) {
856
+ var subscriberInfo: Dictionary<String, Any> = [:];
857
+ subscriberInfo["text"] = text;
858
+ subscriberInfo["isFinal"] = isFinal;
859
+ guard let stream = subscriber.stream else {
860
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidConnect", data: subscriberInfo);
861
+ return;
862
+ }
863
+ subscriberInfo["stream"] = EventUtils.prepareJSStreamEventData(stream);
864
+ self.emitEvent("\(EventUtils.subscriberPreface)subscriberDidConnect", data: subscriberInfo);
865
+ }
866
+ }