Add elapsed time to call interface

GitLab: #161

Change-Id: I7f8ecffcb9ad7ce796f525be70476e7b223c0963
diff --git a/client/src/contexts/CallProvider.tsx b/client/src/contexts/CallProvider.tsx
index da16a01..f29ad74 100644
--- a/client/src/contexts/CallProvider.tsx
+++ b/client/src/contexts/CallProvider.tsx
@@ -51,6 +51,7 @@
   setIsFullscreen: SetState<boolean>;
   callRole: CallRole;
   callStatus: CallStatus;
+  callStartTime: Date | undefined;
 
   acceptCall: () => void;
 }
@@ -75,6 +76,7 @@
   setIsFullscreen: () => {},
   callRole: 'caller',
   callStatus: CallStatus.Default,
+  callStartTime: undefined,
 
   acceptCall: () => {},
 };
@@ -100,6 +102,7 @@
   const [isChatShown, setIsChatShown] = useState(false);
   const [isFullscreen, setIsFullscreen] = useState(false);
   const [callStatus, setCallStatus] = useState(routeState?.callStatus);
+  const [callStartTime, setCallStartTime] = useState<Date | undefined>(undefined);
 
   // TODO: This logic will have to change to support multiple people in a call. Could we move this logic to the server?
   //       The client could make a single request with the conversationId, and the server would be tasked with sending
@@ -214,6 +217,7 @@
     if (callStatus === CallStatus.Connecting && isConnected) {
       console.info('Changing call status to InCall');
       setCallStatus(CallStatus.InCall);
+      setCallStartTime(new Date());
     }
   }, [isConnected, callStatus]);
 
@@ -283,6 +287,7 @@
         setIsFullscreen,
         callRole,
         callStatus,
+        callStartTime,
         acceptCall,
       }}
     >
diff --git a/client/src/pages/CallInterface.tsx b/client/src/pages/CallInterface.tsx
index 5dbda36..c0ab334 100644
--- a/client/src/pages/CallInterface.tsx
+++ b/client/src/pages/CallInterface.tsx
@@ -87,11 +87,13 @@
 }
 
 const CallInterface = () => {
-  const { isVideoOn, localStream, remoteStream } = useContext(CallContext);
+  const { isVideoOn, localStream, remoteStream, callStartTime } = useContext(CallContext);
   const gridItemRef = useRef(null);
   const remoteVideoRef = useRef<HTMLVideoElement | null>(null);
   const localVideoRef = useRef<HTMLVideoElement | null>(null);
 
+  const [elapsedTime, setElapsedTime] = useState<number>();
+
   useEffect(() => {
     if (localStream && localVideoRef.current) {
       localVideoRef.current.srcObject = localStream;
@@ -104,6 +106,15 @@
     }
   }, [remoteStream]);
 
+  useEffect(() => {
+    if (callStartTime) {
+      const interval = setInterval(() => {
+        setElapsedTime((new Date().getTime() - callStartTime.getTime()) / 1000);
+      }, 1000);
+      return () => clearInterval(interval);
+    }
+  }, [callStartTime]);
+
   return (
     <Box display="flex" flexGrow={1}>
       <video
@@ -113,7 +124,7 @@
       />
       <Box flexGrow={1} margin={2} display="flex" flexDirection="column">
         {/* Guest video, takes the whole screen */}
-        <CallInterfaceInformation />
+        <CallInterfaceInformation elapsedTime={elapsedTime} />
         <Box flexGrow={1} marginY={2} position="relative">
           <Draggable bounds="parent" nodeRef={localVideoRef ?? undefined}>
             <video
@@ -146,14 +157,37 @@
   );
 };
 
-const CallInterfaceInformation = () => {
+const formatElapsedSeconds = (elapsedSeconds: number): string => {
+  const seconds = Math.floor(elapsedSeconds % 60);
+  elapsedSeconds = Math.floor(elapsedSeconds / 60);
+  const minutes = elapsedSeconds % 60;
+  elapsedSeconds = Math.floor(elapsedSeconds / 60);
+  const hours = elapsedSeconds % 24;
+
+  const times: string[] = [];
+  if (hours > 0) {
+    times.push(hours.toString().padStart(2, '0'));
+  }
+  times.push(minutes.toString().padStart(2, '0'));
+  times.push(seconds.toString().padStart(2, '0'));
+
+  return times.join(':');
+};
+
+interface CallInterfaceInformationProps {
+  elapsedTime?: number;
+}
+
+const CallInterfaceInformation = ({ elapsedTime = 0 }: CallInterfaceInformationProps) => {
+  const elapsedTimerString = formatElapsedSeconds(elapsedTime);
+
   return (
     <Stack direction="row" justifyContent="space-between" alignItems="center">
       <Typography color="white" component="p">
         Alain Thérieur
       </Typography>
       <Typography color="white" component="p">
-        01:23
+        {elapsedTimerString}
       </Typography>
     </Stack>
   );