feat: add avatar border color customization and improve text contrast across user profile components
This commit is contained in:
@@ -37,7 +37,7 @@ import { getMxIdLocalPart, mxcUrlToHttp } from '../../../utils/matrix';
|
||||
import { UserAvatar } from '../../../components/user-avatar';
|
||||
import { useMediaAuthentication } from '../../../hooks/useMediaAuthentication';
|
||||
import { useAuthenticatedMediaUrl } from '../../../hooks/useAuthenticatedMediaUrl';
|
||||
import { nameInitials, getContrastingTextColor } from '../../../utils/common';
|
||||
import { nameInitials, getContrastingTextColor, stripAlphaFromColor, getTextShadowColor } from '../../../utils/common';
|
||||
import { AsyncStatus, useAsyncCallback } from '../../../hooks/useAsyncCallback';
|
||||
import { useFilePicker } from '../../../hooks/useFilePicker';
|
||||
import { useObjectURL } from '../../../hooks/useObjectURL';
|
||||
@@ -563,6 +563,11 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
? rgbaToHex(localBorderColor)
|
||||
: profileStyle.avatarBorderColor;
|
||||
|
||||
const previewPillBgColor = previewBorderColor ? stripAlphaFromColor(previewBorderColor) : undefined;
|
||||
const previewProfileColor = previewBorderColor ? stripAlphaFromColor(previewBorderColor) : (userColor || colorMXID(userId));
|
||||
|
||||
const previewTextShadow = `0 1px 4px ${getTextShadowColor(previewProfileColor)}`;
|
||||
|
||||
return (
|
||||
<Box direction="Column" gap="300">
|
||||
<Box
|
||||
@@ -710,7 +715,7 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
as="button"
|
||||
onClick={handleAvatarClick}
|
||||
style={{
|
||||
backgroundColor: color.Surface.Container,
|
||||
backgroundColor: previewBorderColor || color.Surface.Container,
|
||||
border: 'none',
|
||||
padding: 0,
|
||||
cursor: 'pointer',
|
||||
@@ -718,6 +723,7 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
}}
|
||||
>
|
||||
<AvatarPresence
|
||||
badgeBackgroundColor={previewBorderColor}
|
||||
badge={
|
||||
presence && (
|
||||
<PresenceBadge presence={presence.presence} status={presence.status} />
|
||||
@@ -727,6 +733,8 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
<Avatar
|
||||
size="500"
|
||||
style={{
|
||||
width: toRem(72),
|
||||
height: toRem(72),
|
||||
outline: previewBorderColor
|
||||
? `${toRem(4)} solid ${previewBorderColor}`
|
||||
: `${config.borderWidth.B600} solid ${color.Surface.Container}`,
|
||||
@@ -905,7 +913,7 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
size="H4"
|
||||
className={classNames(BreakWord, LineClamp3)}
|
||||
title={profile.displayName || getMxIdLocalPart(userId)}
|
||||
style={{ color: userColor || colorMXID(userId) }}
|
||||
style={{ color: previewProfileColor, textShadow: previewTextShadow }}
|
||||
>
|
||||
{profile.displayName || getMxIdLocalPart(userId) || userId}
|
||||
</Text>
|
||||
@@ -937,7 +945,7 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
size="T200"
|
||||
className={BreakWord}
|
||||
title={userId}
|
||||
style={{ color: userColor || colorMXID(userId), opacity: 0.8 }}
|
||||
style={{ color: previewProfileColor, textShadow: previewTextShadow }}
|
||||
>
|
||||
{userId}
|
||||
</Text>
|
||||
@@ -947,8 +955,8 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
onMouseEnter={() => setHoveredArea('status')}
|
||||
onMouseLeave={() => setHoveredArea(null)}
|
||||
style={{
|
||||
backgroundColor: previewBorderColor || color.Surface.Container,
|
||||
border: previewBorderColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
backgroundColor: previewPillBgColor || color.Surface.Container,
|
||||
border: previewPillBgColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
padding: `${toRem(6)} ${toRem(10)}`,
|
||||
borderRadius: toRem(16),
|
||||
maxWidth: toRem(250),
|
||||
@@ -998,16 +1006,15 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
size="T300"
|
||||
className={BreakWord}
|
||||
style={{
|
||||
opacity: presence?.status ? 1 : 0.5,
|
||||
fontStyle: presence?.status ? 'normal' : 'italic',
|
||||
color: previewBorderColor ? getContrastingTextColor(previewBorderColor) : undefined,
|
||||
color: previewPillBgColor ? getContrastingTextColor(previewPillBgColor) : undefined,
|
||||
}}
|
||||
>
|
||||
{presence?.status || 'Click to set a custom status...'}</Text>
|
||||
</Box>
|
||||
{presence?.status && hoveredArea === 'status' && (
|
||||
<>
|
||||
<Icon size="50" src={Icons.Pencil} style={{ color: previewBorderColor ? getContrastingTextColor(previewBorderColor) : undefined }} />
|
||||
<Icon size="50" src={Icons.Pencil} style={{ color: previewPillBgColor ? getContrastingTextColor(previewPillBgColor) : undefined }} />
|
||||
<Box
|
||||
as="button"
|
||||
onClick={(e) => {
|
||||
@@ -1038,8 +1045,8 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
<Box alignItems="Center" gap="200" wrap="Wrap" justifyContent="Center">
|
||||
<Box
|
||||
style={{
|
||||
backgroundColor: previewBorderColor || color.Surface.Container,
|
||||
border: previewBorderColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
backgroundColor: previewPillBgColor || color.Surface.Container,
|
||||
border: previewPillBgColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
padding: `${toRem(4)} ${toRem(8)}`,
|
||||
borderRadius: toRem(16),
|
||||
}}
|
||||
@@ -1047,7 +1054,7 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
<Text
|
||||
size="B300"
|
||||
style={{
|
||||
color: previewBorderColor ? getContrastingTextColor(previewBorderColor) : undefined,
|
||||
color: previewPillBgColor ? getContrastingTextColor(previewPillBgColor) : undefined,
|
||||
}}
|
||||
>
|
||||
ruv.wtf
|
||||
@@ -1055,8 +1062,8 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
</Box>
|
||||
<Box
|
||||
style={{
|
||||
backgroundColor: previewBorderColor || color.Surface.Container,
|
||||
border: previewBorderColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
backgroundColor: previewPillBgColor || color.Surface.Container,
|
||||
border: previewPillBgColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
padding: `${toRem(4)} ${toRem(8)}`,
|
||||
borderRadius: toRem(16),
|
||||
}}
|
||||
@@ -1064,7 +1071,7 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
<Text
|
||||
size="B300"
|
||||
style={{
|
||||
color: previewBorderColor ? getContrastingTextColor(previewBorderColor) : undefined,
|
||||
color: previewPillBgColor ? getContrastingTextColor(previewPillBgColor) : undefined,
|
||||
}}
|
||||
>
|
||||
Share
|
||||
@@ -1072,8 +1079,8 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
</Box>
|
||||
<Box
|
||||
style={{
|
||||
backgroundColor: previewBorderColor || color.Surface.Container,
|
||||
border: previewBorderColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
backgroundColor: previewPillBgColor || color.Surface.Container,
|
||||
border: previewPillBgColor ? 'none' : `${toRem(1)} solid ${color.Surface.ContainerLine}`,
|
||||
padding: `${toRem(4)} ${toRem(8)}`,
|
||||
borderRadius: toRem(16),
|
||||
}}
|
||||
@@ -1081,7 +1088,7 @@ function ProfileBanner({ avatarRef, nameRef }: { avatarRef: React.RefObject<HTML
|
||||
<Text
|
||||
size="B300"
|
||||
style={{
|
||||
color: previewBorderColor ? getContrastingTextColor(previewBorderColor) : undefined,
|
||||
color: previewPillBgColor ? getContrastingTextColor(previewPillBgColor) : undefined,
|
||||
}}
|
||||
>
|
||||
Admin
|
||||
|
||||
Reference in New Issue
Block a user