agora-appbuilder-core 2.3.0-beta.15 → 2.3.0-beta.18

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "agora-appbuilder-core",
3
- "version": "2.3.0-beta.15",
3
+ "version": "2.3.0-beta.18",
4
4
  "description": "React Native template for RTE app builder",
5
5
  "main": "index.js",
6
6
  "files": [
@@ -258,6 +258,10 @@ const RtcConfigure = (props: {children: React.ReactNode}) => {
258
258
  */
259
259
  const dequeVideo = useCallback(
260
260
  (state: RenderStateInterface, newMaxUid: UidType) => {
261
+ if (state?.renderPosition?.indexOf(newMaxUid) === -1) {
262
+ //skip the update if new max uid is not joined yet.
263
+ return {};
264
+ }
261
265
  let renderPosition: RenderStateInterface['renderPosition'] = [
262
266
  ...state.renderPosition,
263
267
  ];
@@ -46,3 +46,7 @@ export {default as VideocallScreen} from '../src/pages/video-call/VideoCallScree
46
46
 
47
47
  //Sidepanel buttons
48
48
  export {SidePanelButtonsArray} from '../src/subComponents/SidePanelButtons';
49
+ export {
50
+ ImageIcon as UiKitImageIcon,
51
+ MaxVideoView as UiKitMaxVideoView,
52
+ } from '../agora-rn-uikit';
@@ -19,6 +19,7 @@ import {
19
19
  } from '../agora-rn-uikit';
20
20
  import {i18nInterface} from '../src/language/i18nTypes';
21
21
  import {IconsInterface} from '../agora-rn-uikit/src/Controls/Icons';
22
+ export type {RenderInterface, RenderStateInterface, UidType};
22
23
  export type {
23
24
  ChatTextInputProps,
24
25
  ChatSendButtonProps,
@@ -57,4 +57,13 @@ export {
57
57
  export {ToggleState} from '../agora-rn-uikit/src/Contexts/PropsContext';
58
58
 
59
59
  //export common function
60
- export * from '../src/utils/common';
60
+ export {
61
+ hasBrandLogo,
62
+ isAndroid,
63
+ isArray,
64
+ isIOS,
65
+ isValidReactComponent,
66
+ isWeb,
67
+ shouldAuthenticate,
68
+ } from '../src/utils/common';
69
+ export {useLocalUid} from '../agora-rn-uikit';
@@ -353,14 +353,14 @@ class Toast extends Component {
353
353
 
354
354
  const translateY = animation.interpolate({
355
355
  inputRange: [0, 1, 2],
356
- outputRange: [0, 1, 0]
356
+ outputRange
357
357
  });
358
358
 
359
359
  return [
360
360
  styles.base,
361
361
  styles[position],
362
362
  {
363
- opacity: translateY
363
+ transform: [{ translateY }]
364
364
  }
365
365
  ];
366
366
  }
@@ -378,11 +378,7 @@ class Toast extends Component {
378
378
  <Animated.View
379
379
  testID='animatedView'
380
380
  onLayout={this.onLayout}
381
- style={[
382
- baseStyle,
383
- style,
384
- { zIndex: 100, display: this.state.isVisible || this.state.inProgress ? 'flex' : 'none' }
385
- ]} //added zindex
381
+ style={[baseStyle, style, { zIndex: 100 }]} //added zindex
386
382
  {...this.panResponder.panHandlers}>
387
383
  {this.renderContent(this.props)}
388
384
  </Animated.View>
@@ -381,7 +381,7 @@ class Toast extends Component {
381
381
  style={[
382
382
  baseStyle,
383
383
  style,
384
- { zIndex: 100, display: this.state.isVisible ? 'flex' : 'none', backgroundColor:'red' }
384
+ { zIndex: 100, display: this.state.isVisible ? 'flex' : 'none' }
385
385
  ]} //added zindex
386
386
  {...this.panResponder.panHandlers}>
387
387
  {this.renderContent(this.props)}
@@ -9,7 +9,7 @@ export default StyleSheet.create({
9
9
  right: 0
10
10
  },
11
11
  top: {
12
- top: 30
12
+ top: 0
13
13
  },
14
14
  bottom: {
15
15
  bottom: 0
@@ -0,0 +1,17 @@
1
+ import { StyleSheet } from 'react-native';
2
+
3
+ export default StyleSheet.create({
4
+ base: {
5
+ position: 'absolute',
6
+ alignItems: 'center',
7
+ justifyContent: 'center',
8
+ left: 0,
9
+ right: 0
10
+ },
11
+ top: {
12
+ top: 30
13
+ },
14
+ bottom: {
15
+ bottom: 0
16
+ }
17
+ });
@@ -32,14 +32,14 @@ enum ChatMessageActionEnum {
32
32
  interface ChatMessagesProviderProps {
33
33
  children: React.ReactNode;
34
34
  }
35
- interface messageInterface {
35
+ export interface messageInterface {
36
36
  createdTimestamp: number;
37
37
  updatedTimestamp?: number;
38
38
  msg: string;
39
39
  msgId: string;
40
40
  isDeleted: boolean;
41
41
  }
42
- interface messageStoreInterface extends messageInterface {
42
+ export interface messageStoreInterface extends messageInterface {
43
43
  uid: UidType;
44
44
  }
45
45
 
@@ -12,6 +12,7 @@ export interface ScreenShareObjectInterface {
12
12
  [key: string | number]: {
13
13
  name: string;
14
14
  isActive: boolean;
15
+ ts: number;
15
16
  };
16
17
  }
17
18
  export interface ScreenShareContextInterface {
@@ -33,6 +34,7 @@ const ScreenShareProvider = (props: ScreenShareProviderProps) => {
33
34
  [rtcProps?.screenShareUid]: {
34
35
  name: '',
35
36
  isActive: false,
37
+ ts: 0,
36
38
  },
37
39
  });
38
40
 
@@ -15,12 +15,12 @@ interface IEventPayloadBase {
15
15
 
16
16
  interface IEventPayloadWithoutAttributes extends IEventPayloadBase {
17
17
  level?: never;
18
- value: string;
18
+ value: any;
19
19
  }
20
20
 
21
21
  interface IEventPayloadWithAttributes extends IEventPayloadBase {
22
22
  level: 2 | 3;
23
- value: string;
23
+ value: any;
24
24
  }
25
25
 
26
26
  export type EventPayload =
@@ -40,7 +40,7 @@ export enum EventLevel {
40
40
  interface dataPayload {
41
41
  action: string;
42
42
  level: 1 | 2 | 3;
43
- value: string;
43
+ value: any;
44
44
  }
45
45
  interface EvtCbPayload {
46
46
  payload: dataPayload;
@@ -156,11 +156,17 @@ const RecordingProvider = (props: RecordingProviderProps) => {
156
156
  // 2. set the local recording state to true to update the UI
157
157
  setRecordingActive(true);
158
158
  // 3. set the presenter mode if screen share is active
159
- const activeScreenshareUid = Object.keys(screenShareData).find(
160
- (key) => screenShareData[key]?.isActive,
161
- );
159
+ // 3.a Get the most recent screenshare uid
160
+ const sorted = Object.entries(screenShareData)
161
+ .filter((el) => el[1]?.ts && el[1].ts > 0 && el[1]?.isActive)
162
+ .sort((a, b) => b[1].ts - a[1].ts);
163
+
164
+ const activeScreenshareUid = sorted.length > 0 ? sorted[0][0] : 0;
162
165
  if (activeScreenshareUid) {
163
- console.log('screenshare: Executing presenter query');
166
+ console.log(
167
+ 'screenshare: Executing presenter query for screenuid',
168
+ activeScreenshareUid,
169
+ );
164
170
  executePresenterQuery(parseInt(activeScreenshareUid));
165
171
  } else {
166
172
  executeNormalQuery();
@@ -20,7 +20,14 @@ function useRecordingLayoutQuery() {
20
20
  const [setPresenterQuery] = useMutation(SET_PRESENTER);
21
21
  const [setNormalQuery] = useMutation(SET_NORMAL);
22
22
  const {phrase} = useParams<any>();
23
-
23
+ /**
24
+ * @param screenShareUid
25
+ * Default : Grid
26
+ * Below query changes the layout to vertical and passed UID is maxed view
27
+ * This should be called only when screenshare is actively going on
28
+ * and we want that as the main view
29
+ * https://docs.agora.io/en/cloud-recording/cloud_recording_layout?platform=RESTful
30
+ */
24
31
  const executePresenterQuery = (screenShareUid: UidType) => {
25
32
  setPresenterQuery({
26
33
  variables: {
@@ -20,15 +20,7 @@ import useUserList from '../../utils/useUserList';
20
20
  import {useScreenContext} from '../../components/contexts/ScreenShareContext';
21
21
  import {useString} from '../../utils/useString';
22
22
  import CustomEvents from '../../custom-events';
23
- import {EventNames} from '../../rtm-events';
24
-
25
- function usePrevious(value: any) {
26
- const ref = useRef();
27
- useEffect(() => {
28
- ref.current = value;
29
- });
30
- return ref.current;
31
- }
23
+ import {EventNames, EventActions} from '../../rtm-events';
32
24
 
33
25
  export const ScreenshareConfigure = (props: {children: React.ReactNode}) => {
34
26
  const rtc = useContext(RtcContext);
@@ -40,7 +32,6 @@ export const ScreenshareConfigure = (props: {children: React.ReactNode}) => {
40
32
  // const userText = useString('remoteUserDefaultLabel')();
41
33
  const getScreenShareName = (name: string) => `${name}'s screenshare`;
42
34
  const userText = 'User';
43
- const prevRenderPosition = usePrevious({renderPosition});
44
35
  const setPinnedLayout = useSetPinnedLayout();
45
36
  const changeLayout = useChangeDefaultLayout();
46
37
 
@@ -58,9 +49,8 @@ export const ScreenshareConfigure = (props: {children: React.ReactNode}) => {
58
49
  value: [screenShareUid],
59
50
  });
60
51
  setPinnedLayout();
61
- }
62
- //screenshare is stopped set the layout Grid View
63
- else {
52
+ } else {
53
+ //screenshare is stopped set the layout Grid View
64
54
  changeLayout();
65
55
  }
66
56
  };
@@ -69,19 +59,38 @@ export const ScreenshareConfigure = (props: {children: React.ReactNode}) => {
69
59
  CustomEvents.on(EventNames.SCREENSHARE_ATTRIBUTE, (data) => {
70
60
  const screenUidOfUser =
71
61
  renderListRef.current.renderList[data.sender].screenUid;
72
- setScreenShareData((prevState) => {
73
- return {
74
- ...prevState,
75
- [screenUidOfUser]: {
76
- name: renderListRef.current.renderList[screenUidOfUser]?.name,
77
- isActive: data.payload.value === 'true' ? true : false,
78
- },
79
- };
80
- });
81
- //if remote user started/stopped the screenshare then change the layout to pinned/grid
82
- data.payload.value === 'true'
83
- ? triggerChangeLayout(true, screenUidOfUser)
84
- : triggerChangeLayout(false);
62
+ switch (data?.payload?.action) {
63
+ case EventActions.SCREENSHARE_STARTED:
64
+ setScreenShareData((prevState) => {
65
+ return {
66
+ ...prevState,
67
+ [screenUidOfUser]: {
68
+ name: renderListRef.current.renderList[screenUidOfUser]?.name,
69
+ isActive: true,
70
+ ts: data.payload.value || 0,
71
+ },
72
+ };
73
+ });
74
+ //if remote user started/stopped the screenshare then change the layout to pinned/grid
75
+ triggerChangeLayout(true, screenUidOfUser);
76
+ break;
77
+ case EventActions.SCREENSHARE_STOPPED:
78
+ setScreenShareData((prevState) => {
79
+ return {
80
+ ...prevState,
81
+ [screenUidOfUser]: {
82
+ name: renderListRef.current.renderList[screenUidOfUser]?.name,
83
+ isActive: false,
84
+ ts: data.payload.value || 0,
85
+ },
86
+ };
87
+ });
88
+ //if remote user started/stopped the screenshare then change the layout to pinned/grid
89
+ triggerChangeLayout(false);
90
+ break;
91
+ default:
92
+ break;
93
+ }
85
94
  });
86
95
  }, []);
87
96
 
@@ -1,3 +1,14 @@
1
+ /*
2
+ ********************************************
3
+ Copyright © 2022 Agora Lab, Inc., all rights reserved.
4
+ AppBuilder and all associated components, source code, APIs, services, and documentation
5
+ (the “Materials”) are owned by Agora Lab, Inc. and its licensors. The Materials may not be
6
+ accessed, used, modified, or distributed for any purpose without a license from Agora Lab, Inc.
7
+ Use without a license or in violation of any license terms and conditions (including use for
8
+ any purpose competitive to Agora Lab, Inc.’s business) is strictly prohibited. For more
9
+ information visit https://appbuilder.agora.io.
10
+ *********************************************
11
+ */
1
12
  import React, {useContext, useEffect, useRef, useState} from 'react';
2
13
  import {RtcContext, PropsContext, UidType} from '../../../agora-rn-uikit';
3
14
  import {ScreenshareContext} from './useScreenshare';
@@ -9,18 +20,11 @@ import {useRecording} from '../recording/useRecording';
9
20
  import {useScreenContext} from '../../components/contexts/ScreenShareContext';
10
21
  import useUserList from '../../utils/useUserList';
11
22
  import CustomEvents, {EventLevel} from '../../custom-events';
12
- import {EventNames} from '../../rtm-events';
23
+ import {EventActions, EventNames} from '../../rtm-events';
13
24
  import {IAgoraRTC} from 'agora-rtc-sdk-ng';
14
25
  import useRecordingLayoutQuery from '../recording/useRecordingLayoutQuery';
15
26
  import {useString} from '../../utils/useString';
16
-
17
- function usePrevious<T = any>(value: any) {
18
- const ref = useRef<T>();
19
- useEffect(() => {
20
- ref.current = value;
21
- });
22
- return ref.current;
23
- }
27
+ import {timeNow} from '../../rtm/utils';
24
28
 
25
29
  export const ScreenshareContextConsumer = ScreenshareContext.Consumer;
26
30
 
@@ -67,19 +71,38 @@ export const ScreenshareConfigure = (props: {children: React.ReactNode}) => {
67
71
  CustomEvents.on(EventNames.SCREENSHARE_ATTRIBUTE, (data) => {
68
72
  const screenUidOfUser =
69
73
  renderListRef.current.renderList[data.sender].screenUid;
70
- setScreenShareData((prevState) => {
71
- return {
72
- ...prevState,
73
- [screenUidOfUser]: {
74
- name: renderListRef.current.renderList[screenUidOfUser]?.name,
75
- isActive: data.payload.value === 'true' ? true : false,
76
- },
77
- };
78
- });
79
- //if remote user started/stopped the screenshare then change the layout to pinned/grid
80
- data.payload.value === 'true'
81
- ? triggerChangeLayout(true, screenUidOfUser)
82
- : triggerChangeLayout(false);
74
+ switch (data?.payload?.action) {
75
+ case EventActions.SCREENSHARE_STARTED:
76
+ setScreenShareData((prevState) => {
77
+ return {
78
+ ...prevState,
79
+ [screenUidOfUser]: {
80
+ name: renderListRef.current.renderList[screenUidOfUser]?.name,
81
+ isActive: true,
82
+ ts: data.payload.value || 0,
83
+ },
84
+ };
85
+ });
86
+ //if remote user started/stopped the screenshare then change the layout to pinned/grid
87
+ triggerChangeLayout(true, screenUidOfUser);
88
+ break;
89
+ case EventActions.SCREENSHARE_STOPPED:
90
+ setScreenShareData((prevState) => {
91
+ return {
92
+ ...prevState,
93
+ [screenUidOfUser]: {
94
+ name: renderListRef.current.renderList[screenUidOfUser]?.name,
95
+ isActive: false,
96
+ ts: data.payload.value || 0,
97
+ },
98
+ };
99
+ });
100
+ //if remote user started/stopped the screenshare then change the layout to pinned/grid
101
+ triggerChangeLayout(false);
102
+ break;
103
+ default:
104
+ break;
105
+ }
83
106
  });
84
107
  }, []);
85
108
 
@@ -90,9 +113,20 @@ export const ScreenshareConfigure = (props: {children: React.ReactNode}) => {
90
113
  console.log('STOPPED SHARING');
91
114
  executeNormalQuery();
92
115
  CustomEvents.send(EventNames.SCREENSHARE_ATTRIBUTE, {
93
- value: `${false}`,
116
+ action: EventActions.SCREENSHARE_STOPPED,
117
+ value: 0,
94
118
  level: EventLevel.LEVEL2,
95
119
  });
120
+ setScreenShareData((prevState) => {
121
+ return {
122
+ ...prevState,
123
+ [screenShareUid]: {
124
+ ...prevState[screenShareUid],
125
+ isActive: false,
126
+ ts: 0,
127
+ },
128
+ };
129
+ });
96
130
  //if local user stopped the screenshare then change layout to grid
97
131
  triggerChangeLayout(false);
98
132
  });
@@ -144,12 +178,14 @@ export const ScreenshareConfigure = (props: {children: React.ReactNode}) => {
144
178
  [screenShareUid]: {
145
179
  name: renderListRef.current.renderList[screenShareUid]?.name,
146
180
  isActive: true,
181
+ ts: timeNow(),
147
182
  },
148
183
  };
149
184
  });
150
185
  // 2. Inform everyone in the channel screenshare is actice
151
186
  CustomEvents.send(EventNames.SCREENSHARE_ATTRIBUTE, {
152
- value: `${true}`,
187
+ action: EventActions.SCREENSHARE_STARTED,
188
+ value: timeNow(),
153
189
  level: EventLevel.LEVEL2,
154
190
  });
155
191
  //3 . if local user started the screenshare then change layout to pinned