Refactor reactions / hand raised to use rxjs and start ordering tiles based on hand raised. (#2885)

* Add support for using CallViewModel for reactions sounds.

* Drop setting

* Convert reaction sounds to call view model / rxjs

* Use call view model for hand raised reactions

* Support raising reactions for matrix rtc members.

* Tie up last bits of useReactions

* linting

* Update calleventaudiorenderer

* Update reaction audio renderer

* more test bits

* All the test bits and pieces

* More refactors

* Refactor reactions into a sender and receiver.

* Fixup reaction toggle button

* Adapt reactions test

* Tests all pass.

* lint

* fix a couple of bugs

* remove unused helper file

* lint

* finnish notation

* Add tests for useReactionsReader

* remove mistaken vitest file

* fix

* filter

* invert

* fixup tests with fake timers

* Port useReactionsReader hook to ReactionsReader class.

* lint

* exclude some files from coverage

* Add screen share sound effect.

* cancel sub on destroy

* tidy tidy
This commit is contained in:
Will Hunt
2024-12-19 15:54:28 +00:00
committed by GitHub
parent 7d00f85abc
commit abf2ecd521
28 changed files with 1835 additions and 1184 deletions

View File

@@ -24,8 +24,10 @@ import {
import { useTranslation } from "react-i18next";
import { logger } from "matrix-js-sdk/src/logger";
import classNames from "classnames";
import { useObservableState } from "observable-hooks";
import { map } from "rxjs";
import { useReactions } from "../useReactions";
import { useReactionsSender } from "../reactions/useReactionsSender";
import styles from "./ReactionToggleButton.module.css";
import {
type ReactionOption,
@@ -33,6 +35,7 @@ import {
ReactionsRowSize,
} from "../reactions";
import { Modal } from "../Modal";
import { type CallViewModel } from "../state/CallViewModel";
interface InnerButtonProps extends ComponentPropsWithoutRef<"button"> {
raised: boolean;
@@ -162,22 +165,27 @@ export function ReactionPopupMenu({
}
interface ReactionToggleButtonProps extends ComponentPropsWithoutRef<"button"> {
userId: string;
identifier: string;
vm: CallViewModel;
}
export function ReactionToggleButton({
userId,
identifier,
vm,
...props
}: ReactionToggleButtonProps): ReactNode {
const { t } = useTranslation();
const { raisedHands, toggleRaisedHand, sendReaction, reactions } =
useReactions();
const { toggleRaisedHand, sendReaction } = useReactionsSender();
const [busy, setBusy] = useState(false);
const [showReactionsMenu, setShowReactionsMenu] = useState(false);
const [errorText, setErrorText] = useState<string>();
const isHandRaised = !!raisedHands[userId];
const canReact = !reactions[userId];
const isHandRaised = useObservableState(
vm.handsRaised$.pipe(map((v) => !!v[identifier])),
);
const canReact = useObservableState(
vm.reactions$.pipe(map((v) => !v[identifier])),
);
useEffect(() => {
// Clear whenever the reactions menu state changes.
@@ -223,7 +231,7 @@ export function ReactionToggleButton({
<InnerButton
disabled={busy}
onClick={() => setShowReactionsMenu((show) => !show)}
raised={isHandRaised}
raised={!!isHandRaised}
open={showReactionsMenu}
{...props}
/>
@@ -237,8 +245,8 @@ export function ReactionToggleButton({
>
<ReactionPopupMenu
errorText={errorText}
isHandRaised={isHandRaised}
canReact={!busy && canReact}
isHandRaised={!!isHandRaised}
canReact={!busy && !!canReact}
sendReaction={(reaction) => void sendRelation(reaction)}
toggleRaisedHand={wrappedToggleRaisedHand}
/>