blob: a9e2807cac45a4c6b3e40fec47a752e3ccbe56d3 [file] [log] [blame]
simon2d3b6532022-11-08 21:01:57 -05001/*
2 * Copyright (C) 2022 Savoir-faire Linux Inc.
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU Affero General Public License as
6 * published by the Free Software Foundation; either version 3 of the
7 * License, or (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU Affero General Public License for more details.
13 *
14 * You should have received a copy of the GNU Affero General Public
15 * License along with this program. If not, see
16 * <https://www.gnu.org/licenses/>.
17 */
18
simonf929a362022-11-18 16:53:45 -050019import { Box, CircularProgress, Grid, IconButtonProps, Stack, Typography } from '@mui/material';
20import { ComponentType, ReactNode } from 'react';
simon4e7445c2022-11-16 21:18:46 -050021import { useTranslation } from 'react-i18next';
simon2d3b6532022-11-08 21:01:57 -050022
23import {
24 CallingAnswerAudioButton,
25 CallingAnswerVideoButton,
simonf929a362022-11-18 16:53:45 -050026 CallingCancelButton,
simon2d3b6532022-11-08 21:01:57 -050027 CallingRefuseButton,
28} from '../components/CallButtons';
29
30export type CallPendingProps = {
31 pending: PendingStatus;
32 caller?: CallerStatus;
33 medium?: CommunicationMedium;
34};
35
36type PendingStatus = 'caller' | 'receiver';
37type CallerStatus = 'calling' | 'connecting';
38type CommunicationMedium = 'audio' | 'video';
39
simon2d3b6532022-11-08 21:01:57 -050040export const CallPending = (props: CallPendingProps) => {
41 return (
42 <Stack
43 direction="column"
44 justifyContent="center"
45 alignItems="center"
46 height="100%"
47 spacing={4}
simon9f814a32022-11-22 21:40:53 -050048 flexGrow={1}
simon2d3b6532022-11-08 21:01:57 -050049 sx={{
50 backgroundColor: 'black',
51 }}
52 >
53 <Box
54 sx={{
55 position: 'relative',
56 display: 'flex',
57 alignItems: 'center',
58 justifyContent: 'center',
59 width: '100%',
60 height: '30%',
61 }}
62 >
63 <Box
64 sx={{
65 aspectRatio: '1',
66 height: '100%',
67 position: 'absolute',
68 }}
69 >
70 <CircularProgress
71 disableShrink
72 thickness={1}
73 size="100%"
74 sx={{
75 position: 'absolute',
76 color: 'white',
77 zIndex: 1,
78 }}
79 />
80 <img
81 // TODO: Insert incoming caller icon here
simonf929a362022-11-18 16:53:45 -050082 alt="contact profile picture"
simon2d3b6532022-11-08 21:01:57 -050083 style={{
84 position: 'absolute',
85 objectFit: 'cover',
86 width: '100%',
87 height: '100%',
88 maxWidth: '100%',
89 borderRadius: '50%',
90 aspectRatio: '1',
91 }}
92 />
93 </Box>
94 </Box>
95 {props.pending === 'caller' ? (
96 <CallPendingCallerInterface {...props} />
97 ) : (
98 <CallPendingReceiverInterface {...props} />
99 )}
100 </Stack>
101 );
102};
103
simonf929a362022-11-18 16:53:45 -0500104const CallPendingDetails = ({
105 title,
106 buttons,
107}: {
108 title: ReactNode;
109 buttons: {
110 ButtonComponent: ComponentType<IconButtonProps>;
111 title: ReactNode;
112 }[];
113}) => {
simon2d3b6532022-11-08 21:01:57 -0500114 return (
simon4e7445c2022-11-16 21:18:46 -0500115 <>
simon2d3b6532022-11-08 21:01:57 -0500116 <Typography variant="h1" color="white">
simonf929a362022-11-18 16:53:45 -0500117 {title}
simon2d3b6532022-11-08 21:01:57 -0500118 </Typography>
simon4e7445c2022-11-16 21:18:46 -0500119 <Box width="50%">
simonf929a362022-11-18 16:53:45 -0500120 <Grid container justifyContent="center">
121 {buttons.map(({ ButtonComponent, title: buttonTitle }, i) => (
122 <Grid item key={i} xs={4}>
123 <Stack direction="column" alignItems="center" spacing={1} sx={{}}>
124 <ButtonComponent color="inherit" size="large" />
125 <Typography variant="body2" color="white" sx={{ opacity: 0.75 }}>
126 {buttonTitle}
127 </Typography>
128 </Stack>
129 </Grid>
130 ))}
131 </Grid>
simon4e7445c2022-11-16 21:18:46 -0500132 </Box>
133 </>
simon2d3b6532022-11-08 21:01:57 -0500134 );
135};
136
simonf929a362022-11-18 16:53:45 -0500137export const CallPendingCallerInterface = ({ caller }: CallPendingProps) => {
simon4e7445c2022-11-16 21:18:46 -0500138 const { t } = useTranslation();
simonf929a362022-11-18 16:53:45 -0500139
140 // TODO: Remove the dummy name
141 const defaultName = 'Alex Thérieur';
simon2d3b6532022-11-08 21:01:57 -0500142 return (
simonf929a362022-11-18 16:53:45 -0500143 <CallPendingDetails
144 title={
145 caller === 'calling'
146 ? t('calling', {
147 member0: defaultName,
148 })
149 : t('connecting')
150 }
151 buttons={[
152 {
153 ButtonComponent: CallingCancelButton,
154 title: t('end_call'),
155 },
156 ]}
157 />
158 );
159};
160
161export const CallPendingReceiverInterface = ({ medium, caller }: CallPendingProps) => {
162 const { t } = useTranslation();
163
164 // TODO: Remove the dummy name
165 const defaultName = 'Alain Thérieur';
166
167 return (
168 <CallPendingDetails
169 title={
170 caller === 'connecting'
171 ? t('connecting')
172 : t('incoming_call', {
173 context: medium,
174 member0: defaultName,
175 })
176 }
177 buttons={[
178 {
179 ButtonComponent: CallingRefuseButton,
180 title: t('refuse_call'),
181 },
182 {
183 ButtonComponent: CallingAnswerAudioButton,
184 title: t('accept_call_audio'),
185 },
186 {
187 ButtonComponent: CallingAnswerVideoButton,
188 title: t('accept_call_video'),
189 },
190 ]}
191 />
simon2d3b6532022-11-08 21:01:57 -0500192 );
193};