chore(site): demui <Avatar /> and <AvatarCard /> (#24527)

This pull-request takes our `<Avatar />` and `<AvatarCard />` component
and removes the bespoke styles to them. As an added bonus I took care of
the `getExternalImageStylesFromUrl` helper util and cleaned out the
MUI-specific code to it.

There are some remnants of `@emotion/react` in
`getExternalImageStylesFromUrl` however we don't have a theme switcher
that could appropriately handle it yet.
This commit is contained in:
Jake Howell
2026-04-21 02:22:16 +10:00
committed by GitHub
parent 3b561dcea9
commit 7f1b9cb648
5 changed files with 27 additions and 43 deletions
+1 -1
View File
@@ -78,7 +78,7 @@ export const Avatar: React.FC<AvatarProps> = ({
<AvatarPrimitive.Image
src={src}
className="aspect-square size-full object-contain"
css={getExternalImageStylesFromUrl(theme.externalImages, src)}
style={getExternalImageStylesFromUrl(theme.externalImages, src)}
/>
{fallback && (
<AvatarPrimitive.Fallback className="flex h-full w-full items-center justify-center rounded-full">
+7 -19
View File
@@ -1,6 +1,7 @@
import { type CSSObject, useTheme } from "@emotion/react";
import type { FC, ReactNode } from "react";
import { Avatar } from "#/components/Avatar/Avatar";
import { cn } from "#/utils/cn";
type AvatarCardProps = {
header: string;
@@ -19,16 +20,12 @@ export const AvatarCard: FC<AvatarCardProps> = ({
return (
<div
css={{
className={cn(
"flex flex-row flex-nowrap gap-4 items-center",
"border border-solid p-4 rounded-lg cursor-default",
)}
style={{
maxWidth: maxWidth === "none" ? undefined : `${maxWidth}px`,
display: "flex",
flexFlow: "row nowrap",
alignItems: "center",
border: `1px solid ${theme.palette.divider}`,
gap: "16px",
padding: "16px",
borderRadius: "8px",
cursor: "default",
}}
>
{/**
@@ -41,16 +38,7 @@ export const AvatarCard: FC<AvatarCardProps> = ({
<h3
// Lets users hover over truncated text to see whole thing
title={header}
css={[
theme.typography.body1 as CSSObject,
{
lineHeight: 1.4,
margin: 0,
overflow: "hidden",
whiteSpace: "nowrap",
textOverflow: "ellipsis",
},
]}
className="text-base leading-snug m-0 truncate"
>
{header}
</h3>
@@ -2,6 +2,7 @@ import { useTheme } from "@emotion/react";
import { getExternalImageStylesFromUrl } from "#/theme/externalImages";
export const ExternalImage: React.FC<React.ComponentPropsWithRef<"img">> = ({
style,
...props
}) => {
const theme = useTheme();
@@ -9,7 +10,10 @@ export const ExternalImage: React.FC<React.ComponentPropsWithRef<"img">> = ({
return (
// biome-ignore lint/a11y/useAltText: alt should be passed in as a prop
<img
css={getExternalImageStylesFromUrl(theme.externalImages, props.src)}
style={{
...getExternalImageStylesFromUrl(theme.externalImages, props.src),
...style,
}}
{...props}
/>
);
+5 -13
View File
@@ -159,19 +159,11 @@ const IconsPage: FC = () => {
<img
alt={icon.url}
src={icon.url}
css={[
{
width: 60,
height: 60,
objectFit: "contain",
pointerEvents: "none",
padding: 12,
},
parseImageParameters(
theme.externalImages,
defaultParametersForBuiltinIcons.get(icon.url) ?? "",
),
]}
className="size-16 object-contain pointer-events-none p-3"
style={parseImageParameters(
theme.externalImages,
defaultParametersForBuiltinIcons.get(icon.url) ?? "",
)}
/>
<figcaption className="w-[88px] h-12 text-[13px] text-ellipsis text-center overflow-hidden">
{icon.description}
+9 -9
View File
@@ -1,17 +1,17 @@
import type { CSSObject } from "@emotion/react";
import type { CSSProperties } from "react";
export interface ExternalImageModeStyles {
/**
* monochrome icons will be flattened to a neutral, theme-appropriate color.
* eg. white, light gray, dark gray, black
*/
monochrome?: CSSObject;
monochrome?: CSSProperties;
/**
* @default
* fullcolor icons should look their best of any background, with distinct colors
* and good contrast. This is the default, and won't alter the image.
*/
fullcolor?: CSSObject;
fullcolor?: CSSProperties;
/**
* whiteWithColor is useful for icons that are primarily white, or contain white text,
* which are hard to see or look incorrect on light backgrounds. This setting will apply
@@ -20,7 +20,7 @@ export interface ExternalImageModeStyles {
* You can also specify a `brightness` level if your icon still doesn't look quite right.
* eg. /icon/aws.svg?blackWithColor&brightness=1.5
*/
whiteWithColor?: CSSObject;
whiteWithColor?: CSSProperties;
/**
* blackWithColor is useful for icons that are primarily black, or contain black text,
* which are hard to see or look incorrect on dark backgrounds. This setting will apply
@@ -29,7 +29,7 @@ export interface ExternalImageModeStyles {
* You can also specify a `brightness` level if your icon still doesn't look quite right.
* eg. /icon/aws.svg?blackWithColor&brightness=1.5
*/
blackWithColor?: CSSObject;
blackWithColor?: CSSProperties;
}
export const forDarkThemes: ExternalImageModeStyles = {
@@ -64,14 +64,14 @@ const multiplier = /^\d+(\.\d+)?%?$/;
*/
const parseInvertFilterParameters = (
params: URLSearchParams,
baseStyles?: CSSObject,
baseStyles?: CSSProperties,
) => {
// Only apply additional styles if the current theme supports this mode
if (!baseStyles) {
return;
}
let extraStyles: CSSObject | undefined;
let extraStyles: CSSProperties | undefined;
const brightness = params.get("brightness") ?? "";
if (multiplier.test(brightness)) {
@@ -93,10 +93,10 @@ const parseInvertFilterParameters = (
export function parseImageParameters(
modes: ExternalImageModeStyles,
searchString: string,
): CSSObject | undefined {
): CSSProperties | undefined {
const params = new URLSearchParams(searchString);
let styles: CSSObject | undefined = modes.fullcolor;
let styles: CSSProperties | undefined = modes.fullcolor;
if (params.has("monochrome")) {
styles = modes.monochrome;