@fishjam-cloud/react-native-client 0.24.0 → 0.25.0-rc.1
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.
- package/README.md +56 -15
- package/dist/index.d.ts +13 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +19 -0
- package/dist/overrides/RTCPeerConnection.d.ts +8 -0
- package/dist/overrides/RTCPeerConnection.d.ts.map +1 -0
- package/dist/overrides/RTCPeerConnection.js +16 -0
- package/dist/overrides/RTCView.d.ts +11 -0
- package/dist/overrides/RTCView.d.ts.map +1 -0
- package/dist/overrides/RTCView.js +21 -0
- package/dist/polyfills/local-storage.d.ts +10 -0
- package/dist/polyfills/local-storage.d.ts.map +1 -0
- package/dist/polyfills/local-storage.js +24 -0
- package/{build/hooks → dist}/useForegroundService.d.ts +10 -10
- package/dist/useForegroundService.d.ts.map +1 -0
- package/dist/useForegroundService.js +10 -0
- package/dist/webrtc-polyfill.d.ts +2 -0
- package/dist/webrtc-polyfill.d.ts.map +1 -0
- package/dist/webrtc-polyfill.js +14 -0
- package/package.json +44 -92
- package/plugin/broadcastExtensionFiles/Atomic.swift +37 -0
- package/plugin/broadcastExtensionFiles/DarwinNotificationCenter.swift +29 -0
- package/plugin/broadcastExtensionFiles/Info.plist +1 -1
- package/plugin/broadcastExtensionFiles/SampleHandler.swift +104 -0
- package/plugin/broadcastExtensionFiles/SampleUploader.swift +146 -0
- package/plugin/broadcastExtensionFiles/SocketConnection.swift +198 -0
- package/plugin/build/types.d.ts +5 -4
- package/plugin/build/withFishjam.d.ts +31 -2
- package/plugin/build/withFishjam.js +31 -5
- package/plugin/build/withFishjamAndroid.d.ts +2 -2
- package/plugin/build/withFishjamAndroid.js +48 -40
- package/plugin/build/withFishjamIos.d.ts +3 -8
- package/plugin/build/withFishjamIos.js +52 -72
- package/plugin/src/types.ts +19 -0
- package/plugin/src/withFishjam.ts +42 -0
- package/plugin/src/withFishjamAndroid.ts +112 -0
- package/plugin/src/withFishjamIos.ts +336 -0
- package/plugin/tsconfig.json +9 -0
- package/plugin/tsconfig.tsbuildinfo +1 -0
- package/LICENSE.txt +0 -201
- package/android/build.gradle +0 -95
- package/android/src/main/AndroidManifest.xml +0 -2
- package/android/src/main/java/io/fishjam/reactnative/AudioDeviceKind.kt +0 -34
- package/android/src/main/java/io/fishjam/reactnative/AudioSwitchManager.kt +0 -61
- package/android/src/main/java/io/fishjam/reactnative/EmitableEvents.kt +0 -126
- package/android/src/main/java/io/fishjam/reactnative/Errors.kt +0 -31
- package/android/src/main/java/io/fishjam/reactnative/PipContainerView.kt +0 -282
- package/android/src/main/java/io/fishjam/reactnative/PipContainerViewModule.kt +0 -41
- package/android/src/main/java/io/fishjam/reactnative/PipTrackSelector.kt +0 -98
- package/android/src/main/java/io/fishjam/reactnative/PipViewFactory.kt +0 -186
- package/android/src/main/java/io/fishjam/reactnative/RNFishjamClient.kt +0 -1001
- package/android/src/main/java/io/fishjam/reactnative/RNFishjamClientModule.kt +0 -358
- package/android/src/main/java/io/fishjam/reactnative/Utils.kt +0 -11
- package/android/src/main/java/io/fishjam/reactnative/VideoPreviewView.kt +0 -40
- package/android/src/main/java/io/fishjam/reactnative/VideoPreviewViewModule.kt +0 -22
- package/android/src/main/java/io/fishjam/reactnative/VideoRendererView.kt +0 -76
- package/android/src/main/java/io/fishjam/reactnative/VideoRendererViewModule.kt +0 -33
- package/android/src/main/java/io/fishjam/reactnative/VideoView.kt +0 -257
- package/android/src/main/java/io/fishjam/reactnative/extensions/CaptureDevice.kt +0 -17
- package/android/src/main/java/io/fishjam/reactnative/foregroundService/FishjamForegroundService.kt +0 -101
- package/android/src/main/java/io/fishjam/reactnative/foregroundService/ForegroundServiceManager.kt +0 -118
- package/android/src/main/java/io/fishjam/reactnative/foregroundService/ForegroundServiceState.kt +0 -46
- package/android/src/main/java/io/fishjam/reactnative/helpers/PictureInPictureHelperFragment.kt +0 -20
- package/android/src/main/java/io/fishjam/reactnative/managers/ListenerManager.kt +0 -24
- package/android/src/main/java/io/fishjam/reactnative/managers/LocalCameraTracksChangedListenersManager.kt +0 -8
- package/android/src/main/java/io/fishjam/reactnative/managers/LocalTracksSwitchListenersManager.kt +0 -17
- package/android/src/main/java/io/fishjam/reactnative/managers/TracksUpdateListenersManager.kt +0 -7
- package/android/src/main/java/io/fishjam/reactnative/utils/PermissionUtils.kt +0 -45
- package/build/RNFishjamClientModule.d.ts +0 -106
- package/build/RNFishjamClientModule.d.ts.map +0 -1
- package/build/RNFishjamClientModule.js +0 -21
- package/build/RNFishjamClientModule.js.map +0 -1
- package/build/common/metadata.d.ts +0 -9
- package/build/common/metadata.d.ts.map +0 -1
- package/build/common/metadata.js +0 -11
- package/build/common/metadata.js.map +0 -1
- package/build/components/FishjamRoom/GridTrackItem.d.ts +0 -12
- package/build/components/FishjamRoom/GridTrackItem.d.ts.map +0 -1
- package/build/components/FishjamRoom/GridTrackItem.js +0 -56
- package/build/components/FishjamRoom/GridTrackItem.js.map +0 -1
- package/build/components/FishjamRoom/VideosGrid.d.ts +0 -3
- package/build/components/FishjamRoom/VideosGrid.d.ts.map +0 -1
- package/build/components/FishjamRoom/VideosGrid.js +0 -20
- package/build/components/FishjamRoom/VideosGrid.js.map +0 -1
- package/build/components/FishjamRoom/index.d.ts +0 -33
- package/build/components/FishjamRoom/index.d.ts.map +0 -1
- package/build/components/FishjamRoom/index.js +0 -52
- package/build/components/FishjamRoom/index.js.map +0 -1
- package/build/components/FishjamRoom/parsePeersToTracks.d.ts +0 -4
- package/build/components/FishjamRoom/parsePeersToTracks.d.ts.map +0 -1
- package/build/components/FishjamRoom/parsePeersToTracks.js +0 -37
- package/build/components/FishjamRoom/parsePeersToTracks.js.map +0 -1
- package/build/components/PipContainerView.d.ts +0 -48
- package/build/components/PipContainerView.d.ts.map +0 -1
- package/build/components/PipContainerView.js +0 -34
- package/build/components/PipContainerView.js.map +0 -1
- package/build/components/VideoPreviewView.d.ts +0 -28
- package/build/components/VideoPreviewView.d.ts.map +0 -1
- package/build/components/VideoPreviewView.js +0 -17
- package/build/components/VideoPreviewView.js.map +0 -1
- package/build/components/VideoRendererView.d.ts +0 -39
- package/build/components/VideoRendererView.d.ts.map +0 -1
- package/build/components/VideoRendererView.js +0 -25
- package/build/components/VideoRendererView.js.map +0 -1
- package/build/consts/index.d.ts +0 -5
- package/build/consts/index.d.ts.map +0 -1
- package/build/consts/index.js +0 -8
- package/build/consts/index.js.map +0 -1
- package/build/debug/common/webRTC.d.ts +0 -9
- package/build/debug/common/webRTC.d.ts.map +0 -1
- package/build/debug/common/webRTC.js +0 -11
- package/build/debug/common/webRTC.js.map +0 -1
- package/build/debug/index.d.ts +0 -4
- package/build/debug/index.d.ts.map +0 -1
- package/build/debug/index.js +0 -3
- package/build/debug/index.js.map +0 -1
- package/build/debug/stats/types.d.ts +0 -55
- package/build/debug/stats/types.d.ts.map +0 -1
- package/build/debug/stats/types.js +0 -2
- package/build/debug/stats/types.js.map +0 -1
- package/build/debug/stats/useRTCStatistics.d.ts +0 -9
- package/build/debug/stats/useRTCStatistics.d.ts.map +0 -1
- package/build/debug/stats/useRTCStatistics.js +0 -79
- package/build/debug/stats/useRTCStatistics.js.map +0 -1
- package/build/hooks/internal/useFishjamEvent.d.ts +0 -4
- package/build/hooks/internal/useFishjamEvent.d.ts.map +0 -1
- package/build/hooks/internal/useFishjamEvent.js +0 -38
- package/build/hooks/internal/useFishjamEvent.js.map +0 -1
- package/build/hooks/internal/useFishjamEventState.d.ts +0 -3
- package/build/hooks/internal/useFishjamEventState.d.ts.map +0 -1
- package/build/hooks/internal/useFishjamEventState.js +0 -18
- package/build/hooks/internal/useFishjamEventState.js.map +0 -1
- package/build/hooks/useAppScreenShare.d.ts +0 -18
- package/build/hooks/useAppScreenShare.d.ts.map +0 -1
- package/build/hooks/useAppScreenShare.js +0 -46
- package/build/hooks/useAppScreenShare.js.map +0 -1
- package/build/hooks/useAudioSettings.d.ts +0 -49
- package/build/hooks/useAudioSettings.d.ts.map +0 -1
- package/build/hooks/useAudioSettings.js +0 -70
- package/build/hooks/useAudioSettings.js.map +0 -1
- package/build/hooks/useBandwidthEstimation.d.ts +0 -14
- package/build/hooks/useBandwidthEstimation.d.ts.map +0 -1
- package/build/hooks/useBandwidthEstimation.js +0 -19
- package/build/hooks/useBandwidthEstimation.js.map +0 -1
- package/build/hooks/useCallKit.d.ts +0 -121
- package/build/hooks/useCallKit.d.ts.map +0 -1
- package/build/hooks/useCallKit.js +0 -142
- package/build/hooks/useCallKit.js.map +0 -1
- package/build/hooks/useCamera.d.ts +0 -113
- package/build/hooks/useCamera.d.ts.map +0 -1
- package/build/hooks/useCamera.js +0 -93
- package/build/hooks/useCamera.js.map +0 -1
- package/build/hooks/useConnection.d.ts +0 -73
- package/build/hooks/useConnection.d.ts.map +0 -1
- package/build/hooks/useConnection.js +0 -46
- package/build/hooks/useConnection.js.map +0 -1
- package/build/hooks/useForegroundService.d.ts.map +0 -1
- package/build/hooks/useForegroundService.js +0 -66
- package/build/hooks/useForegroundService.js.map +0 -1
- package/build/hooks/useMicrophone.d.ts +0 -16
- package/build/hooks/useMicrophone.d.ts.map +0 -1
- package/build/hooks/useMicrophone.js +0 -31
- package/build/hooks/useMicrophone.js.map +0 -1
- package/build/hooks/usePeerStatus.d.ts +0 -10
- package/build/hooks/usePeerStatus.d.ts.map +0 -1
- package/build/hooks/usePeerStatus.js +0 -13
- package/build/hooks/usePeerStatus.js.map +0 -1
- package/build/hooks/usePeers.d.ts +0 -98
- package/build/hooks/usePeers.d.ts.map +0 -1
- package/build/hooks/usePeers.js +0 -81
- package/build/hooks/usePeers.js.map +0 -1
- package/build/hooks/usePermissions.d.ts +0 -24
- package/build/hooks/usePermissions.d.ts.map +0 -1
- package/build/hooks/usePermissions.js +0 -61
- package/build/hooks/usePermissions.js.map +0 -1
- package/build/hooks/useReconnection.d.ts +0 -11
- package/build/hooks/useReconnection.d.ts.map +0 -1
- package/build/hooks/useReconnection.js +0 -14
- package/build/hooks/useReconnection.js.map +0 -1
- package/build/hooks/useSandbox.d.ts +0 -20
- package/build/hooks/useSandbox.d.ts.map +0 -1
- package/build/hooks/useSandbox.js +0 -54
- package/build/hooks/useSandbox.js.map +0 -1
- package/build/hooks/useScreenShare.d.ts +0 -36
- package/build/hooks/useScreenShare.d.ts.map +0 -1
- package/build/hooks/useScreenShare.js +0 -45
- package/build/hooks/useScreenShare.js.map +0 -1
- package/build/hooks/useUpdatePeerMetadata.d.ts +0 -15
- package/build/hooks/useUpdatePeerMetadata.d.ts.map +0 -1
- package/build/hooks/useUpdatePeerMetadata.js +0 -21
- package/build/hooks/useUpdatePeerMetadata.js.map +0 -1
- package/build/index.d.ts +0 -36
- package/build/index.d.ts.map +0 -1
- package/build/index.js +0 -30
- package/build/index.js.map +0 -1
- package/build/livestream/components/LivestreamStreamer.d.ts +0 -24
- package/build/livestream/components/LivestreamStreamer.d.ts.map +0 -1
- package/build/livestream/components/LivestreamStreamer.js +0 -12
- package/build/livestream/components/LivestreamStreamer.js.map +0 -1
- package/build/livestream/components/LivestreamViewer.d.ts +0 -46
- package/build/livestream/components/LivestreamViewer.d.ts.map +0 -1
- package/build/livestream/components/LivestreamViewer.js +0 -10
- package/build/livestream/components/LivestreamViewer.js.map +0 -1
- package/build/livestream/hooks/useLivestreamScreenSharingStreamer.d.ts +0 -49
- package/build/livestream/hooks/useLivestreamScreenSharingStreamer.d.ts.map +0 -1
- package/build/livestream/hooks/useLivestreamScreenSharingStreamer.js +0 -58
- package/build/livestream/hooks/useLivestreamScreenSharingStreamer.js.map +0 -1
- package/build/livestream/hooks/useLivestreamStreamer.d.ts +0 -65
- package/build/livestream/hooks/useLivestreamStreamer.d.ts.map +0 -1
- package/build/livestream/hooks/useLivestreamStreamer.js +0 -71
- package/build/livestream/hooks/useLivestreamStreamer.js.map +0 -1
- package/build/livestream/hooks/useLivestreamViewer.d.ts +0 -36
- package/build/livestream/hooks/useLivestreamViewer.d.ts.map +0 -1
- package/build/livestream/hooks/useLivestreamViewer.js +0 -73
- package/build/livestream/hooks/useLivestreamViewer.js.map +0 -1
- package/build/livestream/index.d.ts +0 -12
- package/build/livestream/index.d.ts.map +0 -1
- package/build/livestream/index.js +0 -7
- package/build/livestream/index.js.map +0 -1
- package/build/protos/fishjam/peer_notifications.d.ts +0 -63
- package/build/protos/fishjam/peer_notifications.d.ts.map +0 -1
- package/build/protos/fishjam/peer_notifications.js +0 -235
- package/build/protos/fishjam/peer_notifications.js.map +0 -1
- package/build/types.d.ts +0 -34
- package/build/types.d.ts.map +0 -1
- package/build/types.js +0 -2
- package/build/types.js.map +0 -1
- package/build/utils/config.d.ts +0 -6
- package/build/utils/config.d.ts.map +0 -1
- package/build/utils/config.js +0 -10
- package/build/utils/config.js.map +0 -1
- package/build/utils/errorListener.d.ts +0 -2
- package/build/utils/errorListener.d.ts.map +0 -1
- package/build/utils/errorListener.js +0 -15
- package/build/utils/errorListener.js.map +0 -1
- package/build/utils/eventPayloadValidator.d.ts +0 -3
- package/build/utils/eventPayloadValidator.d.ts.map +0 -1
- package/build/utils/eventPayloadValidator.js +0 -86
- package/build/utils/eventPayloadValidator.js.map +0 -1
- package/build/utils/getFishjamUrl.d.ts +0 -2
- package/build/utils/getFishjamUrl.d.ts.map +0 -1
- package/build/utils/getFishjamUrl.js +0 -10
- package/build/utils/getFishjamUrl.js.map +0 -1
- package/debug/package.json +0 -4
- package/expo-module.config.json +0 -19
- package/ios/CameraPermissionsRequester.swift +0 -117
- package/ios/Events.swift +0 -152
- package/ios/PictureInPictureManager.swift +0 -215
- package/ios/PipContainerView.swift +0 -56
- package/ios/PipContainerViewModule.swift +0 -48
- package/ios/RNFishjamClient.podspec +0 -30
- package/ios/RNFishjamClient.swift +0 -995
- package/ios/RNFishjamClientModule.swift +0 -289
- package/ios/RNFishjamProxy.swift +0 -12
- package/ios/Utils/PermissionUtils.swift +0 -16
- package/ios/Utils.swift +0 -23
- package/ios/VideoPreviewView.swift +0 -54
- package/ios/VideoPreviewViewModule.swift +0 -21
- package/ios/VideoRendererView.swift +0 -98
- package/ios/VideoRendererViewModule.swift +0 -23
- package/ios/extensions/AVCaptureDevice.swift +0 -20
- package/ios/managers/LocalCameraTracksChangedListenersManager.swift +0 -23
- package/ios/managers/TracksUpdateListenersManager.swift +0 -21
- package/livestream/package.json +0 -4
- package/plugin/broadcastExtensionFiles/FishjamBroadcastSampleHandler.swift +0 -50
- /package/plugin/broadcastExtensionFiles/{FishjamScreenBroadcastExtension.entitlements → ScreenBroadcastExtension.entitlements} +0 -0
|
@@ -1,1001 +0,0 @@
|
|
|
1
|
-
package io.fishjam.reactnative
|
|
2
|
-
|
|
3
|
-
import android.app.Activity
|
|
4
|
-
import android.content.ActivityNotFoundException
|
|
5
|
-
import android.content.Intent
|
|
6
|
-
import android.media.projection.MediaProjectionManager
|
|
7
|
-
import android.util.Log
|
|
8
|
-
import androidx.appcompat.app.AppCompatActivity
|
|
9
|
-
import com.fishjamcloud.client.FishjamClient
|
|
10
|
-
import com.fishjamcloud.client.FishjamClientListener
|
|
11
|
-
import com.fishjamcloud.client.ReconnectionStatus
|
|
12
|
-
import com.fishjamcloud.client.media.CaptureDevice
|
|
13
|
-
import com.fishjamcloud.client.media.CaptureDeviceChangedListener
|
|
14
|
-
import com.fishjamcloud.client.media.LocalAudioTrack
|
|
15
|
-
import com.fishjamcloud.client.media.LocalScreenShareTrack
|
|
16
|
-
import com.fishjamcloud.client.media.LocalVideoTrack
|
|
17
|
-
import com.fishjamcloud.client.media.RemoteAudioTrack
|
|
18
|
-
import com.fishjamcloud.client.media.RemoteVideoTrack
|
|
19
|
-
import com.fishjamcloud.client.media.Track
|
|
20
|
-
import com.fishjamcloud.client.media.VideoTrack
|
|
21
|
-
import com.fishjamcloud.client.models.AuthError
|
|
22
|
-
import com.fishjamcloud.client.models.CustomSource
|
|
23
|
-
import com.fishjamcloud.client.models.Endpoint
|
|
24
|
-
import com.fishjamcloud.client.models.Metadata
|
|
25
|
-
import com.fishjamcloud.client.models.Peer
|
|
26
|
-
import com.fishjamcloud.client.models.RTCInboundStats
|
|
27
|
-
import com.fishjamcloud.client.models.RTCOutboundStats
|
|
28
|
-
import com.fishjamcloud.client.models.ReconnectConfig
|
|
29
|
-
import com.fishjamcloud.client.models.SimulcastConfig
|
|
30
|
-
import com.fishjamcloud.client.models.TrackBandwidthLimit
|
|
31
|
-
import com.fishjamcloud.client.models.TrackEncoding
|
|
32
|
-
import com.fishjamcloud.client.models.VideoParameters
|
|
33
|
-
import com.twilio.audioswitch.AudioDevice
|
|
34
|
-
import expo.modules.kotlin.AppContext
|
|
35
|
-
import expo.modules.kotlin.Promise
|
|
36
|
-
import expo.modules.kotlin.exception.CodedException
|
|
37
|
-
import fishjam.media_events.server.Server
|
|
38
|
-
import io.fishjam.reactnative.extensions.toLocalCamera
|
|
39
|
-
import io.fishjam.reactnative.foregroundService.ForegroundServiceManager
|
|
40
|
-
import io.fishjam.reactnative.managers.LocalCameraTracksChangedListenersManager
|
|
41
|
-
import io.fishjam.reactnative.managers.LocalTracksSwitchListenersManager
|
|
42
|
-
import io.fishjam.reactnative.managers.TracksUpdateListenersManager
|
|
43
|
-
import io.fishjam.reactnative.utils.PermissionUtils
|
|
44
|
-
import kotlinx.coroutines.CoroutineScope
|
|
45
|
-
import kotlinx.coroutines.Dispatchers
|
|
46
|
-
import kotlinx.coroutines.SupervisorJob
|
|
47
|
-
import kotlinx.coroutines.delay
|
|
48
|
-
import kotlinx.coroutines.launch
|
|
49
|
-
import org.webrtc.Logging
|
|
50
|
-
|
|
51
|
-
class RNFishjamClient(
|
|
52
|
-
private val sendEvent: (name: String, data: Map<String, Any?>) -> Unit
|
|
53
|
-
) : FishjamClientListener,
|
|
54
|
-
CaptureDeviceChangedListener {
|
|
55
|
-
private val SCREENSHARE_REQUEST = 1
|
|
56
|
-
|
|
57
|
-
var isMicrophoneOn = false
|
|
58
|
-
var isCameraOn = false
|
|
59
|
-
var isScreenShareOn = false
|
|
60
|
-
var isConnected = false
|
|
61
|
-
|
|
62
|
-
var isCameraInitialized = false
|
|
63
|
-
private set(value) {
|
|
64
|
-
field = value
|
|
65
|
-
emitEvent(
|
|
66
|
-
EmitableEvent.currentCameraChanged(
|
|
67
|
-
getCurrentCaptureDevice(),
|
|
68
|
-
isCameraOn,
|
|
69
|
-
value
|
|
70
|
-
)
|
|
71
|
-
)
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
private var connectPromise: Promise? = null
|
|
75
|
-
private set(value) {
|
|
76
|
-
field = value
|
|
77
|
-
if (value == null) {
|
|
78
|
-
return
|
|
79
|
-
}
|
|
80
|
-
coroutineScope.launch {
|
|
81
|
-
delay(15000)
|
|
82
|
-
// If promise is still assigned it means it was not resolved in that time,
|
|
83
|
-
// so close the client and reject it with timeout error
|
|
84
|
-
connectPromise?.let { promise ->
|
|
85
|
-
fishjamClient.leave {
|
|
86
|
-
promise.reject(SocketError("Failed to connect: Fishjam server is not responding"))
|
|
87
|
-
connectPromise = null
|
|
88
|
-
peerStatus = PeerStatus.Error
|
|
89
|
-
}
|
|
90
|
-
}
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
private var screenSharePermissionPromise: Promise? = null
|
|
94
|
-
|
|
95
|
-
var videoSimulcastConfig: SimulcastConfig = SimulcastConfig()
|
|
96
|
-
private var localUserMetadata: Metadata = mutableMapOf()
|
|
97
|
-
|
|
98
|
-
var screenShareQuality: String? = null
|
|
99
|
-
var screenShareSimulcastConfig: SimulcastConfig = SimulcastConfig()
|
|
100
|
-
|
|
101
|
-
var screenShareMetadata: Map<String, Any> = mutableMapOf()
|
|
102
|
-
|
|
103
|
-
private var mediaProjectionIntent: Intent? = null
|
|
104
|
-
|
|
105
|
-
var audioSwitchManager: AudioSwitchManager? = null
|
|
106
|
-
|
|
107
|
-
var appContext: AppContext? = null
|
|
108
|
-
|
|
109
|
-
var peerStatus = PeerStatus.Idle
|
|
110
|
-
private set(value) {
|
|
111
|
-
field = value
|
|
112
|
-
emitEvent(EmitableEvent.peerStatusChanged(value))
|
|
113
|
-
}
|
|
114
|
-
|
|
115
|
-
var reconnectionStatus = ReconnectionStatus.Idle
|
|
116
|
-
private set(value) {
|
|
117
|
-
field = value
|
|
118
|
-
emitEvent(EmitableEvent.reconnectionStatusChanged(value))
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
private val foregroundServiceManager by lazy {
|
|
122
|
-
ForegroundServiceManager(appContext ?: throw CodedException("appContext not found"))
|
|
123
|
-
}
|
|
124
|
-
|
|
125
|
-
companion object {
|
|
126
|
-
val trackUpdateListenersManager = TracksUpdateListenersManager()
|
|
127
|
-
|
|
128
|
-
val localTracksSwitchListenerManager = LocalTracksSwitchListenersManager()
|
|
129
|
-
|
|
130
|
-
val localCameraTracksChangedListenersManager = LocalCameraTracksChangedListenersManager()
|
|
131
|
-
|
|
132
|
-
lateinit var fishjamClient: FishjamClient
|
|
133
|
-
|
|
134
|
-
fun getAllPeers(): List<Peer> {
|
|
135
|
-
val listOfPeers = fishjamClient.getRemotePeers().toMutableList()
|
|
136
|
-
val localEndpoint = fishjamClient.getLocalEndpoint()
|
|
137
|
-
listOfPeers.add(localEndpoint)
|
|
138
|
-
return listOfPeers
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
private var eventEmitter: ((String, Map<String, Any?>) -> Unit)? = null
|
|
142
|
-
|
|
143
|
-
private fun setEventEmitter(emitter: ((String, Map<String, Any?>) -> Unit)?) {
|
|
144
|
-
if (emitter != null && eventEmitter != null) {
|
|
145
|
-
throw IllegalStateException("Event emitter already set.")
|
|
146
|
-
}
|
|
147
|
-
eventEmitter = emitter
|
|
148
|
-
}
|
|
149
|
-
|
|
150
|
-
fun sendEvent(event: EmitableEvent) {
|
|
151
|
-
if (eventEmitter == null) {
|
|
152
|
-
Log.e("RNFishjamClient", "Event emitter is not set.")
|
|
153
|
-
}
|
|
154
|
-
eventEmitter?.invoke(event.name, event.data)
|
|
155
|
-
}
|
|
156
|
-
|
|
157
|
-
suspend fun createCustomSource(customSource: CustomSource) = fishjamClient.createCustomSource(customSource)
|
|
158
|
-
|
|
159
|
-
suspend fun removeCustomSource(customSource: CustomSource) = fishjamClient.removeCustomSource(customSource)
|
|
160
|
-
}
|
|
161
|
-
|
|
162
|
-
fun onModuleCreate(appContext: AppContext) {
|
|
163
|
-
this.appContext = appContext
|
|
164
|
-
this.audioSwitchManager = AudioSwitchManager(appContext.reactContext!!)
|
|
165
|
-
setEventEmitter(sendEvent)
|
|
166
|
-
create()
|
|
167
|
-
}
|
|
168
|
-
|
|
169
|
-
fun onModuleDestroy() {
|
|
170
|
-
audioSwitchManager?.stop()
|
|
171
|
-
setEventEmitter(null)
|
|
172
|
-
}
|
|
173
|
-
|
|
174
|
-
private val coroutineScope: CoroutineScope =
|
|
175
|
-
CoroutineScope(SupervisorJob() + Dispatchers.Default)
|
|
176
|
-
|
|
177
|
-
fun onActivityResult(
|
|
178
|
-
requestCode: Int,
|
|
179
|
-
resultCode: Int,
|
|
180
|
-
data: Intent?
|
|
181
|
-
) {
|
|
182
|
-
coroutineScope.launch(Dispatchers.Main) {
|
|
183
|
-
if (requestCode != SCREENSHARE_REQUEST) return@launch
|
|
184
|
-
if (resultCode != Activity.RESULT_OK) {
|
|
185
|
-
screenSharePermissionPromise?.resolve("denied")
|
|
186
|
-
screenSharePermissionPromise = null
|
|
187
|
-
return@launch
|
|
188
|
-
}
|
|
189
|
-
|
|
190
|
-
mediaProjectionIntent = data
|
|
191
|
-
screenSharePermissionPromise?.resolve("granted")
|
|
192
|
-
screenSharePermissionPromise = null
|
|
193
|
-
}
|
|
194
|
-
}
|
|
195
|
-
|
|
196
|
-
private fun getSimulcastConfigFromOptions(simulcastConfigMap: io.fishjam.reactnative.SimulcastConfig): SimulcastConfig {
|
|
197
|
-
val simulcastEnabled = simulcastConfigMap.enabled
|
|
198
|
-
val activeEncodings = listOf(TrackEncoding.L, TrackEncoding.M, TrackEncoding.H)
|
|
199
|
-
return SimulcastConfig(
|
|
200
|
-
enabled = simulcastEnabled,
|
|
201
|
-
activeEncodings = activeEncodings
|
|
202
|
-
)
|
|
203
|
-
}
|
|
204
|
-
|
|
205
|
-
private fun create() {
|
|
206
|
-
audioSwitchManager = AudioSwitchManager(appContext?.reactContext!!)
|
|
207
|
-
fishjamClient =
|
|
208
|
-
FishjamClient(
|
|
209
|
-
appContext = appContext?.reactContext!!,
|
|
210
|
-
listener = this
|
|
211
|
-
)
|
|
212
|
-
}
|
|
213
|
-
|
|
214
|
-
private fun getVideoParametersFromOptions(createOptions: CameraConfig): VideoParameters {
|
|
215
|
-
var videoParameters =
|
|
216
|
-
when (createOptions.quality) {
|
|
217
|
-
"QVGA169" -> VideoParameters.presetQVGA169
|
|
218
|
-
"VGA169" -> VideoParameters.presetVGA169
|
|
219
|
-
"QHD169" -> VideoParameters.presetQHD169
|
|
220
|
-
"HD169" -> VideoParameters.presetHD169
|
|
221
|
-
"FHD169" -> VideoParameters.presetFHD169
|
|
222
|
-
"QVGA43" -> VideoParameters.presetQVGA43
|
|
223
|
-
"VGA43" -> VideoParameters.presetVGA43
|
|
224
|
-
"QHD43" -> VideoParameters.presetQHD43
|
|
225
|
-
"HD43" -> VideoParameters.presetHD43
|
|
226
|
-
"FHD43" -> VideoParameters.presetFHD43
|
|
227
|
-
else -> VideoParameters.presetVGA169
|
|
228
|
-
}
|
|
229
|
-
videoParameters =
|
|
230
|
-
videoParameters.copy(
|
|
231
|
-
dimensions = if (createOptions.flipDimensions) videoParameters.dimensions.flip() else videoParameters.dimensions,
|
|
232
|
-
simulcastConfig = getSimulcastConfigFromOptions(createOptions.simulcastConfig),
|
|
233
|
-
maxBitrate = videoParameters.maxBitrate
|
|
234
|
-
)
|
|
235
|
-
return videoParameters
|
|
236
|
-
}
|
|
237
|
-
|
|
238
|
-
private fun getLocalVideoTrack(): LocalVideoTrack? =
|
|
239
|
-
fishjamClient
|
|
240
|
-
.getLocalEndpoint()
|
|
241
|
-
.tracks
|
|
242
|
-
.values
|
|
243
|
-
.filterIsInstance<LocalVideoTrack>()
|
|
244
|
-
.firstOrNull()
|
|
245
|
-
|
|
246
|
-
private fun getLocalAudioTrack(): LocalAudioTrack? =
|
|
247
|
-
fishjamClient
|
|
248
|
-
.getLocalEndpoint()
|
|
249
|
-
.tracks
|
|
250
|
-
.values
|
|
251
|
-
.filterIsInstance<LocalAudioTrack>()
|
|
252
|
-
.firstOrNull()
|
|
253
|
-
|
|
254
|
-
private fun getLocalScreenShareTrack(): LocalScreenShareTrack? =
|
|
255
|
-
fishjamClient
|
|
256
|
-
.getLocalEndpoint()
|
|
257
|
-
.tracks
|
|
258
|
-
.values
|
|
259
|
-
.filterIsInstance<LocalScreenShareTrack>()
|
|
260
|
-
.firstOrNull()
|
|
261
|
-
|
|
262
|
-
private fun ensureConnected() {
|
|
263
|
-
if (!isConnected) {
|
|
264
|
-
throw ClientNotConnectedError()
|
|
265
|
-
}
|
|
266
|
-
}
|
|
267
|
-
|
|
268
|
-
private fun ensureVideoTrack() {
|
|
269
|
-
if (getLocalVideoTrack() == null) {
|
|
270
|
-
throw NoLocalVideoTrackError()
|
|
271
|
-
}
|
|
272
|
-
}
|
|
273
|
-
|
|
274
|
-
private fun ensureAudioTrack() {
|
|
275
|
-
if (getLocalAudioTrack() == null) {
|
|
276
|
-
throw NoLocalAudioTrackError()
|
|
277
|
-
}
|
|
278
|
-
}
|
|
279
|
-
|
|
280
|
-
private fun ensureScreenShareTrack() {
|
|
281
|
-
if (getLocalScreenShareTrack() == null) {
|
|
282
|
-
throw NoScreenShareTrackError()
|
|
283
|
-
}
|
|
284
|
-
}
|
|
285
|
-
|
|
286
|
-
override fun onAuthError(reason: AuthError) {
|
|
287
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
288
|
-
connectPromise?.reject(ConnectionError(reason))
|
|
289
|
-
connectPromise = null
|
|
290
|
-
peerStatus = PeerStatus.Error
|
|
291
|
-
}
|
|
292
|
-
}
|
|
293
|
-
|
|
294
|
-
fun joinRoom(
|
|
295
|
-
url: String,
|
|
296
|
-
peerToken: String,
|
|
297
|
-
peerMetadata: Map<String, Any>,
|
|
298
|
-
config: ConnectConfig,
|
|
299
|
-
promise: Promise
|
|
300
|
-
) {
|
|
301
|
-
if (connectPromise != null || peerStatus == PeerStatus.Connected) {
|
|
302
|
-
promise.reject(JoinError("Room already joined or it's connecting. You must call leaveRoom() before calling joinRoom() again."))
|
|
303
|
-
return
|
|
304
|
-
}
|
|
305
|
-
|
|
306
|
-
peerStatus = PeerStatus.Connecting
|
|
307
|
-
connectPromise = promise
|
|
308
|
-
localUserMetadata = mapOf("server" to emptyMap(), "peer" to peerMetadata)
|
|
309
|
-
fishjamClient.connect(
|
|
310
|
-
com.fishjamcloud.client.ConnectConfig(
|
|
311
|
-
url,
|
|
312
|
-
peerToken,
|
|
313
|
-
peerMetadata,
|
|
314
|
-
ReconnectConfig(
|
|
315
|
-
config.reconnectConfig.maxAttempts,
|
|
316
|
-
config.reconnectConfig.initialDelayMs,
|
|
317
|
-
config.reconnectConfig.delayMs
|
|
318
|
-
)
|
|
319
|
-
)
|
|
320
|
-
)
|
|
321
|
-
}
|
|
322
|
-
|
|
323
|
-
fun leaveRoom() {
|
|
324
|
-
connectPromise?.reject(JoinError("leaveRoom called before connected"))
|
|
325
|
-
connectPromise = null
|
|
326
|
-
|
|
327
|
-
if (isScreenShareOn) {
|
|
328
|
-
stopScreenShare()
|
|
329
|
-
}
|
|
330
|
-
isMicrophoneOn = false
|
|
331
|
-
isCameraOn = false
|
|
332
|
-
isScreenShareOn = false
|
|
333
|
-
isConnected = false
|
|
334
|
-
isCameraInitialized = false
|
|
335
|
-
fishjamClient.leave {
|
|
336
|
-
emitEndpoints()
|
|
337
|
-
}
|
|
338
|
-
}
|
|
339
|
-
|
|
340
|
-
suspend fun startCamera(config: CameraConfig): Boolean {
|
|
341
|
-
if (isCameraInitialized) {
|
|
342
|
-
return true
|
|
343
|
-
}
|
|
344
|
-
if (!PermissionUtils.requestCameraPermission(appContext)) {
|
|
345
|
-
emitEvent(EmitableEvent.warning("Camera permission not granted."))
|
|
346
|
-
return false
|
|
347
|
-
}
|
|
348
|
-
|
|
349
|
-
val cameraTrack = createCameraTrack(config)
|
|
350
|
-
cameraTrack.captureDeviceChangedListener = this
|
|
351
|
-
setCameraTrackState(cameraTrack, config.cameraEnabled)
|
|
352
|
-
emitEndpoints()
|
|
353
|
-
isCameraInitialized = true
|
|
354
|
-
return true
|
|
355
|
-
}
|
|
356
|
-
|
|
357
|
-
private suspend fun createCameraTrack(config: CameraConfig): LocalVideoTrack {
|
|
358
|
-
val videoParameters = getVideoParametersFromOptions(config)
|
|
359
|
-
videoSimulcastConfig = getSimulcastConfigFromOptions(config.simulcastConfig)
|
|
360
|
-
return fishjamClient.createVideoTrack(
|
|
361
|
-
videoParameters,
|
|
362
|
-
config.videoTrackMetadata,
|
|
363
|
-
config.cameraId
|
|
364
|
-
)
|
|
365
|
-
}
|
|
366
|
-
|
|
367
|
-
private fun setCameraTrackState(
|
|
368
|
-
cameraTrack: LocalVideoTrack,
|
|
369
|
-
isEnabled: Boolean
|
|
370
|
-
) {
|
|
371
|
-
cameraTrack.setEnabled(isEnabled)
|
|
372
|
-
isCameraOn = isEnabled
|
|
373
|
-
emitEvent(
|
|
374
|
-
EmitableEvent.currentCameraChanged(
|
|
375
|
-
cameraTrack.getCaptureDevice()?.toLocalCamera(),
|
|
376
|
-
isEnabled,
|
|
377
|
-
isCameraInitialized
|
|
378
|
-
)
|
|
379
|
-
)
|
|
380
|
-
localCameraTracksChangedListenersManager.notifyListeners()
|
|
381
|
-
}
|
|
382
|
-
|
|
383
|
-
fun toggleCamera(): Boolean {
|
|
384
|
-
ensureVideoTrack()
|
|
385
|
-
getLocalVideoTrack()?.let { setCameraTrackState(it, !isCameraOn) }
|
|
386
|
-
return isCameraOn
|
|
387
|
-
}
|
|
388
|
-
|
|
389
|
-
suspend fun flipCamera() {
|
|
390
|
-
ensureVideoTrack()
|
|
391
|
-
localTracksSwitchListenerManager.notifyWillSwitch()
|
|
392
|
-
getLocalVideoTrack()?.flipCamera()
|
|
393
|
-
localTracksSwitchListenerManager.notifySwitched()
|
|
394
|
-
}
|
|
395
|
-
|
|
396
|
-
suspend fun switchCamera(cameraId: String) {
|
|
397
|
-
ensureVideoTrack()
|
|
398
|
-
localTracksSwitchListenerManager.notifyWillSwitch()
|
|
399
|
-
getLocalVideoTrack()?.switchCamera(cameraId)
|
|
400
|
-
localTracksSwitchListenerManager.notifySwitched()
|
|
401
|
-
}
|
|
402
|
-
|
|
403
|
-
suspend fun startMicrophone() {
|
|
404
|
-
// If microphone track already exist, just enable it
|
|
405
|
-
if (getLocalAudioTrack() != null) {
|
|
406
|
-
getLocalAudioTrack()?.let { setMicrophoneTrackState(it, true) }
|
|
407
|
-
} else {
|
|
408
|
-
if (!PermissionUtils.requestMicrophonePermission(appContext)) {
|
|
409
|
-
emitEvent(EmitableEvent.warning("Microphone permission not granted."))
|
|
410
|
-
return
|
|
411
|
-
}
|
|
412
|
-
|
|
413
|
-
val microphoneTrack = fishjamClient.createAudioTrack(getMicrophoneTrackMetadata(true))
|
|
414
|
-
setMicrophoneTrackState(microphoneTrack, true)
|
|
415
|
-
emitEndpoints()
|
|
416
|
-
}
|
|
417
|
-
}
|
|
418
|
-
|
|
419
|
-
fun stopMicrophone() {
|
|
420
|
-
if (getLocalAudioTrack() != null) {
|
|
421
|
-
getLocalAudioTrack()?.let { setMicrophoneTrackState(it, false) }
|
|
422
|
-
}
|
|
423
|
-
}
|
|
424
|
-
|
|
425
|
-
private fun setMicrophoneTrackState(
|
|
426
|
-
microphoneTrack: LocalAudioTrack,
|
|
427
|
-
isEnabled: Boolean
|
|
428
|
-
) {
|
|
429
|
-
microphoneTrack.setEnabled(isEnabled)
|
|
430
|
-
isMicrophoneOn = isEnabled
|
|
431
|
-
updateLocalAudioTrackMetadata(getMicrophoneTrackMetadata(isEnabled))
|
|
432
|
-
emitEvent(EmitableEvent.isMicrophoneOn(isEnabled))
|
|
433
|
-
}
|
|
434
|
-
|
|
435
|
-
suspend fun toggleMicrophone(): Boolean {
|
|
436
|
-
if (isMicrophoneOn) {
|
|
437
|
-
stopMicrophone()
|
|
438
|
-
} else {
|
|
439
|
-
startMicrophone()
|
|
440
|
-
}
|
|
441
|
-
|
|
442
|
-
return isMicrophoneOn
|
|
443
|
-
}
|
|
444
|
-
|
|
445
|
-
private fun getMicrophoneTrackMetadata(isEnabled: Boolean): Map<String, Any> =
|
|
446
|
-
mapOf(
|
|
447
|
-
"active" to isEnabled,
|
|
448
|
-
"paused" to !isEnabled, // TODO: FCE-711,
|
|
449
|
-
"type" to "microphone"
|
|
450
|
-
)
|
|
451
|
-
|
|
452
|
-
fun handleScreenSharePermission(promise: Promise) {
|
|
453
|
-
screenSharePermissionPromise = promise
|
|
454
|
-
if (!isScreenShareOn) {
|
|
455
|
-
ensureConnected()
|
|
456
|
-
val currentActivity = appContext?.currentActivity ?: throw ActivityNotFoundException()
|
|
457
|
-
|
|
458
|
-
val mediaProjectionManager =
|
|
459
|
-
appContext?.reactContext!!.getSystemService(
|
|
460
|
-
AppCompatActivity.MEDIA_PROJECTION_SERVICE
|
|
461
|
-
) as MediaProjectionManager
|
|
462
|
-
val intent = mediaProjectionManager.createScreenCaptureIntent()
|
|
463
|
-
currentActivity.startActivityForResult(intent, SCREENSHARE_REQUEST)
|
|
464
|
-
}
|
|
465
|
-
}
|
|
466
|
-
|
|
467
|
-
suspend fun startForegroundService(config: ForegroundServiceConfig) {
|
|
468
|
-
foregroundServiceManager.updateServiceWithConfig(config)
|
|
469
|
-
foregroundServiceManager.start()
|
|
470
|
-
}
|
|
471
|
-
|
|
472
|
-
fun stopForegroundService() {
|
|
473
|
-
foregroundServiceManager.stop()
|
|
474
|
-
}
|
|
475
|
-
|
|
476
|
-
suspend fun toggleScreenShare(screenShareOptions: ScreenShareOptions) {
|
|
477
|
-
this.screenShareMetadata = screenShareOptions.screenShareMetadata
|
|
478
|
-
this.screenShareQuality = screenShareOptions.quality
|
|
479
|
-
this.screenShareSimulcastConfig =
|
|
480
|
-
getSimulcastConfigFromOptions(screenShareOptions.simulcastConfig)
|
|
481
|
-
|
|
482
|
-
if (!isScreenShareOn) {
|
|
483
|
-
ensureConnected()
|
|
484
|
-
startScreenShare()
|
|
485
|
-
} else {
|
|
486
|
-
stopScreenShare()
|
|
487
|
-
}
|
|
488
|
-
}
|
|
489
|
-
|
|
490
|
-
fun getPeers(): List<Map<String, Any?>> =
|
|
491
|
-
getAllPeers().map { endpoint ->
|
|
492
|
-
mapOf(
|
|
493
|
-
"id" to endpoint.id,
|
|
494
|
-
"isLocal" to (endpoint.id == fishjamClient.getLocalEndpoint().id),
|
|
495
|
-
"metadata" to endpoint.metadata,
|
|
496
|
-
"tracks" to
|
|
497
|
-
endpoint.tracks.values.mapNotNull { track ->
|
|
498
|
-
when (track) {
|
|
499
|
-
is RemoteVideoTrack ->
|
|
500
|
-
mapOf(
|
|
501
|
-
"id" to track.id(),
|
|
502
|
-
"type" to "Video",
|
|
503
|
-
"metadata" to track.metadata,
|
|
504
|
-
"encoding" to track.encoding?.rid,
|
|
505
|
-
"encodingReason" to track.encodingReason?.value,
|
|
506
|
-
"aspectRatio" to track.dimensions?.aspectRatio
|
|
507
|
-
)
|
|
508
|
-
|
|
509
|
-
is RemoteAudioTrack ->
|
|
510
|
-
mapOf(
|
|
511
|
-
"id" to track.id(),
|
|
512
|
-
"type" to "Audio",
|
|
513
|
-
"metadata" to track.metadata,
|
|
514
|
-
"vadStatus" to
|
|
515
|
-
when (track.vadStatus) {
|
|
516
|
-
Server.MediaEvent.VadNotification.Status.STATUS_SPEECH -> "speech"
|
|
517
|
-
else -> "silence"
|
|
518
|
-
}
|
|
519
|
-
)
|
|
520
|
-
|
|
521
|
-
is LocalVideoTrack ->
|
|
522
|
-
mapOf(
|
|
523
|
-
"id" to track.id(),
|
|
524
|
-
"type" to "Video",
|
|
525
|
-
"metadata" to track.metadata,
|
|
526
|
-
"aspectRatio" to track.dimensions?.aspectRatio
|
|
527
|
-
)
|
|
528
|
-
|
|
529
|
-
is LocalScreenShareTrack ->
|
|
530
|
-
mapOf(
|
|
531
|
-
"id" to track.id(),
|
|
532
|
-
"type" to "Video",
|
|
533
|
-
"metadata" to track.metadata,
|
|
534
|
-
"aspectRatio" to track.dimensions?.aspectRatio
|
|
535
|
-
)
|
|
536
|
-
|
|
537
|
-
is LocalAudioTrack ->
|
|
538
|
-
mapOf(
|
|
539
|
-
"id" to track.id(),
|
|
540
|
-
"type" to "Audio",
|
|
541
|
-
"metadata" to track.metadata
|
|
542
|
-
)
|
|
543
|
-
|
|
544
|
-
is VideoTrack -> // TODO(FCE-1418): Remove after refactoring LocalVideoTrack
|
|
545
|
-
mapOf(
|
|
546
|
-
"id" to track.id(),
|
|
547
|
-
"type" to "Video",
|
|
548
|
-
"metadata" to track.metadata,
|
|
549
|
-
"aspectRatio" to track.dimensions?.aspectRatio
|
|
550
|
-
)
|
|
551
|
-
|
|
552
|
-
else -> {
|
|
553
|
-
null
|
|
554
|
-
}
|
|
555
|
-
}
|
|
556
|
-
}
|
|
557
|
-
)
|
|
558
|
-
}
|
|
559
|
-
|
|
560
|
-
fun getCaptureDevices(): List<Map<String, Any>> {
|
|
561
|
-
val devices = LocalVideoTrack.getCaptureDevices(appContext?.reactContext!!)
|
|
562
|
-
return devices.map { device ->
|
|
563
|
-
device.toLocalCamera()
|
|
564
|
-
}
|
|
565
|
-
}
|
|
566
|
-
|
|
567
|
-
fun getCurrentCaptureDevice(): Map<String, Any>? = getLocalVideoTrack()?.getCaptureDevice()?.toLocalCamera()
|
|
568
|
-
|
|
569
|
-
fun updatePeerMetadata(metadata: Metadata) {
|
|
570
|
-
ensureConnected()
|
|
571
|
-
fishjamClient.updatePeerMetadata(metadata)
|
|
572
|
-
}
|
|
573
|
-
|
|
574
|
-
private fun updateTrackMetadata(
|
|
575
|
-
trackId: String,
|
|
576
|
-
metadata: Metadata
|
|
577
|
-
) {
|
|
578
|
-
fishjamClient.updateTrackMetadata(trackId, metadata)
|
|
579
|
-
emitEndpoints()
|
|
580
|
-
}
|
|
581
|
-
|
|
582
|
-
fun updateLocalVideoTrackMetadata(metadata: Metadata) {
|
|
583
|
-
ensureVideoTrack()
|
|
584
|
-
getLocalVideoTrack()?.let {
|
|
585
|
-
updateTrackMetadata(it.id(), metadata)
|
|
586
|
-
}
|
|
587
|
-
}
|
|
588
|
-
|
|
589
|
-
private fun updateLocalAudioTrackMetadata(metadata: Metadata) {
|
|
590
|
-
ensureAudioTrack()
|
|
591
|
-
getLocalAudioTrack()?.let {
|
|
592
|
-
updateTrackMetadata(it.id(), metadata)
|
|
593
|
-
}
|
|
594
|
-
}
|
|
595
|
-
|
|
596
|
-
fun updateLocalScreenShareTrackMetadata(metadata: Metadata) {
|
|
597
|
-
ensureScreenShareTrack()
|
|
598
|
-
getLocalScreenShareTrack()?.let {
|
|
599
|
-
updateTrackMetadata(it.id(), metadata)
|
|
600
|
-
}
|
|
601
|
-
}
|
|
602
|
-
|
|
603
|
-
fun setOutputAudioDevice(audioDevice: String) {
|
|
604
|
-
audioSwitchManager?.selectAudioOutput(AudioDeviceKind.fromTypeName(audioDevice))
|
|
605
|
-
}
|
|
606
|
-
|
|
607
|
-
fun startAudioSwitcher() {
|
|
608
|
-
audioSwitchManager?.let {
|
|
609
|
-
it.start(this::emitAudioDeviceEvent)
|
|
610
|
-
emitAudioDeviceEvent(
|
|
611
|
-
it.availableAudioDevices(),
|
|
612
|
-
it.selectedAudioDevice()
|
|
613
|
-
)
|
|
614
|
-
}
|
|
615
|
-
}
|
|
616
|
-
|
|
617
|
-
fun stopAudioSwitcher() {
|
|
618
|
-
audioSwitchManager?.stop()
|
|
619
|
-
}
|
|
620
|
-
|
|
621
|
-
private fun toggleTrackEncoding(
|
|
622
|
-
encoding: String,
|
|
623
|
-
trackId: String,
|
|
624
|
-
simulcastConfig: SimulcastConfig
|
|
625
|
-
): SimulcastConfig {
|
|
626
|
-
val trackEncoding = encoding.toTrackEncoding()
|
|
627
|
-
|
|
628
|
-
val isTrackEncodingActive = simulcastConfig.activeEncodings.contains(trackEncoding)
|
|
629
|
-
|
|
630
|
-
if (isTrackEncodingActive) {
|
|
631
|
-
fishjamClient.disableTrackEncoding(trackId, trackEncoding)
|
|
632
|
-
} else {
|
|
633
|
-
fishjamClient.enableTrackEncoding(trackId, trackEncoding)
|
|
634
|
-
}
|
|
635
|
-
|
|
636
|
-
val updatedActiveEncodings =
|
|
637
|
-
if (isTrackEncodingActive) {
|
|
638
|
-
simulcastConfig.activeEncodings.filter { it != trackEncoding }
|
|
639
|
-
} else {
|
|
640
|
-
simulcastConfig.activeEncodings + trackEncoding
|
|
641
|
-
}
|
|
642
|
-
|
|
643
|
-
return SimulcastConfig(
|
|
644
|
-
enabled = true,
|
|
645
|
-
activeEncodings = updatedActiveEncodings
|
|
646
|
-
)
|
|
647
|
-
}
|
|
648
|
-
|
|
649
|
-
fun toggleScreenShareTrackEncoding(encoding: String): Map<String, Any> {
|
|
650
|
-
ensureScreenShareTrack()
|
|
651
|
-
getLocalScreenShareTrack()?.let {
|
|
652
|
-
screenShareSimulcastConfig =
|
|
653
|
-
toggleTrackEncoding(encoding, it.id(), screenShareSimulcastConfig)
|
|
654
|
-
}
|
|
655
|
-
return getSimulcastConfigAsRNMap(screenShareSimulcastConfig)
|
|
656
|
-
}
|
|
657
|
-
|
|
658
|
-
fun setScreenShareTrackBandwidth(bandwidth: Int) {
|
|
659
|
-
ensureScreenShareTrack()
|
|
660
|
-
getLocalScreenShareTrack()?.let {
|
|
661
|
-
fishjamClient.setTrackBandwidth(it.id(), TrackBandwidthLimit.BandwidthLimit(bandwidth))
|
|
662
|
-
}
|
|
663
|
-
}
|
|
664
|
-
|
|
665
|
-
fun setScreenShareTrackEncodingBandwidth(
|
|
666
|
-
encoding: String,
|
|
667
|
-
bandwidth: Int
|
|
668
|
-
) {
|
|
669
|
-
ensureScreenShareTrack()
|
|
670
|
-
getLocalScreenShareTrack()?.let {
|
|
671
|
-
fishjamClient.setEncodingBandwidth(
|
|
672
|
-
it.id(),
|
|
673
|
-
encoding,
|
|
674
|
-
TrackBandwidthLimit.BandwidthLimit(bandwidth)
|
|
675
|
-
)
|
|
676
|
-
}
|
|
677
|
-
}
|
|
678
|
-
|
|
679
|
-
fun setTargetTrackEncoding(
|
|
680
|
-
trackId: String,
|
|
681
|
-
encoding: String
|
|
682
|
-
) {
|
|
683
|
-
ensureConnected()
|
|
684
|
-
fishjamClient.setTargetTrackEncoding(trackId, encoding.toTrackEncoding())
|
|
685
|
-
}
|
|
686
|
-
|
|
687
|
-
fun toggleVideoTrackEncoding(encoding: String): Map<String, Any?> {
|
|
688
|
-
ensureVideoTrack()
|
|
689
|
-
val trackId = getLocalVideoTrack()?.id() ?: return emptyMap()
|
|
690
|
-
videoSimulcastConfig = toggleTrackEncoding(encoding, trackId, videoSimulcastConfig)
|
|
691
|
-
|
|
692
|
-
val event = EmitableEvent.simulcastConfigUpdate(videoSimulcastConfig)
|
|
693
|
-
emitEvent(event)
|
|
694
|
-
|
|
695
|
-
return event.data
|
|
696
|
-
}
|
|
697
|
-
|
|
698
|
-
fun setVideoTrackEncodingBandwidth(
|
|
699
|
-
encoding: String,
|
|
700
|
-
bandwidth: Int
|
|
701
|
-
) {
|
|
702
|
-
ensureVideoTrack()
|
|
703
|
-
getLocalVideoTrack()?.let {
|
|
704
|
-
fishjamClient.setEncodingBandwidth(
|
|
705
|
-
it.id(),
|
|
706
|
-
encoding,
|
|
707
|
-
TrackBandwidthLimit.BandwidthLimit(bandwidth)
|
|
708
|
-
)
|
|
709
|
-
}
|
|
710
|
-
}
|
|
711
|
-
|
|
712
|
-
fun setVideoTrackBandwidth(bandwidth: Int) {
|
|
713
|
-
ensureVideoTrack()
|
|
714
|
-
getLocalVideoTrack()?.let {
|
|
715
|
-
fishjamClient.setTrackBandwidth(it.id(), TrackBandwidthLimit.BandwidthLimit(bandwidth))
|
|
716
|
-
}
|
|
717
|
-
}
|
|
718
|
-
|
|
719
|
-
fun changeWebRTCLoggingSeverity(severity: String) {
|
|
720
|
-
when (severity) {
|
|
721
|
-
"verbose" -> fishjamClient.changeWebRTCLoggingSeverity(Logging.Severity.LS_VERBOSE)
|
|
722
|
-
|
|
723
|
-
"info" -> fishjamClient.changeWebRTCLoggingSeverity(Logging.Severity.LS_INFO)
|
|
724
|
-
|
|
725
|
-
"error" -> fishjamClient.changeWebRTCLoggingSeverity(Logging.Severity.LS_ERROR)
|
|
726
|
-
|
|
727
|
-
"warning" -> fishjamClient.changeWebRTCLoggingSeverity(Logging.Severity.LS_WARNING)
|
|
728
|
-
|
|
729
|
-
"none" -> fishjamClient.changeWebRTCLoggingSeverity(Logging.Severity.LS_NONE)
|
|
730
|
-
|
|
731
|
-
else -> {
|
|
732
|
-
throw CodedException("Severity with name=$severity not found")
|
|
733
|
-
}
|
|
734
|
-
}
|
|
735
|
-
}
|
|
736
|
-
|
|
737
|
-
private fun rtcOutboundStatsToRNMap(stats: RTCOutboundStats): Map<String, Any?> {
|
|
738
|
-
val innerMap = mutableMapOf<String, Double>()
|
|
739
|
-
innerMap["bandwidth"] = stats.qualityLimitationDurations?.bandwidth ?: 0.0
|
|
740
|
-
innerMap["cpu"] = stats.qualityLimitationDurations?.cpu ?: 0.0
|
|
741
|
-
innerMap["none"] = stats.qualityLimitationDurations?.none ?: 0.0
|
|
742
|
-
innerMap["other"] = stats.qualityLimitationDurations?.other ?: 0.0
|
|
743
|
-
|
|
744
|
-
val res = mutableMapOf<String, Any?>()
|
|
745
|
-
res["kind"] = stats.kind
|
|
746
|
-
res["rid"] = stats.rid
|
|
747
|
-
res["bytesSent"] = stats.bytesSent?.toInt() ?: 0
|
|
748
|
-
res["targetBitrate"] = stats.targetBitrate ?: 0.0
|
|
749
|
-
res["packetsSent"] = stats.packetsSent?.toInt() ?: 0
|
|
750
|
-
res["framesEncoded"] = stats.framesEncoded?.toInt() ?: 0
|
|
751
|
-
res["framesPerSecond"] = stats.framesPerSecond ?: 0.0
|
|
752
|
-
res["frameWidth"] = stats.frameWidth?.toInt() ?: 0
|
|
753
|
-
res["frameHeight"] = stats.frameHeight?.toInt() ?: 0
|
|
754
|
-
res["qualityLimitationDurations"] = innerMap
|
|
755
|
-
|
|
756
|
-
return res
|
|
757
|
-
}
|
|
758
|
-
|
|
759
|
-
private fun rtcInboundStatsToRNMap(stats: RTCInboundStats): Map<String, Any?> {
|
|
760
|
-
val res = mutableMapOf<String, Any?>()
|
|
761
|
-
res["kind"] = stats.kind
|
|
762
|
-
res["jitter"] = stats.jitter ?: 0.0
|
|
763
|
-
res["packetsLost"] = stats.packetsLost ?: 0
|
|
764
|
-
res["packetsReceived"] = stats.packetsReceived?.toInt() ?: 0
|
|
765
|
-
res["bytesReceived"] = stats.bytesReceived?.toInt() ?: 0
|
|
766
|
-
res["framesReceived"] = stats.framesReceived ?: 0
|
|
767
|
-
res["frameWidth"] = stats.frameWidth?.toInt() ?: 0
|
|
768
|
-
res["frameHeight"] = stats.frameHeight?.toInt() ?: 0
|
|
769
|
-
res["framesPerSecond"] = stats.framesPerSecond ?: 0.0
|
|
770
|
-
res["framesDropped"] = stats.framesDropped?.toInt() ?: 0
|
|
771
|
-
|
|
772
|
-
return res
|
|
773
|
-
}
|
|
774
|
-
|
|
775
|
-
suspend fun getStatistics(): Map<String, Map<String, Any?>> {
|
|
776
|
-
val newMap = mutableMapOf<String, Map<String, Any?>>()
|
|
777
|
-
val stats = fishjamClient.getStats()
|
|
778
|
-
stats.forEach { entry ->
|
|
779
|
-
newMap[entry.key] =
|
|
780
|
-
if (entry.value is RTCInboundStats) {
|
|
781
|
-
rtcInboundStatsToRNMap(
|
|
782
|
-
entry.value as RTCInboundStats
|
|
783
|
-
)
|
|
784
|
-
} else {
|
|
785
|
-
rtcOutboundStatsToRNMap(entry.value as RTCOutboundStats)
|
|
786
|
-
}
|
|
787
|
-
}
|
|
788
|
-
return newMap
|
|
789
|
-
}
|
|
790
|
-
|
|
791
|
-
private suspend fun startScreenShare() {
|
|
792
|
-
val videoParameters = getScreenShareVideoParameters()
|
|
793
|
-
if (mediaProjectionIntent == null) {
|
|
794
|
-
throw MissingScreenSharePermission()
|
|
795
|
-
}
|
|
796
|
-
|
|
797
|
-
foregroundServiceManager.updateService { screenSharingEnabled = true }
|
|
798
|
-
foregroundServiceManager.start()
|
|
799
|
-
|
|
800
|
-
fishjamClient.createScreenShareTrack(
|
|
801
|
-
mediaProjectionIntent!!,
|
|
802
|
-
videoParameters,
|
|
803
|
-
screenShareMetadata
|
|
804
|
-
)
|
|
805
|
-
mediaProjectionIntent = null
|
|
806
|
-
|
|
807
|
-
setScreenShareTrackState(true)
|
|
808
|
-
emitEndpoints()
|
|
809
|
-
}
|
|
810
|
-
|
|
811
|
-
private fun getScreenShareVideoParameters(): VideoParameters {
|
|
812
|
-
val videoParameters =
|
|
813
|
-
when (screenShareQuality) {
|
|
814
|
-
"VGA" -> VideoParameters.presetScreenShareVGA
|
|
815
|
-
"HD5" -> VideoParameters.presetScreenShareHD5
|
|
816
|
-
"HD15" -> VideoParameters.presetScreenShareHD15
|
|
817
|
-
"FHD15" -> VideoParameters.presetScreenShareFHD15
|
|
818
|
-
"FHD30" -> VideoParameters.presetScreenShareFHD30
|
|
819
|
-
else -> VideoParameters.presetScreenShareHD15
|
|
820
|
-
}
|
|
821
|
-
val dimensions = videoParameters.dimensions.flip()
|
|
822
|
-
return videoParameters.copy(
|
|
823
|
-
dimensions = dimensions,
|
|
824
|
-
simulcastConfig = screenShareSimulcastConfig,
|
|
825
|
-
maxBitrate = videoParameters.maxBitrate
|
|
826
|
-
)
|
|
827
|
-
}
|
|
828
|
-
|
|
829
|
-
private fun setScreenShareTrackState(isEnabled: Boolean) {
|
|
830
|
-
isScreenShareOn = isEnabled
|
|
831
|
-
emitEvent(EmitableEvent.isScreenShareOn(isEnabled))
|
|
832
|
-
}
|
|
833
|
-
|
|
834
|
-
private fun stopScreenShare() {
|
|
835
|
-
ensureScreenShareTrack()
|
|
836
|
-
coroutineScope.launch {
|
|
837
|
-
foregroundServiceManager.updateService { screenSharingEnabled = false }
|
|
838
|
-
foregroundServiceManager.start()
|
|
839
|
-
val screenShareTrack =
|
|
840
|
-
fishjamClient.getLocalEndpoint().tracks.values.first { track ->
|
|
841
|
-
track is LocalScreenShareTrack
|
|
842
|
-
} as? LocalScreenShareTrack
|
|
843
|
-
if (screenShareTrack != null) {
|
|
844
|
-
fishjamClient.removeTrack(screenShareTrack.id())
|
|
845
|
-
}
|
|
846
|
-
setScreenShareTrackState(false)
|
|
847
|
-
emitEndpoints()
|
|
848
|
-
}
|
|
849
|
-
}
|
|
850
|
-
|
|
851
|
-
private fun emitEvent(event: EmitableEvent) {
|
|
852
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
853
|
-
RNFishjamClient.sendEvent(event)
|
|
854
|
-
}
|
|
855
|
-
}
|
|
856
|
-
|
|
857
|
-
private fun emitEndpoints() {
|
|
858
|
-
emitEvent(EmitableEvent.peersUpdate(getPeers()))
|
|
859
|
-
}
|
|
860
|
-
|
|
861
|
-
private fun emitAudioDeviceEvent(
|
|
862
|
-
audioDevices: List<AudioDevice>,
|
|
863
|
-
selectedDevice: AudioDevice?
|
|
864
|
-
) {
|
|
865
|
-
emitEvent(EmitableEvent.audioDeviceUpdate(audioDevices, selectedDevice))
|
|
866
|
-
}
|
|
867
|
-
|
|
868
|
-
private fun getSimulcastConfigAsRNMap(simulcastConfig: SimulcastConfig): Map<String, Any> =
|
|
869
|
-
mapOf(
|
|
870
|
-
"enabled" to simulcastConfig.enabled,
|
|
871
|
-
"activeEncodings" to
|
|
872
|
-
simulcastConfig.activeEncodings.map {
|
|
873
|
-
it.rid
|
|
874
|
-
}
|
|
875
|
-
)
|
|
876
|
-
|
|
877
|
-
override fun onJoined(
|
|
878
|
-
peerID: String,
|
|
879
|
-
peersInRoom: MutableMap<String, Endpoint>
|
|
880
|
-
) {
|
|
881
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
882
|
-
isConnected = true
|
|
883
|
-
connectPromise?.resolve(null)
|
|
884
|
-
connectPromise = null
|
|
885
|
-
emitEndpoints()
|
|
886
|
-
peerStatus = PeerStatus.Connected
|
|
887
|
-
}
|
|
888
|
-
}
|
|
889
|
-
|
|
890
|
-
override fun onJoinError(metadata: Any) {
|
|
891
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
892
|
-
connectPromise?.reject(JoinError(metadata))
|
|
893
|
-
connectPromise = null
|
|
894
|
-
}
|
|
895
|
-
}
|
|
896
|
-
|
|
897
|
-
private fun addOrUpdateTrack(track: Track) {
|
|
898
|
-
emitEndpoints()
|
|
899
|
-
trackUpdateListenersManager.notifyListeners()
|
|
900
|
-
}
|
|
901
|
-
|
|
902
|
-
override fun onTrackReady(track: Track) {
|
|
903
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
904
|
-
addOrUpdateTrack(track)
|
|
905
|
-
}
|
|
906
|
-
}
|
|
907
|
-
|
|
908
|
-
override fun onTrackAdded(track: Track) {
|
|
909
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
910
|
-
trackUpdateListenersManager.notifyListeners()
|
|
911
|
-
}
|
|
912
|
-
}
|
|
913
|
-
|
|
914
|
-
override fun onTrackRemoved(track: Track) {
|
|
915
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
916
|
-
emitEndpoints()
|
|
917
|
-
trackUpdateListenersManager.notifyListeners()
|
|
918
|
-
}
|
|
919
|
-
}
|
|
920
|
-
|
|
921
|
-
override fun onTrackUpdated(track: Track) {
|
|
922
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
923
|
-
emitEndpoints()
|
|
924
|
-
trackUpdateListenersManager.notifyListeners()
|
|
925
|
-
}
|
|
926
|
-
}
|
|
927
|
-
|
|
928
|
-
override fun onPeerJoined(peer: Peer) {
|
|
929
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
930
|
-
emitEndpoints()
|
|
931
|
-
trackUpdateListenersManager.notifyListeners()
|
|
932
|
-
}
|
|
933
|
-
}
|
|
934
|
-
|
|
935
|
-
override fun onPeerLeft(peer: Peer) {
|
|
936
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
937
|
-
emitEndpoints()
|
|
938
|
-
trackUpdateListenersManager.notifyListeners()
|
|
939
|
-
}
|
|
940
|
-
}
|
|
941
|
-
|
|
942
|
-
override fun onPeerUpdated(peer: Peer) {}
|
|
943
|
-
|
|
944
|
-
override fun onBandwidthEstimationChanged(estimation: Long) {
|
|
945
|
-
emitEvent(EmitableEvent.bandwidthEstimation(estimation))
|
|
946
|
-
}
|
|
947
|
-
|
|
948
|
-
override fun onDisconnected() {
|
|
949
|
-
peerStatus = PeerStatus.Idle
|
|
950
|
-
}
|
|
951
|
-
|
|
952
|
-
override fun onSocketClose(
|
|
953
|
-
code: Int,
|
|
954
|
-
reason: String
|
|
955
|
-
) {
|
|
956
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
957
|
-
connectPromise?.reject(SocketClosedError(code, reason))
|
|
958
|
-
connectPromise = null
|
|
959
|
-
peerStatus = PeerStatus.Idle
|
|
960
|
-
}
|
|
961
|
-
}
|
|
962
|
-
|
|
963
|
-
override fun onSocketError(t: Throwable) {
|
|
964
|
-
CoroutineScope(Dispatchers.Main).launch {
|
|
965
|
-
connectPromise?.reject(SocketError(t.message ?: t.toString()))
|
|
966
|
-
connectPromise = null
|
|
967
|
-
peerStatus = PeerStatus.Error
|
|
968
|
-
}
|
|
969
|
-
}
|
|
970
|
-
|
|
971
|
-
override fun onReconnected() {
|
|
972
|
-
reconnectionStatus = ReconnectionStatus.Reconnecting
|
|
973
|
-
}
|
|
974
|
-
|
|
975
|
-
override fun onReconnectionStarted() {
|
|
976
|
-
reconnectionStatus = ReconnectionStatus.Idle
|
|
977
|
-
}
|
|
978
|
-
|
|
979
|
-
override fun onReconnectionRetriesLimitReached() {
|
|
980
|
-
reconnectionStatus = ReconnectionStatus.Error
|
|
981
|
-
}
|
|
982
|
-
|
|
983
|
-
override fun onCaptureDeviceChanged(captureDevice: CaptureDevice?) {
|
|
984
|
-
emitEvent(
|
|
985
|
-
EmitableEvent.currentCameraChanged(
|
|
986
|
-
captureDevice?.toLocalCamera(),
|
|
987
|
-
isCameraOn,
|
|
988
|
-
isCameraInitialized
|
|
989
|
-
)
|
|
990
|
-
)
|
|
991
|
-
}
|
|
992
|
-
|
|
993
|
-
override fun onIncompatibleTracksDetected() {
|
|
994
|
-
// TODO: FCE-1215 Add proper url after docs are updated
|
|
995
|
-
emitEvent(
|
|
996
|
-
EmitableEvent.warning(
|
|
997
|
-
"Incompatible track detected. This usually means your device is missing codecs negotiated for the room. Visit https://docs.fishjam.io/category/react-native-integration for information."
|
|
998
|
-
)
|
|
999
|
-
)
|
|
1000
|
-
}
|
|
1001
|
-
}
|