narinder1231 commited on
Commit
1dec6f5
·
1 Parent(s): 585d8da

integrate voiceToVoice websocket

Browse files
Files changed (1) hide show
  1. src/pages/voiceToVoice/index.tsx +135 -15
src/pages/voiceToVoice/index.tsx CHANGED
@@ -1,15 +1,71 @@
1
- import { Box, Button } from "@mui/material";
2
- import React, { useState } from "react";
 
 
 
 
3
 
4
  const gifSrc = new URL("./assets/animation.gif", import.meta.url).href;
5
  const imgSrc = new URL("./assets/img.png", import.meta.url).href;
6
 
7
  const VoiceToVoice: React.FC = () => {
8
- const [listening, setIsListening] = useState<boolean>(false);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
9
 
10
- function handleClick() {
11
- setIsListening((prevState) => !prevState);
12
- }
 
 
 
 
 
 
 
 
13
 
14
  return (
15
  <Box
@@ -20,40 +76,104 @@ const VoiceToVoice: React.FC = () => {
20
  justifyContent: "center",
21
  height: "100vh",
22
  width: "100vw",
 
23
  }}
24
  >
 
 
25
  <Box
26
  sx={{
27
- width: "200px",
 
 
 
 
28
  display: "flex",
29
  flexDirection: "column",
30
  alignItems: "center",
31
  }}
32
  >
33
- <Box sx={{ mb: "10px" }}>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
34
  {listening ? (
35
- <img src={gifSrc} alt="Listening animation" width={200} height={200} />
 
 
 
 
 
 
 
 
 
36
  ) : (
37
- <img src={imgSrc} alt="Static image" width={200} />
 
 
 
 
 
 
 
 
38
  )}
39
  </Box>
 
40
  <Button
41
  onClick={handleClick}
42
  variant="contained"
 
43
  sx={{
44
  width: "100%",
45
- height: "30px",
46
- borderRadius: "5%",
47
  backgroundColor: listening ? "rgb(218, 176, 176)" : "rgb(126, 184, 203)",
 
 
48
  "&:hover": {
49
- backgroundColor: "rgb(199, 206, 208)",
50
- transition: "background-color 0.3s ease",
 
 
 
 
 
 
51
  },
52
  }}
53
  >
54
- {listening ? "STOP" : "SPEAK"}
55
  </Button>
56
  </Box>
 
 
 
 
 
 
 
 
 
 
 
57
  </Box>
58
  );
59
  };
 
1
+ import { Box, Button, CircularProgress, Snackbar, Alert } from "@mui/material";
2
+ import React, { useState, useEffect, useRef } from "react";
3
+
4
+ import { useBeep } from "../../hooks/useBeep";
5
+ import { useTimer } from "../../hooks/useTimer";
6
+ import { useWebRTC } from "../../hooks/useWebRTC";
7
 
8
  const gifSrc = new URL("./assets/animation.gif", import.meta.url).href;
9
  const imgSrc = new URL("./assets/img.png", import.meta.url).href;
10
 
11
  const VoiceToVoice: React.FC = () => {
12
+ const { startCall, endCall, remoteStream, isConnected, error } = useWebRTC();
13
+ const { timer, startTimer, stopTimer } = useTimer();
14
+ const { startBeeping, stopBeeping } = useBeep();
15
+ const [listening, setListening] = useState<boolean>(false);
16
+ const [isLoading, setIsLoading] = useState<boolean>(false);
17
+ const [showError, setShowError] = useState<boolean>(false);
18
+ const audioRef = useRef<HTMLAudioElement>(null);
19
+
20
+ useEffect(() => {
21
+ if (audioRef.current && remoteStream) {
22
+ audioRef.current.srcObject = remoteStream;
23
+ audioRef.current.play().catch(() => setShowError(true));
24
+ }
25
+ }, [remoteStream]);
26
+
27
+ const handleClick = async () => {
28
+ if (listening) {
29
+ setIsLoading(true);
30
+ try {
31
+ endCall();
32
+ stopTimer();
33
+ stopBeeping();
34
+ setListening(false);
35
+ } finally {
36
+ setIsLoading(false);
37
+ }
38
+ } else {
39
+ setIsLoading(true);
40
+ setListening(true);
41
+ startBeeping();
42
+ try {
43
+ await startCall();
44
+ stopBeeping();
45
+ startTimer();
46
+ } catch {
47
+ stopBeeping();
48
+ stopTimer();
49
+ setListening(false);
50
+ endCall();
51
+ setShowError(true);
52
+ } finally {
53
+ setIsLoading(false);
54
+ }
55
+ }
56
+ };
57
 
58
+ useEffect(() => {
59
+ setListening(isConnected);
60
+ }, [isConnected]);
61
+
62
+ useEffect(() => {
63
+ if (!isConnected && listening) {
64
+ setListening(false);
65
+ stopTimer();
66
+ stopBeeping();
67
+ }
68
+ }, [isConnected, listening, stopTimer, stopBeeping]);
69
 
70
  return (
71
  <Box
 
76
  justifyContent: "center",
77
  height: "100vh",
78
  width: "100vw",
79
+ bgcolor: "#f5f5f5",
80
  }}
