agora-appbuilder-core 3.0.9 → 4.0.0-api.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 (305) hide show
  1. package/Readme.md +6 -0
  2. package/package.json +2 -2
  3. package/template/_package-lock.json +5871 -4728
  4. package/template/agora-rn-uikit/src/AgoraUIKit.tsx +6 -6
  5. package/template/agora-rn-uikit/src/Contexts/ContentContext.tsx +10 -0
  6. package/template/agora-rn-uikit/src/Contexts/DispatchContext.tsx +22 -0
  7. package/template/agora-rn-uikit/src/Contexts/LocalUserContext.tsx +10 -6
  8. package/template/agora-rn-uikit/src/Contexts/PropsContext.tsx +28 -8
  9. package/template/agora-rn-uikit/src/Contexts/RtcContext.tsx +7 -15
  10. package/template/agora-rn-uikit/src/Controls/BtnTemplate.tsx +30 -26
  11. package/template/agora-rn-uikit/src/Controls/Icons.ts +30 -83
  12. package/template/agora-rn-uikit/src/Controls/ImageIcon.tsx +6 -6
  13. package/template/agora-rn-uikit/src/Controls/Local/LocalAudioMute.tsx +4 -2
  14. package/template/agora-rn-uikit/src/Controls/Local/LocalVideoMute.tsx +4 -2
  15. package/template/agora-rn-uikit/src/Controls/Local/Recording.tsx +0 -2
  16. package/template/agora-rn-uikit/src/Controls/Local/SwitchCamera.tsx +6 -6
  17. package/template/agora-rn-uikit/src/Controls/LocalControls.tsx +5 -5
  18. package/template/agora-rn-uikit/src/Controls/Remote/RemoteAudioMute.tsx +4 -4
  19. package/template/agora-rn-uikit/src/Controls/Remote/RemoteVideoMute.tsx +4 -4
  20. package/template/agora-rn-uikit/src/Controls/RemoteControls.tsx +2 -2
  21. package/template/agora-rn-uikit/src/Reducer/LocalMuteAudio.ts +6 -6
  22. package/template/agora-rn-uikit/src/Reducer/LocalMuteVideo.ts +6 -6
  23. package/template/agora-rn-uikit/src/Reducer/LocalPermissionState.ts +23 -0
  24. package/template/agora-rn-uikit/src/Reducer/RemoteAudioStateChanged.ts +6 -6
  25. package/template/agora-rn-uikit/src/Reducer/RemoteVideoStateChanged.ts +7 -7
  26. package/template/agora-rn-uikit/src/Reducer/UpdateDualStreamMode.ts +7 -7
  27. package/template/agora-rn-uikit/src/Reducer/UserJoined.ts +10 -10
  28. package/template/agora-rn-uikit/src/Reducer/UserMuteRemoteAudio.ts +6 -6
  29. package/template/agora-rn-uikit/src/Reducer/UserMuteRemoteVideo.ts +6 -6
  30. package/template/agora-rn-uikit/src/Reducer/UserOffline.ts +5 -5
  31. package/template/agora-rn-uikit/src/Reducer/UserPin.ts +11 -0
  32. package/template/agora-rn-uikit/src/Reducer/index.ts +2 -0
  33. package/template/agora-rn-uikit/src/Rtc/Create.tsx +74 -7
  34. package/template/agora-rn-uikit/src/Rtc/Join.tsx +5 -4
  35. package/template/agora-rn-uikit/src/RtcConfigure.tsx +76 -49
  36. package/template/agora-rn-uikit/src/Views/MaxVideoView.native.tsx +17 -7
  37. package/template/agora-rn-uikit/src/Views/MaxVideoView.tsx +17 -11
  38. package/template/agora-rn-uikit/src/Views/MinVideoView.tsx +2 -2
  39. package/template/agora-rn-uikit/src/index.ts +17 -9
  40. package/template/android/app/build.gradle +1 -0
  41. package/template/android/app/src/main/AndroidManifest.xml +22 -15
  42. package/template/android/app/src/main/assets/fonts/SourceSansPro-Regular.ttf +0 -0
  43. package/template/android/app/src/main/assets/fonts/icomoon.ttf +0 -0
  44. package/template/android/app/src/main/java/com/helloworld/MainActivity.java +50 -0
  45. package/template/android/app/src/main/res/values/colors.xml +7 -0
  46. package/template/android/build.gradle +3 -3
  47. package/template/babel.config.js +1 -0
  48. package/template/bridge/rtc/webNg/RtcEngine.ts +110 -17
  49. package/template/customization-api/action-library.ts +10 -14
  50. package/template/customization-api/app-state.ts +4 -6
  51. package/template/customization-api/customEvents.ts +2 -2
  52. package/template/customization-api/customize.ts +1 -1
  53. package/template/customization-api/sub-components.ts +4 -12
  54. package/template/customization-api/typeDefinition.ts +15 -38
  55. package/template/customization-implementation/createHook.ts +24 -6
  56. package/template/customization-implementation/index.ts +1 -1
  57. package/template/customization-implementation/useCustomization.tsx +5 -7
  58. package/template/electron/index.html +27 -27
  59. package/template/electron/renderer/index.js +1 -0
  60. package/template/global.d.ts +26 -4
  61. package/template/index.rsdk.tsx +1 -0
  62. package/template/index.web.js +2 -1
  63. package/template/index.wsdk.tsx +9 -2
  64. package/template/ios/HelloWorld/Info.plist +14 -1
  65. package/template/ios/HelloWorld.xcodeproj/project.pbxproj +17 -0
  66. package/template/metro.config.js +1 -1
  67. package/template/package.json +18 -7
  68. package/template/react-native-toast-message/index.d.ts +43 -43
  69. package/template/react-native-toast-message/src/colors/index.js +3 -2
  70. package/template/react-native-toast-message/src/components/base/index.js +46 -59
  71. package/template/react-native-toast-message/src/components/base/styles.js +16 -32
  72. package/template/react-native-toast-message/src/components/checkbox.js +178 -0
  73. package/template/react-native-toast-message/src/components/error.js +3 -2
  74. package/template/react-native-toast-message/src/components/info.js +3 -2
  75. package/template/react-native-toast-message/src/components/success.js +3 -2
  76. package/template/react-native-toast-message/src/index.js +122 -31
  77. package/template/react-native-toast-message/src/index.sdk.tsx +125 -35
  78. package/template/react-native-toast-message/src/styles.js +3 -4
  79. package/template/react-native-toast-message/src/styles.sdk.ts +3 -4
  80. package/template/react-native.config.js +7 -0
  81. package/template/src/App.tsx +19 -14
  82. package/template/src/AppWrapper.tsx +74 -29
  83. package/template/src/SDKAppWrapper.tsx +60 -64
  84. package/template/src/app-state/useLocalUserInfo.ts +3 -3
  85. package/template/src/assets/font-styles.css +329 -0
  86. package/template/src/assets/fonts/SourceSansPro-Regular.ttf +0 -0
  87. package/template/src/assets/fonts/icomoon.ttf +0 -0
  88. package/template/src/assets/permission.png +0 -0
  89. package/template/src/assets/selection.json +1 -0
  90. package/template/src/atoms/ActionMenu.tsx +236 -0
  91. package/template/src/atoms/AnimatedActiveSpeaker.native.tsx +71 -0
  92. package/template/src/atoms/AnimatedActiveSpeaker.tsx +84 -0
  93. package/template/src/atoms/AnimatedRings.native.tsx +68 -0
  94. package/template/src/atoms/AnimatedRings.tsx +70 -0
  95. package/template/src/atoms/Card.tsx +61 -0
  96. package/template/src/atoms/CircularProgress.native.tsx +121 -0
  97. package/template/src/atoms/CircularProgress.tsx +102 -0
  98. package/template/src/atoms/CustomIcon.tsx +88 -0
  99. package/template/src/atoms/CustomSwitch.tsx +287 -0
  100. package/template/src/atoms/Dropdown.tsx +306 -0
  101. package/template/src/atoms/HorizontalRule.tsx +3 -1
  102. package/template/src/atoms/IconButton.tsx +162 -0
  103. package/template/src/atoms/ImageIcon.tsx +98 -0
  104. package/template/src/atoms/InfoBubble.tsx +291 -0
  105. package/template/src/atoms/Input.tsx +87 -0
  106. package/template/src/atoms/InviteInfo.tsx +166 -0
  107. package/template/src/atoms/LinkButton.tsx +28 -0
  108. package/template/src/atoms/OutlineButton.tsx +61 -0
  109. package/template/src/atoms/ParticipantsCount.tsx +74 -0
  110. package/template/src/atoms/Popup.tsx +147 -0
  111. package/template/src/atoms/PrimaryButton.tsx +51 -26
  112. package/template/src/atoms/RecordingInfo.tsx +52 -0
  113. package/template/src/atoms/SecondaryButton.tsx +8 -5
  114. package/template/src/atoms/Spacer.tsx +22 -0
  115. package/template/src/atoms/TertiaryButton.tsx +78 -0
  116. package/template/src/atoms/TextInput.tsx +12 -14
  117. package/template/src/atoms/Toggle.tsx +47 -0
  118. package/template/src/atoms/Toolbar.tsx +68 -0
  119. package/template/src/atoms/ToolbarItem.tsx +63 -0
  120. package/template/src/atoms/Tooltip.native.tsx +65 -0
  121. package/template/src/atoms/Tooltip.tsx +94 -0
  122. package/template/src/atoms/UserAvatar.tsx +60 -0
  123. package/template/src/components/Chat.tsx +164 -278
  124. package/template/src/components/ChatContext.ts +8 -1
  125. package/template/src/components/ColorConfigure.tsx +1 -1
  126. package/template/src/components/ColorContext.ts +1 -1
  127. package/template/src/components/CommonStyles.ts +44 -0
  128. package/template/src/components/Controls.tsx +331 -73
  129. package/template/src/components/{Controls.native.tsx → Controls1.native.tsx} +8 -6
  130. package/template/src/components/DeviceConfigure.tsx +511 -106
  131. package/template/src/components/DeviceContext.tsx +8 -4
  132. package/template/src/components/EventsConfigure.tsx +192 -10
  133. package/template/src/components/GraphQLProvider.tsx +1 -1
  134. package/template/src/components/GridVideo.tsx +60 -45
  135. package/template/src/components/HostControlView.tsx +114 -35
  136. package/template/src/components/Navbar.tsx +219 -437
  137. package/template/src/components/Navigation.tsx +15 -1
  138. package/template/src/components/NetworkQualityContext.tsx +22 -22
  139. package/template/src/components/ParticipantsView.tsx +178 -156
  140. package/template/src/components/PinnedVideo.tsx +206 -121
  141. package/template/src/components/Precall.native.tsx +358 -119
  142. package/template/src/components/Precall.tsx +272 -138
  143. package/template/src/components/RTMConfigure.tsx +66 -19
  144. package/template/src/components/Router.electron.ts +1 -0
  145. package/template/src/components/Router.native.ts +1 -0
  146. package/template/src/components/Router.sdk.ts +1 -0
  147. package/template/src/components/Router.ts +1 -0
  148. package/template/src/components/SdkApiContext.tsx +161 -0
  149. package/template/src/components/Settings.tsx +26 -95
  150. package/template/src/components/SettingsView.tsx +251 -56
  151. package/template/src/components/Share.tsx +305 -276
  152. package/template/src/components/StorageContext.tsx +30 -3
  153. package/template/src/components/ToastComponent.tsx +8 -0
  154. package/template/src/components/chat-messages/useChatMessages.tsx +97 -50
  155. package/template/src/components/chat-ui/useChatUIControls.tsx +76 -0
  156. package/template/src/components/common/Error.tsx +20 -6
  157. package/template/src/components/common/Logo.tsx +16 -15
  158. package/template/src/components/contexts/LiveStreamDataContext.tsx +16 -11
  159. package/template/src/components/contexts/VideoMeetingDataContext.tsx +41 -11
  160. package/template/src/components/contexts/WhiteboardContext.tsx +3 -3
  161. package/template/src/components/livestream/LiveStreamContext.tsx +284 -50
  162. package/template/src/components/livestream/Types.ts +39 -14
  163. package/template/src/components/livestream/index.ts +1 -0
  164. package/template/src/components/livestream/views/LiveStreamControls.tsx +9 -4
  165. package/template/src/components/participants/AllAudienceParticipants.tsx +102 -31
  166. package/template/src/components/participants/AllHostParticipants.tsx +106 -35
  167. package/template/src/components/participants/Participant.tsx +300 -0
  168. package/template/src/components/participants/ParticipantName.tsx +13 -7
  169. package/template/src/components/participants/ParticipantSectionTitle.tsx +35 -10
  170. package/template/src/components/participants/ScreenshareParticipants.tsx +144 -12
  171. package/template/src/components/participants/UserActionMenuOptions.tsx +396 -0
  172. package/template/src/components/popups/InvitePopup.tsx +115 -0
  173. package/template/src/components/popups/StopRecordingPopup.tsx +114 -0
  174. package/template/src/components/precall/LocalMute.tsx +84 -14
  175. package/template/src/components/precall/{LocalMute.native.tsx → LocalMute1.native.tsx} +21 -5
  176. package/template/src/components/precall/PermissionHelper.native.tsx +5 -0
  177. package/template/src/components/precall/PermissionHelper.tsx +126 -0
  178. package/template/src/components/precall/PreCallSettings.tsx +52 -0
  179. package/template/src/components/precall/VideoPreview.native.tsx +51 -6
  180. package/template/src/components/precall/VideoPreview.tsx +164 -8
  181. package/template/src/components/precall/joinCallBtn.native.tsx +2 -2
  182. package/template/src/components/precall/joinCallBtn.tsx +17 -4
  183. package/template/src/components/precall/meetingTitle.tsx +17 -14
  184. package/template/src/components/precall/selectDevice.tsx +1 -21
  185. package/template/src/components/precall/textInput.tsx +34 -6
  186. package/template/src/components/precall/usePreCall.tsx +39 -1
  187. package/template/src/components/{meeting-info/useMeetingInfo.tsx → room-info/useRoomInfo.tsx} +34 -10
  188. package/template/src/components/{meeting-info/useSetMeetingInfo.tsx → room-info/useSetRoomInfo.tsx} +12 -12
  189. package/template/src/components/styles.ts +42 -21
  190. package/template/src/components/useShareLink.tsx +19 -21
  191. package/template/src/components/useToast.tsx +41 -0
  192. package/template/src/components/useUserPreference.tsx +9 -6
  193. package/template/src/components/useVideoCall.tsx +84 -0
  194. package/template/src/language/default-labels/createScreenLabels.ts +3 -3
  195. package/template/src/language/default-labels/joinScreenLabels.ts +2 -2
  196. package/template/src/language/default-labels/precallScreenLabels.ts +3 -3
  197. package/template/src/language/default-labels/shareLinkScreenLabels.ts +5 -5
  198. package/template/src/language/default-labels/videoCallScreenLabels.ts +5 -5
  199. package/template/src/pages/Authenticate.tsx +5 -15
  200. package/template/src/pages/Create.tsx +304 -191
  201. package/template/src/pages/Endcall.tsx +148 -0
  202. package/template/src/pages/Join.tsx +96 -70
  203. package/template/src/pages/VideoCall.tsx +179 -69
  204. package/template/src/pages/video-call/ActionSheet.native.tsx +215 -0
  205. package/template/src/pages/video-call/ActionSheet.tsx +226 -0
  206. package/template/src/pages/video-call/ActionSheetContent.tsx +479 -0
  207. package/template/src/pages/video-call/ActionSheetHandle.tsx +38 -0
  208. package/template/src/pages/video-call/ActionSheetStyles.css +138 -0
  209. package/template/src/pages/video-call/DefaultLayouts.ts +6 -6
  210. package/template/src/pages/video-call/NameWithMicIcon.tsx +93 -49
  211. package/template/src/pages/video-call/RenderComponent.tsx +6 -30
  212. package/template/src/pages/video-call/SidePanelHeader.tsx +186 -0
  213. package/template/src/pages/video-call/VideoCallMobileView.tsx +138 -0
  214. package/template/src/pages/video-call/VideoCallScreen.native.tsx +37 -0
  215. package/template/src/pages/video-call/VideoCallScreen.tsx +109 -66
  216. package/template/src/pages/video-call/VideoComponent.tsx +20 -4
  217. package/template/src/pages/video-call/VideoRenderer.tsx +227 -61
  218. package/template/src/pages/video-call/index.ts +35 -7
  219. package/template/src/rtm/RTMEngine.ts +8 -0
  220. package/template/src/rtm-events/constants.ts +3 -1
  221. package/template/src/rtm-events-api/Events.ts +5 -4
  222. package/template/src/rtm-events-api/LocalEvents.ts +6 -0
  223. package/template/src/rtm-events-api/types.ts +5 -5
  224. package/template/src/subComponents/ChatBubble.tsx +125 -84
  225. package/template/src/subComponents/ChatContainer.tsx +280 -93
  226. package/template/src/subComponents/ChatInput.ios.tsx +175 -0
  227. package/template/src/subComponents/ChatInput.tsx +72 -115
  228. package/template/src/subComponents/Checkbox.native.tsx +16 -5
  229. package/template/src/subComponents/Checkbox.tsx +2 -2
  230. package/template/src/subComponents/CopyJoinInfo.tsx +36 -58
  231. package/template/src/subComponents/EndcallPopup.tsx +107 -0
  232. package/template/src/subComponents/FallbackLogo.tsx +122 -40
  233. package/template/src/subComponents/LanguageSelector.tsx +1 -1
  234. package/template/src/subComponents/LayoutIconButton.tsx +201 -0
  235. package/template/src/subComponents/LayoutIconDropdown.tsx +131 -134
  236. package/template/src/subComponents/{LayoutIconDropdown.native.tsx → LayoutIconDropdown1.native.tsx} +4 -18
  237. package/template/src/subComponents/LocalAudioMute.tsx +119 -27
  238. package/template/src/subComponents/LocalEndCall.tsx +73 -35
  239. package/template/src/subComponents/LocalSwitchCamera.tsx +19 -32
  240. package/template/src/subComponents/LocalVideoMute.tsx +117 -27
  241. package/template/src/subComponents/Logo.tsx +3 -4
  242. package/template/src/subComponents/LogoutButton.tsx +1 -1
  243. package/template/src/subComponents/NetworkQualityPill.tsx +66 -68
  244. package/template/src/subComponents/OpenInNativeButton.tsx +3 -3
  245. package/template/src/subComponents/Recording.tsx +28 -29
  246. package/template/src/subComponents/RemoteAudioMute.tsx +83 -29
  247. package/template/src/subComponents/RemoteEndCall.tsx +8 -5
  248. package/template/src/subComponents/RemoteMutePopup.tsx +193 -0
  249. package/template/src/subComponents/RemoteVideoMute.tsx +74 -21
  250. package/template/src/subComponents/RemoveMeetingPopup.tsx +109 -0
  251. package/template/src/subComponents/RemoveScreensharePopup.tsx +109 -0
  252. package/template/src/subComponents/ScreenShareNotice.tsx +83 -8
  253. package/template/src/subComponents/SelectDevice.tsx +404 -61
  254. package/template/src/subComponents/SelectDeviceSettings.backup.tsx +207 -0
  255. package/template/src/subComponents/SelectOAuth.tsx +9 -8
  256. package/template/src/subComponents/SidePanelButtons.ts +0 -3
  257. package/template/src/subComponents/SidePanelHeader.tsx +112 -0
  258. package/template/src/subComponents/ToastConfig.tsx +150 -10
  259. package/template/src/subComponents/chat/ChatParticipants.tsx +188 -79
  260. package/template/src/subComponents/livestream/CurrentLiveStreamRequestsView.tsx +97 -34
  261. package/template/src/subComponents/livestream/controls/LocalRaiseHand.tsx +29 -33
  262. package/template/src/subComponents/livestream/controls/RemoteLiveStreamApprovedRequestRecall.tsx +8 -8
  263. package/template/src/subComponents/livestream/controls/RemoteLiveStreamRequestApprove.tsx +24 -11
  264. package/template/src/subComponents/livestream/controls/RemoteLiveStreamRequestReject.tsx +17 -10
  265. package/template/src/subComponents/recording/useRecording.tsx +81 -29
  266. package/template/src/subComponents/screenshare/ScreenshareButton.tsx +52 -70
  267. package/template/src/subComponents/screenshare/ScreenshareConfigure.native.tsx +23 -12
  268. package/template/src/subComponents/screenshare/ScreenshareConfigure.tsx +44 -19
  269. package/template/src/theme/index.ts +46 -0
  270. package/template/src/utils/PlatformWrapper.tsx +21 -0
  271. package/template/src/utils/SdkEvents.ts +23 -14
  272. package/template/src/utils/SdkMethodEvents.ts +81 -0
  273. package/template/src/utils/common.tsx +155 -1
  274. package/template/src/utils/hexadecimalTransparency.ts +108 -0
  275. package/template/src/utils/index.tsx +19 -0
  276. package/template/src/utils/isMobileOrTablet.ts +7 -2
  277. package/template/src/utils/pendingStateUpdateHelper.ts +19 -0
  278. package/template/src/utils/useActiveSpeaker.ts +42 -0
  279. package/template/src/utils/{useCreateMeeting.ts → useCreateRoom.ts} +19 -14
  280. package/template/src/utils/{useButtonTemplate.tsx → useFocus.tsx} +19 -16
  281. package/template/src/utils/useGetMeetingPhrase.ts +10 -10
  282. package/template/src/utils/useIsAudioEnabled.ts +3 -3
  283. package/template/src/utils/useIsHandRaised.ts +13 -0
  284. package/template/src/utils/useIsPSTN.ts +3 -3
  285. package/template/src/utils/useIsVideoEnabled.ts +3 -3
  286. package/template/src/utils/{useJoinMeeting.ts → useJoinRoom.ts} +27 -21
  287. package/template/src/utils/useMutePSTN.ts +2 -2
  288. package/template/src/utils/useMuteToggleLocal.ts +58 -5
  289. package/template/src/utils/useRemoteEndCall.ts +4 -4
  290. package/template/src/utils/useRemoteEndScreenshare.ts +26 -0
  291. package/template/src/utils/useRemoteMute.ts +7 -7
  292. package/template/src/utils/useRemoteRequest.ts +84 -0
  293. package/template/src/utils/useSwitchCamera.native.tsx +25 -0
  294. package/template/src/utils/useSwitchCamera.tsx +19 -0
  295. package/template/src/utils/useToolbar.tsx +59 -0
  296. package/template/web/index.html +5 -0
  297. package/template/webpack.commons.js +13 -8
  298. package/template/webpack.rsdk.config.js +1 -2
  299. package/template/webpack.web.config.js +1 -0
  300. package/template/agora-rn-uikit/src/Contexts/RenderContext.tsx +0 -10
  301. package/template/src/assets/icons.ts +0 -102
  302. package/template/src/components/chat-ui/useChatUIControl.tsx +0 -69
  303. package/template/src/components/participants/MeParticipant.tsx +0 -38
  304. package/template/src/components/participants/RemoteParticipants.tsx +0 -71
  305. package/template/src/pages/video-call/CustomUserContextHolder.tsx +0 -20
