Make the loading state more subtle

- instead of a label we show a animated gradient
This commit is contained in:
Timo
2024-11-26 12:33:48 +01:00
parent 8f9bee79ae
commit 765f7b4f31
5 changed files with 38 additions and 9 deletions

View File

@@ -18,7 +18,9 @@ borders don't support gradients */
position: absolute;
z-index: -1; /* Put it below the outline */
opacity: 0; /* Hidden unless speaking */
transition: opacity ease 0.15s;
/* this only animates in one direction. In the other direction,
the background will disappear and the opacity has no effect.*/
transition: opacity ease 0.5s;
inset: calc(-1 * var(--cpd-border-width-4));
border-radius: var(--cpd-space-5x);
background-blend-mode: overlay, normal;
@@ -48,6 +50,11 @@ borders don't support gradients */
outline: var(--cpd-border-width-2) solid var(--cpd-color-bg-canvas-default) !important;
}
.tile.loading {
/* !important because loading border should take priority over hover */
outline: var(--cpd-border-width-2) solid var(--cpd-color-bg-canvas-default) !important;
}
.tile.handRaised::before {
background: linear-gradient(
119deg,
@@ -62,6 +69,31 @@ borders don't support gradients */
opacity: 1;
}
.tile.loading::before {
background: linear-gradient(
var(--angle),
var(--cpd-color-green-900) 0%,
var(--cpd-color-blue-200) 100%
);
opacity: 1;
animation: rotate-gradient linear 2s infinite;
}
@property --angle {
syntax: "<angle>";
inherits: false;
initial-value: 0deg;
}
@keyframes rotate-gradient {
from {
--angle: 0deg;
}
to {
--angle: 360deg;
}
}
@media (hover: hover) {
.tile:hover {
outline: var(--cpd-border-width-2) solid

View File

@@ -42,6 +42,7 @@ import {
useDisplayName,
LocalUserMediaViewModel,
RemoteUserMediaViewModel,
EncryptionStatus,
} from "../state/MediaViewModel";
import { Slider } from "../Slider";
import { MediaView } from "./MediaView";
@@ -145,6 +146,8 @@ const UserMediaTile = forwardRef<HTMLDivElement, UserMediaTileProps>(
className={classNames(className, styles.tile, {
[styles.speaking]: showSpeaking,
[styles.handRaised]: !showSpeaking && !!handRaised,
[styles.loading]:
encryptionStatus === EncryptionStatus.Connecting && !vm.local,
})}
nameTagLeadingIcon={
<AudioIcon

View File

@@ -75,7 +75,7 @@ describe("MediaView", () => {
<MediaView {...baseProps} video={undefined} localParticipant={false} />,
);
expect(screen.getByRole("img", { name: "some name" })).toBeVisible();
expect(screen.getByText("video_tile.waiting_for_media")).toBeVisible();
expect(screen.getByTestId("videoTile")).toBeVisible();
});
});

View File

@@ -120,11 +120,6 @@ export const MediaView = forwardRef<HTMLDivElement, Props>(
/>
)}
</div>
{!video && !localParticipant && (
<div className={styles.status}>
{t("video_tile.waiting_for_media")}
</div>
)}
{/* TODO: Bring this back once encryption status is less broken */}
{/*encryptionStatus !== EncryptionStatus.Okay && (
<div className={styles.status}>