81
  >
82
+ <audio ref={audioRef} autoPlay playsInline style={{ display: "none" }} />
83
+
84
  <Box
85
  sx={{
86
+ width: "280px",
87
+ padding: "20px",
88
+ backgroundColor: "white",
89
+ borderRadius: "12px",
90
+ boxShadow: "0 4px 6px rgba(0, 0, 0, 0.1)",
91
  display: "flex",
92
  flexDirection: "column",
93
  alignItems: "center",
94
  }}
95
  >
96
+ <Box
97
+ sx={{
98
+ mb: "20px",
99
+ position: "relative",
100
+ width: "200px",
101
+ height: "200px",
102
+ display: "flex",
103
+ justifyContent: "center",
104
+ alignItems: "center",
105
+ }}
106
+ >
107
+ {isLoading ? (
108
+ <CircularProgress
109
+ size={60}
110
+ sx={{
111
+ position: "absolute",
112
+ color: listening ? "rgb(218, 176, 176)" : "rgb(126, 184, 203)",
113
+ }}
114
+ />
115
+ ) : null}
116
  {listening ? (
117
+ <img
118
+ src={gifSrc}
119
+ alt="Listening animation"
120
+ width={200}
121
+ height={200}
122
+ style={{
123
+ opacity: isLoading ? 0.5 : 1,
124
+ transition: "opacity 0.3s ease",
125
+ }}
126
+ />
127
  ) : (
128
+ <img
129
+ src={imgSrc}
130
+ alt="Static image"
131
+ width={200}
132
+ style={{
133
+ opacity: isLoading ? 0.5 : 1,
134
+ transition: "opacity 0.3s ease",
135
+ }}
136
+ />
137
  )}
138
  </Box>
139
+
140
  <Button
141
  onClick={handleClick}
142
  variant="contained"
143
+ disabled={isLoading}
144
  sx={{
145
  width: "100%",
146
+ height: "40px",
147
+ borderRadius: "20px",
148
  backgroundColor: listening ? "rgb(218, 176, 176)" : "rgb(126, 184, 203)",
149
+ fontWeight: "bold",
150
+ letterSpacing: "1px",
151
  "&:hover": {
152
+ backgroundColor: listening ? "rgb(198, 156, 156)" : "rgb(106, 164, 183)",
153
+ transform: "translateY(-1px)",
154
+ boxShadow: "0 4px 8px rgba(0, 0, 0, 0.2)",
155
+ },
156
+ transition: "all 0.3s ease",
157
+ "&:disabled": {
158
+ backgroundColor: "rgba(0, 0, 0, 0.12)",
159
+ color: "rgba(0, 0, 0, 0.26)",
160
  },
161
  }}
162
  >
163
+ {isLoading ? "Processing..." : listening ? `STOP (${timer})` : "SPEAK"}
164
  </Button>
165
  </Box>
166
+
167
+ <Snackbar
168
+ open={showError}
169
+ autoHideDuration={6000}
170
+ onClose={() => setShowError(false)}
171
+ anchorOrigin={{ vertical: "bottom", horizontal: "center" }}
172
+ >
173
+ <Alert onClose={() => setShowError(false)} severity="error" sx={{ width: "100%" }}>
174
+ {error || "An error occurred. Please try again."}
175
+ </Alert>
176
+ </Snackbar>
177
  </Box>
178
  );
179
  };