@100mslive/roomkit-react 0.1.7 → 0.1.8-alpha.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.
- package/dist/AudioLevel/AudioLevel.d.ts +5 -8
- package/dist/AudioLevel/index.d.ts +2 -1
- package/dist/AudioLevel/useBorderAudioLevel.d.ts +8 -0
- package/dist/{HLSView-3S74KF3A.js → HLSView-IQRPLYNH.js} +5 -4
- package/dist/{HLSView-3S74KF3A.js.map → HLSView-IQRPLYNH.js.map} +2 -2
- package/dist/Prebuilt/components/Chip.d.ts +12 -0
- package/dist/Prebuilt/components/PrebuiltDialogPortal.d.ts +4 -0
- package/dist/{VirtualBackground-3TI5NA4V.js → VirtualBackground-GP4ATXD3.js} +3 -3
- package/dist/{chunk-36X4ZCLC.js → chunk-2H5NIZB7.js} +2 -2
- package/dist/{chunk-Z7P5WITU.js → chunk-GLYGPYNS.js} +560 -1190
- package/dist/chunk-GLYGPYNS.js.map +7 -0
- package/dist/{chunk-5DQ3WTED.js → chunk-Z3O2WGWV.js} +2 -2
- package/dist/{chunk-5DQ3WTED.js.map → chunk-Z3O2WGWV.js.map} +1 -1
- package/dist/{conference-JNABIZBG.js → conference-JD35TNH4.js} +1351 -662
- package/dist/conference-JD35TNH4.js.map +7 -0
- package/dist/index.cjs.js +3387 -3297
- package/dist/index.cjs.js.map +4 -4
- package/dist/index.js +4 -2
- package/dist/meta.cjs.json +1001 -826
- package/dist/meta.esbuild.json +1053 -877
- package/package.json +6 -6
- package/src/AudioLevel/AudioLevel.tsx +79 -30
- package/src/AudioLevel/audio-level.png +0 -0
- package/src/AudioLevel/index.ts +2 -1
- package/src/AudioLevel/useBorderAudioLevel.tsx +34 -0
- package/src/Prebuilt/App.tsx +1 -0
- package/src/Prebuilt/common/utils.js +0 -7
- package/src/Prebuilt/components/{Chip.jsx → Chip.tsx} +13 -2
- package/src/Prebuilt/components/Footer/ParticipantList.jsx +23 -12
- package/src/Prebuilt/components/Footer/RoleAccordion.tsx +43 -3
- package/src/Prebuilt/components/Leave/DesktopLeaveRoom.tsx +7 -4
- package/src/Prebuilt/components/MoreSettings/ChangeNameModal.jsx +3 -2
- package/src/Prebuilt/components/MoreSettings/EmbedUrl.jsx +3 -2
- package/src/Prebuilt/components/MwebLandscapePrompt.jsx +58 -0
- package/src/Prebuilt/components/Notifications/HLSFailureModal.jsx +3 -2
- package/src/Prebuilt/components/Notifications/PermissionErrorModal.jsx +3 -2
- package/src/Prebuilt/components/PrebuiltDialogPortal.tsx +6 -0
- package/src/Prebuilt/components/Preview/PreviewJoin.tsx +4 -3
- package/src/Prebuilt/components/RoleChangeModal.jsx +3 -2
- package/src/Prebuilt/components/RoleChangeRequest/RequestPrompt.tsx +3 -2
- package/src/Prebuilt/components/Settings/SettingsModal.jsx +3 -2
- package/src/Prebuilt/components/Settings/StartRecording.jsx +3 -2
- package/src/Prebuilt/components/StatsForNerds.jsx +3 -2
- package/src/Prebuilt/components/VideoTile.jsx +22 -69
- package/src/Prebuilt/components/pdfAnnotator/pdfFileOptions.jsx +3 -2
- package/src/Prebuilt/components/pdfAnnotator/shareScreenOptions.jsx +4 -29
- package/src/Prebuilt/components/pdfAnnotator/uploadedFile.jsx +3 -2
- package/src/Prebuilt/layouts/HLSView.jsx +1 -0
- package/src/Prebuilt/primitives/DialogContent.jsx +5 -4
- package/dist/chunk-Z7P5WITU.js.map +0 -7
- package/dist/conference-JNABIZBG.js.map +0 -7
- /package/dist/{VirtualBackground-3TI5NA4V.js.map → VirtualBackground-GP4ATXD3.js.map} +0 -0
- /package/dist/{chunk-36X4ZCLC.js.map → chunk-2H5NIZB7.js.map} +0 -0
package/package.json
CHANGED
@@ -10,7 +10,7 @@
|
|
10
10
|
"prebuilt",
|
11
11
|
"roomkit"
|
12
12
|
],
|
13
|
-
"version": "0.1.
|
13
|
+
"version": "0.1.8-alpha.0",
|
14
14
|
"author": "100ms",
|
15
15
|
"license": "MIT",
|
16
16
|
"files": [
|
@@ -76,10 +76,10 @@
|
|
76
76
|
"react": ">=17.0.2 <19.0.0"
|
77
77
|
},
|
78
78
|
"dependencies": {
|
79
|
-
"@100mslive/hls-player": "0.1.
|
80
|
-
"@100mslive/hms-virtual-background": "1.11.
|
81
|
-
"@100mslive/react-icons": "0.8.
|
82
|
-
"@100mslive/react-sdk": "0.8.
|
79
|
+
"@100mslive/hls-player": "0.1.17-alpha.0",
|
80
|
+
"@100mslive/hms-virtual-background": "1.11.17-alpha.0",
|
81
|
+
"@100mslive/react-icons": "0.8.17-alpha.0",
|
82
|
+
"@100mslive/react-sdk": "0.8.17-alpha.0",
|
83
83
|
"@100mslive/types-prebuilt": "0.12.0",
|
84
84
|
"@emoji-mart/data": "^1.0.6",
|
85
85
|
"@emoji-mart/react": "^1.0.1",
|
@@ -115,5 +115,5 @@
|
|
115
115
|
"uuid": "^8.3.2",
|
116
116
|
"worker-timers": "^7.0.40"
|
117
117
|
},
|
118
|
-
"gitHead": "
|
118
|
+
"gitHead": "d6e072de081b508a297ebc1684a33a8e9db048ef"
|
119
119
|
}
|
@@ -1,34 +1,83 @@
|
|
1
|
-
import {
|
2
|
-
import {
|
3
|
-
import {
|
4
|
-
import {
|
1
|
+
import React, { useEffect, useRef } from 'react';
|
2
|
+
import { selectTrackAudioByID, useHMSVanillaStore } from '@100mslive/react-sdk';
|
3
|
+
import { Box, Flex } from '../Layout';
|
4
|
+
import { keyframes } from '../Theme';
|
5
|
+
//@ts-ignore
|
6
|
+
import bg from './audio-level.png';
|
5
7
|
|
6
|
-
|
7
|
-
|
8
|
-
*
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
8
|
+
// keep the calculated values before hand to avoid recalcuation everytime
|
9
|
+
const positionValues = new Array(101).fill(0).reduce((acc, _, index) => {
|
10
|
+
acc[index] = Math.round((index / 100) * 4) / 4; // convert to 0.25 multiples
|
11
|
+
return acc;
|
12
|
+
}, {});
|
13
|
+
|
14
|
+
const barAnimation = keyframes({
|
15
|
+
from: {
|
16
|
+
maskSize: '4em .8em',
|
17
|
+
'-webkit-mask-position-y': '.1em',
|
18
|
+
maskPosition: 'initial .1em',
|
19
|
+
},
|
20
|
+
|
21
|
+
'50%': {
|
22
|
+
maskSize: '4em 1em',
|
23
|
+
'-webkit-mask-position-y': 0,
|
24
|
+
maskPosition: 'initial 0',
|
25
|
+
},
|
26
|
+
|
27
|
+
to: {
|
28
|
+
maskSize: '4em .8em',
|
29
|
+
'-webkit-mask-position-y': '.1em',
|
30
|
+
maskPosition: 'initial 0',
|
31
|
+
},
|
32
|
+
});
|
33
|
+
|
34
|
+
const AudioBar = () => {
|
35
|
+
return (
|
36
|
+
<Box
|
37
|
+
css={{
|
38
|
+
width: '.25em',
|
39
|
+
height: '1em',
|
40
|
+
maskImage: `url(${bg})`,
|
41
|
+
'-webkit-mask-repeat': 'no-repeat',
|
42
|
+
backgroundColor: '$on_primary_high',
|
43
|
+
maskSize: '4em 1em',
|
44
|
+
}}
|
45
|
+
/>
|
22
46
|
);
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
});
|
29
|
-
return ref;
|
30
|
-
}
|
47
|
+
};
|
48
|
+
|
49
|
+
export const AudioLevel = ({ trackId, size }: { trackId?: string; size?: 'small' | 'medium' }) => {
|
50
|
+
const ref = useRef<HTMLDivElement | null>(null);
|
51
|
+
const vanillaStore = useHMSVanillaStore();
|
31
52
|
|
32
|
-
|
33
|
-
|
53
|
+
useEffect(() => {
|
54
|
+
const unsubscribe = vanillaStore.subscribe(audioLevel => {
|
55
|
+
if (ref.current) {
|
56
|
+
let index = 0;
|
57
|
+
//@ts-ignore
|
58
|
+
for (const child of ref.current.children) {
|
59
|
+
const positionX = `-${positionValues[audioLevel] * (index === 1 ? 2.5 : 1.25)}em`;
|
60
|
+
child.style['-webkit-mask-position-x'] = positionX;
|
61
|
+
child.style['mask-position'] = `${positionX} 0`;
|
62
|
+
child.style['animation'] =
|
63
|
+
positionValues[audioLevel] > 0 ? `${barAnimation} 0.6s steps(3,jump-none) 0s infinite` : 'none';
|
64
|
+
index++;
|
65
|
+
}
|
66
|
+
}
|
67
|
+
}, selectTrackAudioByID(trackId));
|
68
|
+
return unsubscribe;
|
69
|
+
}, [vanillaStore, trackId]);
|
70
|
+
return (
|
71
|
+
<Flex
|
72
|
+
ref={ref}
|
73
|
+
css={{
|
74
|
+
fontSize: size === 'small' ? '0.75rem' : '1rem',
|
75
|
+
gap: size === 'small' ? '$1' : '$2',
|
76
|
+
}}
|
77
|
+
>
|
78
|
+
<AudioBar />
|
79
|
+
<AudioBar />
|
80
|
+
<AudioBar />
|
81
|
+
</Flex>
|
82
|
+
);
|
34
83
|
};
|
Binary file
|
package/src/AudioLevel/index.ts
CHANGED
@@ -1 +1,2 @@
|
|
1
|
-
export { useBorderAudioLevel } from './
|
1
|
+
export { useBorderAudioLevel } from './useBorderAudioLevel';
|
2
|
+
export { AudioLevel } from './AudioLevel';
|
@@ -0,0 +1,34 @@
|
|
1
|
+
import { useCallback, useRef } from 'react';
|
2
|
+
import { HMSTrackID } from '@100mslive/hms-video-store';
|
3
|
+
import { useAudioLevelStyles } from '@100mslive/react-sdk';
|
4
|
+
import { useTheme } from '../Theme';
|
5
|
+
|
6
|
+
/**
|
7
|
+
* pass in a track id and get a ref. That ref can be attached to an element which will have border
|
8
|
+
* as per audio level post that.
|
9
|
+
*/
|
10
|
+
export function useBorderAudioLevel(audioTrackId?: HMSTrackID) {
|
11
|
+
const { theme } = useTheme();
|
12
|
+
const color = theme.colors.primary_default.value;
|
13
|
+
const getStyle = useCallback(
|
14
|
+
(level: number) => {
|
15
|
+
const style: Record<string, string> = {
|
16
|
+
transition: 'outline 0.4s ease-in-out',
|
17
|
+
};
|
18
|
+
style['outline'] = level ? `${sigmoid(level) * 4}px solid ${color}` : '0px solid transparent';
|
19
|
+
return style;
|
20
|
+
},
|
21
|
+
[color],
|
22
|
+
);
|
23
|
+
const ref = useRef(null);
|
24
|
+
useAudioLevelStyles({
|
25
|
+
trackId: audioTrackId,
|
26
|
+
getStyle,
|
27
|
+
ref,
|
28
|
+
});
|
29
|
+
return ref;
|
30
|
+
}
|
31
|
+
|
32
|
+
export const sigmoid = (z: number) => {
|
33
|
+
return 1 / (1 + Math.exp(-z));
|
34
|
+
};
|
package/src/Prebuilt/App.tsx
CHANGED
@@ -218,6 +218,7 @@ export const HMSPrebuilt = React.forwardRef<HMSPrebuiltRefType, HMSPrebuiltProps
|
|
218
218
|
<AppData appDetails={metadata} tokenEndpoint={tokenByRoomIdRoleEndpoint} />
|
219
219
|
<Init />
|
220
220
|
<Box
|
221
|
+
id="prebuilt-container"
|
221
222
|
css={{
|
222
223
|
bg: '$background_dim',
|
223
224
|
size: '100%',
|
@@ -88,10 +88,3 @@ export const formatTime = timeInSeconds => {
|
|
88
88
|
const hour = hours !== 0 ? `${hours < 10 ? '0' : ''}${hours}:` : '';
|
89
89
|
return `${hour}${minutes < 10 ? '0' : ''}${minutes}:${seconds < 10 ? '0' : ''}${seconds}`;
|
90
90
|
};
|
91
|
-
|
92
|
-
export const getAttributeBoxSize = (width, height) => {
|
93
|
-
if (!width || !height) {
|
94
|
-
return '';
|
95
|
-
}
|
96
|
-
return width < 180 || height < 180 ? 'small' : 'medium';
|
97
|
-
};
|
@@ -1,6 +1,7 @@
|
|
1
1
|
import React from 'react';
|
2
2
|
import { Flex } from '../../Layout';
|
3
3
|
import { Text } from '../../Text';
|
4
|
+
import { CSS } from '../../Theme';
|
4
5
|
|
5
6
|
const Chip = ({
|
6
7
|
icon = <></>,
|
@@ -8,12 +9,22 @@ const Chip = ({
|
|
8
9
|
backgroundColor = '$surface_default',
|
9
10
|
textColor = '$on_surface_high',
|
10
11
|
hideIfNoContent = false,
|
12
|
+
onClick,
|
13
|
+
css = {},
|
14
|
+
}: {
|
15
|
+
icon?: React.JSX.Element;
|
16
|
+
content: string;
|
17
|
+
backgroundColor?: string;
|
18
|
+
textColor?: string;
|
19
|
+
hideIfNoContent?: boolean;
|
20
|
+
onClick?: () => void | Promise<void>;
|
21
|
+
css?: CSS;
|
11
22
|
}) => {
|
12
23
|
if (hideIfNoContent && !content) {
|
13
|
-
return;
|
24
|
+
return null;
|
14
25
|
}
|
15
26
|
return (
|
16
|
-
<Flex align="center" css={{ backgroundColor, p: '$4 $6', borderRadius: '$4' }}>
|
27
|
+
<Flex align="center" css={{ backgroundColor, p: '$4 $6', borderRadius: '$4', ...css }} onClick={() => onClick?.()}>
|
17
28
|
{icon}
|
18
29
|
<Text variant="sm" css={{ fontWeight: '$semiBold', color: textColor, ml: '$2' }}>
|
19
30
|
{content}
|
@@ -127,13 +127,15 @@ const VirtualizedParticipants = ({ peersOrderedByRoles = {}, isConnected, filter
|
|
127
127
|
flex: '1 1 0',
|
128
128
|
}}
|
129
129
|
>
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
130
|
+
{handRaisedList.length > 0 ? (
|
131
|
+
<RoleAccordion
|
132
|
+
peerList={handRaisedList}
|
133
|
+
roleName="Hand Raised"
|
134
|
+
filter={filter}
|
135
|
+
isConnected={isConnected}
|
136
|
+
isHandRaisedAccordion
|
137
|
+
/>
|
138
|
+
) : null}
|
137
139
|
{Object.keys(peersOrderedByRoles).map(role => (
|
138
140
|
<RoleAccordion
|
139
141
|
key={role}
|
@@ -179,7 +181,10 @@ export const Participant = ({ peer, isConnected }) => {
|
|
179
181
|
const ParticipantActions = React.memo(({ peerId, role, isLocal }) => {
|
180
182
|
const isHandRaised = useHMSStore(selectHasPeerHandRaised(peerId));
|
181
183
|
const canChangeRole = useHMSStore(selectPermissions)?.changeRole;
|
182
|
-
const
|
184
|
+
const canRemoveOthers = useHMSStore(selectPermissions)?.removeOthers;
|
185
|
+
const { elements } = useRoomLayoutConferencingScreen();
|
186
|
+
const { on_stage_exp } = elements || {};
|
187
|
+
const shouldShowMoreActions = (on_stage_exp && canChangeRole) || canRemoveOthers;
|
183
188
|
const isAudioMuted = !useHMSStore(selectIsPeerAudioEnabled(peerId));
|
184
189
|
|
185
190
|
return (
|
@@ -210,15 +215,21 @@ const ParticipantActions = React.memo(({ peerId, role, isLocal }) => {
|
|
210
215
|
</Flex>
|
211
216
|
) : null}
|
212
217
|
|
213
|
-
{shouldShowMoreActions && !isLocal ?
|
218
|
+
{shouldShowMoreActions && !isLocal ? (
|
219
|
+
<ParticipantMoreActions
|
220
|
+
peerId={peerId}
|
221
|
+
role={role}
|
222
|
+
elements={elements}
|
223
|
+
canChangeRole={canChangeRole}
|
224
|
+
canRemoveOthers={canRemoveOthers}
|
225
|
+
/>
|
226
|
+
) : null}
|
214
227
|
</Flex>
|
215
228
|
);
|
216
229
|
});
|
217
230
|
|
218
|
-
const ParticipantMoreActions = ({ peerId, role }) => {
|
231
|
+
const ParticipantMoreActions = ({ peerId, role, elements, canChangeRole, canRemoveOthers }) => {
|
219
232
|
const hmsActions = useHMSActions();
|
220
|
-
const { changeRole: canChangeRole, removeOthers: canRemoveOthers } = useHMSStore(selectPermissions);
|
221
|
-
const { elements } = useRoomLayoutConferencingScreen();
|
222
233
|
const {
|
223
234
|
bring_to_stage_label,
|
224
235
|
remove_from_stage_label,
|
@@ -1,10 +1,12 @@
|
|
1
|
-
import React from 'react';
|
1
|
+
import React, { useCallback, useEffect, useRef, useState } from 'react';
|
2
2
|
import { useMeasure } from 'react-use';
|
3
3
|
import { FixedSizeList } from 'react-window';
|
4
|
-
import { HMSPeer } from '@100mslive/react-sdk';
|
4
|
+
import { HMSPeer, HMSPeerListIterator, useHMSActions } from '@100mslive/react-sdk';
|
5
|
+
import { AddCircleIcon } from '@100mslive/react-icons';
|
5
6
|
import { Accordion } from '../../../Accordion';
|
6
7
|
import { Box, Flex } from '../../../Layout';
|
7
8
|
import { Text } from '../../../Text';
|
9
|
+
import Chip from '../Chip';
|
8
10
|
// @ts-ignore: No implicit Any
|
9
11
|
import { Participant } from './ParticipantList';
|
10
12
|
import { RoleOptions } from './RoleOptions';
|
@@ -38,11 +40,34 @@ export const RoleAccordion = ({
|
|
38
40
|
filter?: { search: string };
|
39
41
|
}) => {
|
40
42
|
const [ref, { width }] = useMeasure<HTMLDivElement>();
|
43
|
+
const actions = useHMSActions();
|
41
44
|
const showAcordion = filter?.search ? peerList.some(peer => peer.name.toLowerCase().includes(filter.search)) : true;
|
45
|
+
const [hasNext, setHasNext] = useState(false);
|
46
|
+
const iteratorRef = useRef<HMSPeerListIterator | null>(null);
|
42
47
|
|
43
|
-
|
48
|
+
const loadNext = useCallback(() => {
|
49
|
+
if (!roleName || roleName === 'Hand Raised') {
|
50
|
+
return;
|
51
|
+
}
|
52
|
+
if (!iteratorRef.current) {
|
53
|
+
iteratorRef.current = actions.getPeerListIterator({ role: roleName });
|
54
|
+
}
|
55
|
+
iteratorRef.current
|
56
|
+
.next()
|
57
|
+
.catch(console.error)
|
58
|
+
.finally(() => {
|
59
|
+
setHasNext(iteratorRef.current ? iteratorRef.current.hasNext() : false);
|
60
|
+
});
|
61
|
+
}, [actions, roleName]);
|
62
|
+
|
63
|
+
useEffect(() => {
|
64
|
+
loadNext();
|
65
|
+
}, [loadNext]);
|
66
|
+
|
67
|
+
if (!showAcordion || (isHandRaisedAccordion && filter?.search) || (peerList.length === 0 && filter?.search)) {
|
44
68
|
return null;
|
45
69
|
}
|
70
|
+
|
46
71
|
const height = ROW_HEIGHT * peerList.length;
|
47
72
|
|
48
73
|
return (
|
@@ -86,6 +111,21 @@ export const RoleAccordion = ({
|
|
86
111
|
>
|
87
112
|
{VirtualizedParticipantItem}
|
88
113
|
</FixedSizeList>
|
114
|
+
{hasNext ? (
|
115
|
+
<Chip
|
116
|
+
icon={<AddCircleIcon />}
|
117
|
+
content="Load More"
|
118
|
+
onClick={loadNext}
|
119
|
+
backgroundColor="$secondary_default"
|
120
|
+
css={{
|
121
|
+
w: 'max-content',
|
122
|
+
borderRadius: '$size$9',
|
123
|
+
m: '$2 auto',
|
124
|
+
p: '$4',
|
125
|
+
cursor: 'pointer',
|
126
|
+
}}
|
127
|
+
/>
|
128
|
+
) : null}
|
89
129
|
</Accordion.Content>
|
90
130
|
</Accordion.Item>
|
91
131
|
</Accordion.Root>
|
@@ -1,11 +1,14 @@
|
|
1
1
|
import React, { Fragment, useState } from 'react';
|
2
2
|
import { ConferencingScreen } from '@100mslive/types-prebuilt';
|
3
|
+
// @ts-ignore: No implicit Any
|
3
4
|
import { selectIsConnectedToRoom, selectPermissions, useHMSStore, useRecordingStreaming } from '@100mslive/react-sdk';
|
5
|
+
// @ts-ignore: No implicit Any
|
4
6
|
import { ExitIcon, StopIcon, VerticalMenuIcon } from '@100mslive/react-icons';
|
5
7
|
import { Dropdown } from '../../../Dropdown';
|
6
8
|
import { Box, Flex } from '../../../Layout';
|
7
9
|
import { Dialog } from '../../../Modal';
|
8
10
|
import { Tooltip } from '../../../Tooltip';
|
11
|
+
import { PrebuiltDialogPortal } from '../PrebuiltDialogPortal';
|
9
12
|
import { EndSessionContent } from './EndSessionContent';
|
10
13
|
import { LeaveIconButton, MenuTriggerButton } from './LeaveAtoms';
|
11
14
|
import { LeaveCard } from './LeaveCard';
|
@@ -135,7 +138,7 @@ export const DesktopLeaveRoom = ({
|
|
135
138
|
)}
|
136
139
|
|
137
140
|
<Dialog.Root open={showEndStreamAlert} modal={false}>
|
138
|
-
<
|
141
|
+
<PrebuiltDialogPortal>
|
139
142
|
<Dialog.Overlay />
|
140
143
|
<Dialog.Content css={{ w: 'min(420px, 90%)', p: '$8', bg: '$surface_dim' }}>
|
141
144
|
<EndSessionContent
|
@@ -145,16 +148,16 @@ export const DesktopLeaveRoom = ({
|
|
145
148
|
isModal
|
146
149
|
/>
|
147
150
|
</Dialog.Content>
|
148
|
-
</
|
151
|
+
</PrebuiltDialogPortal>
|
149
152
|
</Dialog.Root>
|
150
153
|
|
151
154
|
<Dialog.Root open={showLeaveRoomAlert} modal={false}>
|
152
|
-
<
|
155
|
+
<PrebuiltDialogPortal>
|
153
156
|
<Dialog.Overlay />
|
154
157
|
<Dialog.Content css={{ w: 'min(420px, 90%)', p: '$8', bg: '$surface_dim' }}>
|
155
158
|
<LeaveSessionContent setShowLeaveRoomAlert={setShowLeaveRoomAlert} leaveRoom={leaveRoom} isModal />
|
156
159
|
</Dialog.Content>
|
157
|
-
</
|
160
|
+
</PrebuiltDialogPortal>
|
158
161
|
</Dialog.Root>
|
159
162
|
</Fragment>
|
160
163
|
);
|
@@ -3,6 +3,7 @@ import { useMedia } from 'react-use';
|
|
3
3
|
import { selectLocalPeerName, useHMSActions, useHMSStore } from '@100mslive/react-sdk';
|
4
4
|
import { config as cssConfig, Dialog } from '../../../';
|
5
5
|
import { Sheet } from '../../../Sheet';
|
6
|
+
import { PrebuiltDialogPortal } from '../PrebuiltDialogPortal';
|
6
7
|
import { ToastManager } from '../Toast/ToastManager';
|
7
8
|
import { ChangeNameContent } from './ChangeNameContent';
|
8
9
|
import { UserPreferencesKeys, useUserPreferences } from '../hooks/useUserPreferences';
|
@@ -58,12 +59,12 @@ export const ChangeNameModal = ({ onOpenChange, openParentSheet = null }) => {
|
|
58
59
|
|
59
60
|
return (
|
60
61
|
<Dialog.Root defaultOpen onOpenChange={onOpenChange}>
|
61
|
-
<
|
62
|
+
<PrebuiltDialogPortal>
|
62
63
|
<Dialog.Overlay />
|
63
64
|
<Dialog.Content css={{ bg: '$surface_dim', width: 'min(400px,80%)', p: '$10' }}>
|
64
65
|
<ChangeNameContent {...props} />
|
65
66
|
</Dialog.Content>
|
66
|
-
</
|
67
|
+
</PrebuiltDialogPortal>
|
67
68
|
</Dialog.Root>
|
68
69
|
);
|
69
70
|
};
|
@@ -1,6 +1,7 @@
|
|
1
1
|
import React, { useState } from 'react';
|
2
2
|
import { LinkIcon } from '@100mslive/react-icons';
|
3
3
|
import { Button, Dialog, Dropdown, Flex, Input, Text } from '../../../';
|
4
|
+
import { PrebuiltDialogPortal } from '../PrebuiltDialogPortal';
|
4
5
|
import { useSetAppDataByKey } from '../AppData/useUISettings';
|
5
6
|
import { APP_DATA } from '../../common/constants';
|
6
7
|
|
@@ -30,7 +31,7 @@ export function EmbedUrlModal({ onOpenChange }) {
|
|
30
31
|
|
31
32
|
return (
|
32
33
|
<Dialog.Root defaultOpen onOpenChange={onOpenChange}>
|
33
|
-
<
|
34
|
+
<PrebuiltDialogPortal>
|
34
35
|
<Dialog.Overlay />
|
35
36
|
<Dialog.Content css={{ w: 'min(420px, 90%)', p: '$8', bg: '$surface_dim' }}>
|
36
37
|
<Dialog.Title
|
@@ -75,7 +76,7 @@ export function EmbedUrlModal({ onOpenChange }) {
|
|
75
76
|
</Button>
|
76
77
|
</Flex>
|
77
78
|
</Dialog.Content>
|
78
|
-
</
|
79
|
+
</PrebuiltDialogPortal>
|
79
80
|
</Dialog.Root>
|
80
81
|
);
|
81
82
|
}
|
@@ -0,0 +1,58 @@
|
|
1
|
+
import React, { useEffect, useState } from 'react';
|
2
|
+
import { RefreshIcon } from '@100mslive/react-icons';
|
3
|
+
import { Button } from '../../Button';
|
4
|
+
import { Box, Flex } from '../../Layout';
|
5
|
+
import { Dialog } from '../../Modal';
|
6
|
+
import { Text } from '../../Text';
|
7
|
+
import { PrebuiltDialogPortal } from './PrebuiltDialogPortal';
|
8
|
+
import { isAndroid, isIOS } from '../common/constants';
|
9
|
+
|
10
|
+
export const MwebLandscapePrompt = () => {
|
11
|
+
const isMobile = isAndroid || isIOS;
|
12
|
+
const [showMwebLandscapePrompt, setShowMwebLandscapePrompt] = useState(false);
|
13
|
+
|
14
|
+
useEffect(() => {
|
15
|
+
const handleResize = () => {
|
16
|
+
setShowMwebLandscapePrompt(isMobile && window.innerHeight < window.innerWidth);
|
17
|
+
};
|
18
|
+
|
19
|
+
handleResize();
|
20
|
+
window.addEventListener('resize', handleResize);
|
21
|
+
|
22
|
+
return () => {
|
23
|
+
window.removeEventListener('resize', handleResize);
|
24
|
+
};
|
25
|
+
}, []);
|
26
|
+
|
27
|
+
return (
|
28
|
+
<Dialog.Root open={showMwebLandscapePrompt} onOpenChange={setShowMwebLandscapePrompt}>
|
29
|
+
<PrebuiltDialogPortal>
|
30
|
+
<Dialog.Overlay />
|
31
|
+
<Dialog.Content css={{ w: 'min(420px, 90%)', p: '$8', bg: '$surface_dim' }}>
|
32
|
+
<Box>
|
33
|
+
<Flex
|
34
|
+
css={{
|
35
|
+
color: '$primary_default',
|
36
|
+
display: 'flex',
|
37
|
+
alignItems: 'center',
|
38
|
+
}}
|
39
|
+
>
|
40
|
+
<RefreshIcon style={{ marginRight: '0.5rem' }} />
|
41
|
+
<Text variant="lg" css={{ color: '$on_surface_high', fontWeight: '$semiBold' }}>
|
42
|
+
Please rotate your device
|
43
|
+
</Text>
|
44
|
+
</Flex>
|
45
|
+
<Text variant="sm" css={{ color: '$on_surface_medium', mb: '$8', mt: '$4' }}>
|
46
|
+
We do not support landscape mode as of now, please use the app in portrait mode for the best experience.
|
47
|
+
</Text>
|
48
|
+
<Flex align="center" justify="between" css={{ w: '100%', gap: '$8' }}>
|
49
|
+
<Button outlined variant="standard" css={{ w: '100%' }} onClick={() => setShowMwebLandscapePrompt(false)}>
|
50
|
+
Continue anyway
|
51
|
+
</Button>
|
52
|
+
</Flex>
|
53
|
+
</Box>
|
54
|
+
</Dialog.Content>
|
55
|
+
</PrebuiltDialogPortal>
|
56
|
+
</Dialog.Root>
|
57
|
+
);
|
58
|
+
};
|
@@ -4,6 +4,7 @@ import { Button } from '../../../Button';
|
|
4
4
|
import { Flex } from '../../../Layout';
|
5
5
|
import { Dialog } from '../../../Modal';
|
6
6
|
import { Text } from '../../../Text';
|
7
|
+
import { PrebuiltDialogPortal } from '../PrebuiltDialogPortal';
|
7
8
|
import { useSetAppDataByKey } from '../AppData/useUISettings';
|
8
9
|
import { APP_DATA } from '../../common/constants';
|
9
10
|
|
@@ -37,7 +38,7 @@ export function HLSFailureModal() {
|
|
37
38
|
}
|
38
39
|
}}
|
39
40
|
>
|
40
|
-
<
|
41
|
+
<PrebuiltDialogPortal>
|
41
42
|
<Dialog.Overlay />
|
42
43
|
<Dialog.Content css={{ w: 'min(360px, 90%)' }}>
|
43
44
|
<Dialog.Title
|
@@ -65,7 +66,7 @@ export function HLSFailureModal() {
|
|
65
66
|
</Button>
|
66
67
|
</Flex>
|
67
68
|
</Dialog.Content>
|
68
|
-
</
|
69
|
+
</PrebuiltDialogPortal>
|
69
70
|
</Dialog.Root>
|
70
71
|
) : null;
|
71
72
|
}
|
@@ -4,6 +4,7 @@ import { HMSNotificationTypes, useHMSNotifications } from '@100mslive/react-sdk'
|
|
4
4
|
import { Button, config as cssConfig, Dialog, Flex, Text } from '../../../';
|
5
5
|
import androidPermissionAlert from '../../images/android-perm-1.png';
|
6
6
|
import iosPermissions from '../../images/ios-perm-0.png';
|
7
|
+
import { PrebuiltDialogPortal } from '../PrebuiltDialogPortal';
|
7
8
|
import { isAndroid, isIOS } from '../../common/constants';
|
8
9
|
|
9
10
|
export function PermissionErrorModal() {
|
@@ -39,7 +40,7 @@ export function PermissionErrorModal() {
|
|
39
40
|
|
40
41
|
return deviceType ? (
|
41
42
|
<Dialog.Root open={!!deviceType}>
|
42
|
-
<
|
43
|
+
<PrebuiltDialogPortal>
|
43
44
|
<Dialog.Overlay />
|
44
45
|
<Dialog.Content css={{ w: 'min(380px, 90%)', p: '$8' }}>
|
45
46
|
<Dialog.Title
|
@@ -118,7 +119,7 @@ export function PermissionErrorModal() {
|
|
118
119
|
</Flex>
|
119
120
|
) : null}
|
120
121
|
</Dialog.Content>
|
121
|
-
</
|
122
|
+
</PrebuiltDialogPortal>
|
122
123
|
</Dialog.Root>
|
123
124
|
) : null;
|
124
125
|
}
|
@@ -0,0 +1,6 @@
|
|
1
|
+
import React, { ReactNode } from 'react';
|
2
|
+
import { Dialog } from '../../Modal';
|
3
|
+
|
4
|
+
export const PrebuiltDialogPortal = ({ children }: { children: ReactNode }) => (
|
5
|
+
<Dialog.Portal container={document.getElementById('prebuilt-container')}>{children}</Dialog.Portal>
|
6
|
+
);
|
@@ -14,6 +14,7 @@ import {
|
|
14
14
|
} from '@100mslive/react-sdk';
|
15
15
|
import { MicOffIcon, SettingsIcon } from '@100mslive/react-icons';
|
16
16
|
import { Avatar, Box, config as cssConfig, Flex, flexCenter, styled, StyledVideoTile, Text, Video } from '../../..';
|
17
|
+
import { AudioLevel } from '../../../AudioLevel';
|
17
18
|
import { useHMSPrebuiltContext } from '../../AppContext';
|
18
19
|
// @ts-ignore: No implicit Any
|
19
20
|
import IconButton from '../../IconButton';
|
@@ -31,8 +32,6 @@ import { Logo } from '../Header/HeaderComponents';
|
|
31
32
|
// @ts-ignore: No implicit Any
|
32
33
|
import SettingsModal from '../Settings/SettingsModal';
|
33
34
|
// @ts-ignore: No implicit Any
|
34
|
-
import { AudioLevel } from '../VideoTile';
|
35
|
-
// @ts-ignore: No implicit Any
|
36
35
|
import PreviewForm from './PreviewForm';
|
37
36
|
// @ts-ignore: No implicit Any
|
38
37
|
import { useAuthToken, useUISettings } from '../AppData/useUISettings';
|
@@ -246,7 +245,9 @@ export const PreviewTile = ({ name, error }: { name: string; error?: boolean })
|
|
246
245
|
<MicOffIcon />
|
247
246
|
</StyledVideoTile.AudioIndicator>
|
248
247
|
) : (
|
249
|
-
<
|
248
|
+
<StyledVideoTile.AudioIndicator size="medium">
|
249
|
+
<AudioLevel trackId={localPeer?.audioTrack} />
|
250
|
+
</StyledVideoTile.AudioIndicator>
|
250
251
|
)}
|
251
252
|
</StyledVideoTile.Container>
|
252
253
|
);
|
@@ -9,6 +9,7 @@ import { Box, Flex } from '../../Layout';
|
|
9
9
|
import { Dialog } from '../../Modal';
|
10
10
|
import { Text } from '../../Text';
|
11
11
|
import { Tooltip } from '../../Tooltip';
|
12
|
+
import { PrebuiltDialogPortal } from './PrebuiltDialogPortal';
|
12
13
|
import { useDropdownSelection } from './hooks/useDropdownSelection';
|
13
14
|
import { useFilteredRoles } from '../common/hooks';
|
14
15
|
import { textEllipsis } from '../../utils';
|
@@ -47,7 +48,7 @@ export const RoleChangeModal = ({ peerId, onOpenChange }) => {
|
|
47
48
|
const peerNameMaxWidth = 200;
|
48
49
|
return (
|
49
50
|
<Dialog.Root defaultOpen onOpenChange={onOpenChange}>
|
50
|
-
<
|
51
|
+
<PrebuiltDialogPortal>
|
51
52
|
<Dialog.Overlay />
|
52
53
|
<Dialog.Content css={{ width: 'min(400px,80%)', p: '$10' }}>
|
53
54
|
<Dialog.Title css={{ p: 0 }} asChild>
|
@@ -179,7 +180,7 @@ export const RoleChangeModal = ({ peerId, onOpenChange }) => {
|
|
179
180
|
</Box>
|
180
181
|
</Flex>
|
181
182
|
</Dialog.Content>
|
182
|
-
</
|
183
|
+
</PrebuiltDialogPortal>
|
183
184
|
</Dialog.Root>
|
184
185
|
);
|
185
186
|
};
|