@@ -13,9 +13,11 @@ import {createContext} from 'react';
13
13
 
14
14
  interface DeviceContext {
15
15
  selectedCam: string;
16
- setSelectedCam: (cam: string) => void;
16
+ setSelectedCam: (cam: string) => Promise<any>;
17
17
  selectedMic: string;
18
- setSelectedMic: (mic: string) => void;
18
+ setSelectedMic: (mic: string) => Promise<any>;
19
+ selectedSpeaker: string;
20
+ setSelectedSpeaker: (speaker: string) => Promise<any>;
19
21
  deviceList: MediaDeviceInfo[];
20
22
  setDeviceList: (devices: MediaDeviceInfo[]) => void;
21
23
  }
@@ -23,9 +25,11 @@ interface DeviceContext {
23
25
  const DeviceContext = createContext<DeviceContext>({
24
26
  selectedCam: '',
25
27
  selectedMic: '',
28
+ selectedSpeaker: '',
26
29
  deviceList: [],
27
- setSelectedCam: () => {},
28
- setSelectedMic: () => {},
30
+ setSelectedCam: async () => {},
31
+ setSelectedMic: async () => {},
32
+ setSelectedSpeaker: async () => {},
29
33
  setDeviceList: () => {},
30
34
  });
31
35
  export default DeviceContext;
@@ -9,39 +9,195 @@
9
9
  information visit https://appbuilder.agora.io.
10
10
  *********************************************
11
11
  */
12
- import React, {useContext, useEffect} from 'react';
13
- import {RtcContext} from '../../agora-rn-uikit';
12
+ import React, {useContext, useEffect, useRef} from 'react';
13
+ import {StyleSheet} from 'react-native';
14
+ import PrimaryButton from '../atoms/PrimaryButton';
15
+ import {
16
+ RtcContext,
17
+ UidType,
18
+ useLocalUid,
19
+ DispatchContext,
20
+ } from '../../agora-rn-uikit';
14
21
  import events from '../rtm-events-api';
15
22
  import {controlMessageEnum} from '../components/ChatContext';
23
+ import Toast from '../../react-native-toast-message';
24
+ import TertiaryButton from '../atoms/TertiaryButton';
25
+ import {useContent} from 'customization-api';
26
+ import {useParams} from '../components/Router';
27
+ import StorageContext from './StorageContext';
28
+ import {isWebInternal} from '../utils/common';
29
+ import LocalEventEmitter, {
30
+ LocalEventsEnum,
31
+ } from '../rtm-events-api/LocalEvents';
16
32
 
17
33
  interface Props {
18
34
  children: React.ReactNode;
19
35
  }
20
36
 
21
37
  const EventsConfigure: React.FC<Props> = (props) => {
22
- const {RtcEngine, dispatch} = useContext(RtcContext);
38
+ const {setStore} = useContext(StorageContext);
39
+ const {RtcEngineUnsafe} = useContext(RtcContext);
40
+ const {dispatch} = useContext(DispatchContext);
41
+ const {defaultContent} = useContent();
42
+ const defaultContentRef = useRef({defaultContent});
43
+ const {phrase} = useParams<{phrase: string}>();
44
+ const localUid = useLocalUid();
45
+ const activeSpeakerUid = useRef(undefined);
23
46
  useEffect(() => {
24
- events.on(controlMessageEnum.muteVideo, () => {
25
- RtcEngine.muteLocalVideoStream(true);
47
+ defaultContentRef.current.defaultContent = defaultContent;
48
+ }, [defaultContent]);
49
+
50
+ const emitActiveSpeaker = (uid: UidType) => {
51
+ if (uid !== activeSpeakerUid.current) {
52
+ activeSpeakerUid.current = uid;
53
+ LocalEventEmitter.emit(LocalEventsEnum.ACTIVE_SPEAKER, uid);
54
+ }
55
+ };
56
+
57
+ useEffect(() => {
58
+ RtcEngineUnsafe.addListener('AudioVolumeIndication', (...args) => {
59
+ // console.log('-- AudioVolumeCallback', args);
60
+ const [speakers, totalVolume] = args;
61
+ if (speakers[0]?.uid === 0) {
62
+ //callback for local user
63
+ const isLocalUserSpeaking = speakers[0].vad; //1-speaking , 0-not speaking
64
+ const localUserVolumeLevel = speakers[0].volume;
65
+ // vad value is not consistent while speaking so using volume level
66
+ if (localUserVolumeLevel > 0) {
67
+ emitActiveSpeaker(localUid);
68
+ } else {
69
+ //undefined
70
+ emitActiveSpeaker(undefined);
71
+ }
72
+ } else {
73
+ // remote users callback, this will be handeled in ActiveSpeaker callback(367)
74
+ // const highestvolumeObj = speakers.reduce(function (prev, current) {
75
+ // return prev.volume > current.volume ? prev : current;
76
+ // }, null);
77
+ }
78
+ });
79
+
80
+ RtcEngineUnsafe.addListener('ActiveSpeaker', (...args) => {
81
+ // used as a callback from the web bridge as well remote users
82
+ emitActiveSpeaker(args[0]);
83
+ });
84
+ //user joined event listener
85
+ // events.on(controlMessageEnum.newUserJoined, ({payload}) => {
86
+ // const data = JSON.parse(payload);
87
+ // if (data?.name) {
88
+ // Toast.show({
89
+ // text1: `${trimText(data.name)} has joined the call`,
90
+ // visibilityTime: 3000,
91
+ // type: 'info',
92
+ // primaryBtn: null,
93
+ // secondaryBtn: null,
94
+ // });
95
+ // }
96
+ // });
97
+ events.on(controlMessageEnum.muteVideo, async ({payload, sender}) => {
98
+ Toast.show({
99
+ type: 'info',
100
+ // text1: `${
101
+ // defaultContentRef.current.defaultContent[sender].name || 'The host'
102
+ // } muted you.`,
103
+ text1: 'The host has muted your video.',
104
+ visibilityTime: 3000,
105
+ primaryBtn: null,
106
+ secondaryBtn: null,
107
+ });
108
+ isWebInternal()
109
+ ? await RtcEngineUnsafe.muteLocalVideoStream(true)
110
+ : await RtcEngineUnsafe.enableLocalVideo(false);
26
111
  dispatch({
27
112
  type: 'LocalMuteVideo',
28
113
  value: [0],
29
114
  });
30
115
  });
31
- events.on(controlMessageEnum.muteAudio, () => {
32
- RtcEngine.muteLocalAudioStream(true);
116
+ events.on(controlMessageEnum.muteAudio, ({sender}) => {
117
+ Toast.show({
118
+ type: 'info',
119
+ // text1: `${
120
+ // defaultContentRef.current.defaultContent[sender].name || 'The host'
121
+ // } muted you.`,
122
+ text1: 'The host has muted your audio.',
123
+ visibilityTime: 3000,
124
+ primaryBtn: null,
125
+ secondaryBtn: null,
126
+ });
127
+ RtcEngineUnsafe.muteLocalAudioStream(true);
33
128
  dispatch({
34
129
  type: 'LocalMuteAudio',
35
130
  value: [0],
36
131
  });
37
132
  });
38
133
  events.on(controlMessageEnum.kickUser, () => {
39
- dispatch({
40
- type: 'EndCall',
41
- value: [],
134
+ Toast.show({
135
+ type: 'info',
136
+ text1: 'The host has removed you from the room.',
137
+ visibilityTime: 5000,
138
+ primaryBtn: null,
139
+ secondaryBtn: null,
140
+ });
141
+ setTimeout(() => {
142
+ dispatch({
143
+ type: 'EndCall',
144
+ value: [],
145
+ });
146
+ }, 5000);
147
+ });
148
+ events.on(controlMessageEnum.requestAudio, () => {
149
+ Toast.show({
150
+ type: 'info',
151
+ text1: 'The host has requested you to speak',
152
+ visibilityTime: 3000,
153
+ primaryBtn: (
154
+ <PrimaryButton
155
+ containerStyle={style.primaryBtn}
156
+ textStyle={{fontWeight: '600', fontSize: 16, paddingLeft: 0}}
157
+ text="UNMUTE"
158
+ onPress={() => {
159
+ RtcEngineUnsafe.muteLocalAudioStream(false);
160
+ dispatch({
161
+ type: 'LocalMuteAudio',
162
+ value: [1],
163
+ });
164
+ Toast.hide();
165
+ }}
166
+ />
167
+ ),
168
+ secondaryBtn: SecondaryBtn,
42
169
  });
43
170
  });
171
+ events.on(controlMessageEnum.requestVideo, () => {
172
+ Toast.show({
173
+ type: 'info',
174
+ text1: 'The host has asked you to start your video.',
175
+ visibilityTime: 3000,
176
+ primaryBtn: (
177
+ <PrimaryButton
178
+ containerStyle={style.primaryBtn}
179
+ textStyle={style.primaryBtnText}
180
+ text="UNMUTE"
181
+ onPress={async () => {
182
+ isWebInternal()
183
+ ? await RtcEngineUnsafe.muteLocalVideoStream(false)
184
+ : await RtcEngineUnsafe.enableLocalVideo(true);
185
+ dispatch({
186
+ type: 'LocalMuteVideo',
187
+ value: [1],
188
+ });
189
+ Toast.hide();
190
+ }}
191
+ />
192
+ ),
193
+ secondaryBtn: SecondaryBtn,
194
+ });
195
+ });
196
+
44
197
  return () => {
198
+ //events.off(controlMessageEnum.newUserJoined);
199
+ events.off(controlMessageEnum.requestAudio);
200
+ events.off(controlMessageEnum.requestVideo);
45
201
  events.off(controlMessageEnum.muteVideo);
46
202
  events.off(controlMessageEnum.muteAudio);
47
203
  events.off(controlMessageEnum.kickUser);
@@ -52,3 +208,29 @@ const EventsConfigure: React.FC<Props> = (props) => {
52
208
  };
53
209
 
54
210
  export default EventsConfigure;
211
+
212
+ const style = StyleSheet.create({
213
+ secondaryBtn: {marginLeft: 16, height: 40, paddingVertical: 5},
214
+ primaryBtn: {
215
+ maxWidth: 109,
216
+ minWidth: 109,
217
+ height: 40,
218
+ borderRadius: 4,
219
+ paddingVertical: 5,
220
+ paddingHorizontal: 12,
221
+ },
222
+ primaryBtnText: {
223
+ fontWeight: '600',
224
+ fontSize: 16,
225
+ paddingLeft: 0,
226
+ },
227
+ });
228
+ const SecondaryBtn = (
229
+ <TertiaryButton
230
+ containerStyle={style.secondaryBtn}
231
+ text="LATER"
232
+ onPress={() => {
233
+ Toast.hide();
234
+ }}
235
+ />
236
+ );
@@ -20,7 +20,7 @@ import {setContext} from '@apollo/client/link/context';
20
20
  // import useMount from './useMount';
21
21
  import React, {createContext, useContext, useRef} from 'react';
22
22
  import StorageContext from './StorageContext';
23
- import AsyncStorage from '@react-native-community/async-storage';
23
+ import AsyncStorage from '@react-native-async-storage/async-storage'; //'@react-native-community/async-storage';
24
24
 
25
25
  export const GraphQLContext = createContext<{
26
26
  client: ApolloClient<NormalizedCacheObject>;
@@ -9,12 +9,13 @@
9
9
  information visit https://appbuilder.agora.io.
10
10
  *********************************************
11
11
  */
12
- import {layoutComponent, useRtc} from 'customization-api';
13
- import React, {useMemo, useState} from 'react';
14
- import {View, StyleSheet, Dimensions, Pressable} from 'react-native';
15
- import {isWebInternal} from '../utils/common';
12
+ import {layoutComponent, useContent} from 'customization-api';
13
+ import React, {useContext, useMemo, useState} from 'react';
14
+ import {View, StyleSheet, Pressable, Text} from 'react-native';
15
+ import {isWebInternal, useIsDesktop} from '../utils/common';
16
16
  import {useSetPinnedLayout} from '../pages/video-call/DefaultLayouts';
17
17
  import RenderComponent from '../pages/video-call/RenderComponent';
18
+ import {ClientRole, DispatchContext, PropsContext} from '../../agora-rn-uikit';
18
19
  const layout = (len: number, isDesktop: boolean = true) => {
19
20
  const rows = Math.round(Math.sqrt(len));
20
21
  const cols = Math.ceil(len / rows);
@@ -34,35 +35,38 @@ const layout = (len: number, isDesktop: boolean = true) => {
34
35
  };
35
36
 
36
37
  const GridVideo: layoutComponent = ({renderData}) => {
37
- const {dispatch} = useRtc();
38
- let onLayout = (e: any) => {
39
- setDim([
40
- e.nativeEvent.layout.width,
41
- e.nativeEvent.layout.height,
42
- e.nativeEvent.layout.width > e.nativeEvent.layout.height,
43
- ]);
44
- };
45
- const [dim, setDim] = useState<[number, number, boolean]>([
46
- Dimensions.get('window').width,
47
- Dimensions.get('window').height,
48
- Dimensions.get('window').width > Dimensions.get('window').height,
49
- ]);
50
- const isDesktop = dim[0] > dim[1] + 100;
38
+ const {dispatch} = useContext(DispatchContext);
39
+ const {rtcProps} = useContext(PropsContext);
40
+ const {activeUids} = useContent();
41
+ const isDesktop = useIsDesktop();
51
42
 
52
43
  let {matrix, dims} = useMemo(
53
- () => layout(renderData.length, isDesktop),
54
- [renderData.length, isDesktop],
44
+ () => layout(renderData.length, isDesktop()),
45
+ [renderData.length, isDesktop()],
55
46
  );
56
47
 
57
48
  const setPinnedLayout = useSetPinnedLayout();
49
+
50
+ //livestreaming audience will see this if no host joined the call
51
+ if (
52
+ $config.EVENT_MODE &&
53
+ rtcProps?.role === ClientRole.Audience &&
54
+ activeUids.length === 0
55
+ ) {
56
+ return (
57
+ <View style={style.infoTextContainer}>
58
+ <Text style={style.infoTextStyle}>Waiting for the host to join...</Text>
59
+ </View>
60
+ );
61
+ }
62
+
58
63
  return (
59
- <View
60
- style={[style.full, {paddingHorizontal: isDesktop ? 50 : 0}]}
61
- onLayout={onLayout}>
64
+ <View style={[style.full]}>
62
65
  {matrix.map((r, ridx) => (
63
66
  <View style={style.gridRow} key={ridx}>
64
67
  {r.map((c, cidx) => (
65
68
  <Pressable
69
+ disabled={renderData.length === 1}
66
70
  onPress={() => {
67
71
  if (!(ridx === 0 && cidx === 0)) {
68
72
  dispatch({
@@ -77,7 +81,25 @@ const GridVideo: layoutComponent = ({renderData}) => {
77
81
  marginHorizontal: 'auto',
78
82
  }}
79
83
  key={cidx}>
80
- <View style={style.gridVideoContainerInner}>
84
+ <View
85
+ style={[
86
+ style.gridVideoContainerInner,
87
+ //if only one item no margin required
88
+ r?.length > 1
89
+ ? //first item will have marginRight in the row
90
+ cidx === 0
91
+ ? {marginRight: 4}
92
+ : //last item will have marginLeft in the row
93
+ cidx === r?.length - 1
94
+ ? {marginLeft: 4}
95
+ : //middle item will have marginHorizontal
96
+ {marginHorizontal: 4}
97
+ : //if more than one row than add marginHorizontal
98
+ //for ex: 7 people in the call with 3 column layout. last person tile should be aligned propert
99
+ ridx > 1
100
+ ? {marginHorizontal: 4}
101
+ : {},
102
+ ]}>
81
103
  <RenderComponent uid={renderData[ridx * dims.c + cidx]} />
82
104
  </View>
83
105
  </Pressable>
@@ -91,39 +113,32 @@ const GridVideo: layoutComponent = ({renderData}) => {
91
113
  const style = StyleSheet.create({
92
114
  full: {
93
115
  flex: 1,
94
- // padding: 20,
95
116
  },
96
117
  gridRow: {
97
118
  flex: 1,
98
119
  flexDirection: 'row',
99
120
  width: '100%',
100
- paddingVertical: 10,
121
+ paddingVertical: 4,
101
122
  },
102
123
  gridVideoContainerInner: {
103
- // borderColor: '#fff',
104
- // borderWidth:2,
105
- // width: '100%',
106
- borderRadius: 15,
124
+ //borderRadius: 12,
107
125
  flex: 1,
108
126
  overflow: 'hidden',
109
- // margin: 1,
110
- marginHorizontal: 10,
111
127
  },
112
- MicBackdrop: {
113
- width: 20,
114
- height: 20,
115
- borderRadius: 10,
116
- alignSelf: 'center',
117
- marginHorizontal: 10,
118
- marginRight: 20,
119
- backgroundColor: $config.SECONDARY_FONT_COLOR,
120
- display: 'flex',
128
+ infoTextContainer: {
129
+ flex: 1,
130
+ backgroundColor: $config.VIDEO_AUDIO_TILE_COLOR,
121
131
  justifyContent: 'center',
132
+ marginHorizontal: 'auto',
133
+ marginVertical: 4,
122
134
  },
123
- MicIcon: {
124
- width: '80%',
125
- height: '80%',
126
- alignSelf: 'center',
135
+ infoTextStyle: {
136
+ fontFamily: 'Source Sans Pro',
137
+ fontWeight: '600',
138
+ fontSize: 32,
139
+ color: $config.VIDEO_AUDIO_TILE_AVATAR_COLOR,
140
+ textAlign: 'center',
141
+ padding: 12,
127
142
  },
128
143
  });
129
144
  export default GridVideo;
@@ -9,27 +9,76 @@
9
9
  information visit https://appbuilder.agora.io.
10
10
  *********************************************
11
11
  */
12
- import React from 'react';
13
- import {View, Text, StyleSheet} from 'react-native';
12
+ import React, {useRef, useState} from 'react';
13
+ import {View, StyleSheet, useWindowDimensions} from 'react-native';
14
14
  import SecondaryButton from '../atoms/SecondaryButton';
15
15
  import {useString} from '../utils/useString';
16
16
  import useRemoteMute, {MUTE_REMOTE_TYPE} from '../utils/useRemoteMute';
17
+ import TertiaryButton from '../atoms/TertiaryButton';
18
+ import Spacer from '../atoms/Spacer';
19
+ import RemoteMutePopup from '../subComponents/RemoteMutePopup';
20
+ import {calculatePosition} from '../utils/common';
17
21
 
18
22
  export interface MuteAllAudioButtonProps {
19
23
  render?: (onPress: () => void) => JSX.Element;
20
24
  }
21
25
 
22
26
  export const MuteAllAudioButton = (props: MuteAllAudioButtonProps) => {
27
+ const [showAudioMuteModal, setShowAudioMuteModal] = useState(false);
28
+ const audioBtnRef = useRef(null);
29
+ const [modalPosition, setModalPosition] = useState({});
23
30
  const muteRemoteAudio = useRemoteMute();
24
31
  //commented for v1 release
25
32
  //const muteAllAudioButton = useString('muteAllAudioButton')();
26
- const muteAllAudioButton = 'Mute all audios';
27
- const onPress = () => muteRemoteAudio(MUTE_REMOTE_TYPE.audio);
28
-
33
+ const muteAllAudioButton = 'Mute all';
34
+ const onPressAction = () => muteRemoteAudio(MUTE_REMOTE_TYPE.audio);
35
+ const {width: globalWidth, height: globalHeight} = useWindowDimensions();
36
+ const showAudioModal = () => {
37
+ audioBtnRef?.current?.measure(
38
+ (_fx, _fy, localWidth, localHeight, px, py) => {
39
+ const data = calculatePosition({
40
+ px,
41
+ py,
42
+ localHeight,
43
+ localWidth,
44
+ globalHeight,
45
+ globalWidth,
46
+ extra: {
47
+ bottom: 10,
48
+ left: localWidth / 2,
49
+ right: -(localWidth / 2),
50
+ },
51
+ popupWidth: 290,
52
+ });
53
+ setModalPosition(data);
54
+ setShowAudioMuteModal(true);
55
+ },
56
+ );
57
+ };
58
+ const onPress = () => {
59
+ showAudioModal();
60
+ };
29
61
  return props?.render ? (
30
62
  props.render(onPress)
31
63
  ) : (
32
- <SecondaryButton onPress={onPress} text={muteAllAudioButton} />
64
+ <>
65
+ <RemoteMutePopup
66
+ type="audio"
67
+ actionMenuVisible={showAudioMuteModal}
68
+ setActionMenuVisible={setShowAudioMuteModal}
69
+ name={null}
70
+ modalPosition={modalPosition}
71
+ onMutePress={() => {
72
+ onPressAction();
73
+ setShowAudioMuteModal(false);
74
+ }}
75
+ />
76
+ <TertiaryButton
77
+ setRef={(ref) => (audioBtnRef.current = ref)}
78
+ onPress={onPress}
79
+ text={muteAllAudioButton}
80
+ />
81
+ </>
33
82
  );
34
83
  };
35
84
 
@@ -37,53 +86,83 @@ export interface MuteAllVideoButtonProps {
37
86
  render?: (onPress: () => void) => JSX.Element;
38
87
  }
39
88
  export const MuteAllVideoButton = (props: MuteAllVideoButtonProps) => {
89
+ const [showVideoMuteModal, setShowVideoMuteModal] = useState(false);
90
+ const videoBtnRef = useRef(null);
91
+ const [modalPosition, setModalPosition] = useState({});
40
92
  const muteRemoteVideo = useRemoteMute();
41
-
93
+ const {width: globalWidth, height: globalHeight} = useWindowDimensions();
42
94
  //commented for v1 release
43
95
  //const muteAllVideoButton = useString('muteAllVideoButton')();
44
- const muteAllVideoButton = 'Mute all videos';
45
- const onPress = () => muteRemoteVideo(MUTE_REMOTE_TYPE.video);
46
-
96
+ const muteAllVideoButton = 'Turn off all cameras';
97
+ const onPressAction = () => muteRemoteVideo(MUTE_REMOTE_TYPE.video);
98
+ const showVideoModal = () => {
99
+ videoBtnRef?.current?.measure(
100
+ (_fx, _fy, localWidth, localHeight, px, py) => {
101
+ const data = calculatePosition({
102
+ px,
103
+ py,
104
+ localHeight,
105
+ localWidth,
106
+ globalHeight,
107
+ globalWidth,
108
+ extra: {
109
+ bottom: 10,
110
+ left: globalWidth < 720 ? 0 : localWidth / 2,
111
+ right: globalHeight < 720 ? 0 : -(localWidth / 2),
112
+ },
113
+ popupWidth: 290,
114
+ });
115
+ setModalPosition(data);
116
+ setShowVideoMuteModal(true);
117
+ },
118
+ );
119
+ };
120
+ const onPress = () => {
121
+ showVideoModal();
122
+ };
47
123
  return props?.render ? (
48
124
  props.render(onPress)
49
125
  ) : (
50
- <SecondaryButton onPress={onPress} text={muteAllVideoButton} />
126
+ <>
127
+ <RemoteMutePopup
128
+ type="video"
129
+ actionMenuVisible={showVideoMuteModal}
130
+ setActionMenuVisible={setShowVideoMuteModal}
131
+ name={null}
132
+ modalPosition={modalPosition}
133
+ onMutePress={() => {
134
+ onPressAction();
135
+ setShowVideoMuteModal(false);
136
+ }}
137
+ />
138
+ <TertiaryButton
139
+ setRef={(ref) => (videoBtnRef.current = ref)}
140
+ onPress={onPress}
141
+ text={muteAllVideoButton}
142
+ />
143
+ </>
51
144
  );
52
145
  };
53
146
 
54
147
  const HostControlView = () => {
55
148
  //commented for v1 release
56
149
  //const hostControlsLabel = useString('hostControlsLabel')();
57
- const hostControlsLabel = 'Host Controls';
150
+
58
151
  return (
59
- <>
60
- <Text style={style.heading}>{hostControlsLabel}</Text>
61
- <View>
62
- <View style={style.btnContainer}>
63
- <MuteAllAudioButton />
64
- </View>
65
- {!$config.AUDIO_ROOM && (
66
- <View style={style.btnContainer}>
67
- <MuteAllVideoButton />
68
- </View>
69
- )}
70
- </View>
71
- </>
152
+ <View style={style.container}>
153
+ {!$config.AUDIO_ROOM && <MuteAllVideoButton />}
154
+ <Spacer horizontal size={16} />
155
+ <MuteAllAudioButton />
156
+ </View>
72
157
  );
73
158
  };
74
159
 
75
160
  const style = StyleSheet.create({
76
- heading: {
77
- fontSize: 20,
78
- fontWeight: '700',
79
- color: $config.PRIMARY_FONT_COLOR,
80
- // marginBottom: 20,
81
- alignSelf: 'center',
82
- },
83
- btnContainer: {
84
- alignItems: 'center',
85
- marginVertical: 15,
161
+ container: {
162
+ flexDirection: 'row',
163
+ justifyContent: 'center',
86
164
  },
165
+ btn: {},
87
166
  });
88
167
 
89
168
  export default HostControlView;