mirror of
https://github.com/vector-im/element-call.git
synced 2026-09-10 21:55:19 +00:00
Introduce ElementCallView
Being in a call and deciding to show one are different jobs, but RoomPage did both: routing, authentication, resolving room aliases and knocking, and then the call itself. Only the first set belongs to whatever is hosting Element Call. Add ElementCallView as the seam between them. It takes a client and a call to join, and owns whether the user has joined — which is the call's own business rather than its host's. RoomPage keeps everything about arriving at a call and renders this for the call itself. Nothing else moves yet. muteStates is still passed in, because the standalone shell shares one with the lobby it shows while waiting to be let into a room, and two instances would both report the user's mute state to the host.
This commit is contained in:
@@ -0,0 +1,73 @@
|
|||||||
|
/*
|
||||||
|
Copyright 2026 Element Creations Ltd.
|
||||||
|
|
||||||
|
SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
|
||||||
|
Please see LICENSE in the repository root for full details.
|
||||||
|
*/
|
||||||
|
|
||||||
|
import { type FC, type ReactNode, useState } from "react";
|
||||||
|
import { type MatrixClient } from "matrix-js-sdk";
|
||||||
|
import { type MatrixRTCSession } from "matrix-js-sdk/lib/matrixrtc";
|
||||||
|
|
||||||
|
import { GroupCallView } from "./room/GroupCallView";
|
||||||
|
import { type MuteStates } from "./state/MuteStates";
|
||||||
|
import { type UrlParams } from "./UrlParams";
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
/** The client to place the call with. */
|
||||||
|
client: MatrixClient;
|
||||||
|
/** The call to join. */
|
||||||
|
rtcSession: MatrixRTCSession;
|
||||||
|
/** The audio and video mute state to start from, and keep in step with. */
|
||||||
|
muteStates: MuteStates;
|
||||||
|
/**
|
||||||
|
* Whether the user is signed in as a guest, and so should be offered the
|
||||||
|
* chance to create an account when the call ends.
|
||||||
|
*/
|
||||||
|
isPasswordlessUser: boolean;
|
||||||
|
/** Whether to keep the user in this call rather than letting them navigate. */
|
||||||
|
confineToRoom: boolean;
|
||||||
|
/** Whether to wait for the host to ask us to join. */
|
||||||
|
preload: UrlParams["preload"];
|
||||||
|
/** Whether to enter the call directly, without showing the lobby first. */
|
||||||
|
skipLobby: UrlParams["skipLobby"];
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A call, as a component.
|
||||||
|
*
|
||||||
|
* This owns being in a call, and nothing about how Element Call came to be
|
||||||
|
* showing one: no routing, no authentication, no resolving of room aliases.
|
||||||
|
* Those belong to whatever is hosting it — the standalone app's own shell, or
|
||||||
|
* an application embedding Element Call directly.
|
||||||
|
*
|
||||||
|
* TODO: `muteStates` is still passed in, because the standalone shell shares
|
||||||
|
* one with the lobby it shows while waiting to be let into a room. Ownership
|
||||||
|
* moves here once that lobby has its own.
|
||||||
|
*/
|
||||||
|
export const ElementCallView: FC<Props> = ({
|
||||||
|
client,
|
||||||
|
rtcSession,
|
||||||
|
muteStates,
|
||||||
|
isPasswordlessUser,
|
||||||
|
confineToRoom,
|
||||||
|
preload,
|
||||||
|
skipLobby,
|
||||||
|
}): ReactNode => {
|
||||||
|
// Whether the user is in the call is the call's own business, not its host's.
|
||||||
|
const [joined, setJoined] = useState(false);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<GroupCallView
|
||||||
|
client={client}
|
||||||
|
rtcSession={rtcSession}
|
||||||
|
joined={joined}
|
||||||
|
setJoined={setJoined}
|
||||||
|
isPasswordlessUser={isPasswordlessUser}
|
||||||
|
confineToRoom={confineToRoom}
|
||||||
|
preload={preload}
|
||||||
|
skipLobby={skipLobby}
|
||||||
|
muteStates={muteStates}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
};
|
||||||
@@ -25,7 +25,7 @@ import {
|
|||||||
import { useClientLegacy } from "../ClientContext";
|
import { useClientLegacy } from "../ClientContext";
|
||||||
import { ErrorPage, FullScreenView, LoadingPage } from "../FullScreenView";
|
import { ErrorPage, FullScreenView, LoadingPage } from "../FullScreenView";
|
||||||
import { RoomAuthView } from "./RoomAuthView";
|
import { RoomAuthView } from "./RoomAuthView";
|
||||||
import { GroupCallView } from "./GroupCallView";
|
import { ElementCallView } from "../ElementCallView";
|
||||||
import { useRoomIdentifier, useUrlParams } from "../UrlParams";
|
import { useRoomIdentifier, useUrlParams } from "../UrlParams";
|
||||||
import { useRegisterPasswordlessUser } from "../auth/useRegisterPasswordlessUser";
|
import { useRegisterPasswordlessUser } from "../auth/useRegisterPasswordlessUser";
|
||||||
import { HomePage } from "../home/HomePage";
|
import { HomePage } from "../home/HomePage";
|
||||||
@@ -62,7 +62,6 @@ export const RoomPage: FC = (): ReactNode => {
|
|||||||
const { avatarUrl, displayName: userDisplayName } = useProfile(client);
|
const { avatarUrl, displayName: userDisplayName } = useProfile(client);
|
||||||
|
|
||||||
const groupCallState = useLoadGroupCall(client, roomIdOrAlias, viaServers);
|
const groupCallState = useLoadGroupCall(client, roomIdOrAlias, viaServers);
|
||||||
const [joined, setJoined] = useState(false);
|
|
||||||
|
|
||||||
const devices = useMediaDevices();
|
const devices = useMediaDevices();
|
||||||
const [muteStates, setMuteStates] = useState<MuteStates | null>(null);
|
const [muteStates, setMuteStates] = useState<MuteStates | null>(null);
|
||||||
@@ -125,11 +124,9 @@ export const RoomPage: FC = (): ReactNode => {
|
|||||||
case "loaded":
|
case "loaded":
|
||||||
return (
|
return (
|
||||||
muteStates && (
|
muteStates && (
|
||||||
<GroupCallView
|
<ElementCallView
|
||||||
client={client!}
|
client={client!}
|
||||||
rtcSession={groupCallState.rtcSession}
|
rtcSession={groupCallState.rtcSession}
|
||||||
joined={joined}
|
|
||||||
setJoined={setJoined}
|
|
||||||
isPasswordlessUser={passwordlessUser}
|
isPasswordlessUser={passwordlessUser}
|
||||||
confineToRoom={confineToRoom}
|
confineToRoom={confineToRoom}
|
||||||
preload={preload}
|
preload={preload}
|
||||||
|
|||||||
Reference in New Issue
Block a user