Fix layout and visual regressions around default avatars (#10031)
This commit is contained in:
parent
5a08859e37
commit
0d1fce37b2
5 changed files with 21 additions and 28 deletions
|
@ -153,10 +153,7 @@ describe("Spaces", () => {
|
||||||
|
|
||||||
openSpaceCreateMenu().within(() => {
|
openSpaceCreateMenu().within(() => {
|
||||||
cy.get(".mx_SpaceCreateMenuType_private").click();
|
cy.get(".mx_SpaceCreateMenuType_private").click();
|
||||||
cy.get('.mx_SpaceBasicSettings_avatarContainer input[type="file"]').selectFile(
|
// We don't set an avatar here to get a Percy snapshot of the default avatar style for spaces
|
||||||
"cypress/fixtures/riot.png",
|
|
||||||
{ force: true },
|
|
||||||
);
|
|
||||||
cy.get('input[label="Address"]').should("not.exist");
|
cy.get('input[label="Address"]').should("not.exist");
|
||||||
cy.get('textarea[label="Description"]').type("This is a personal space to mourn Riot.im...");
|
cy.get('textarea[label="Description"]').type("This is a personal space to mourn Riot.im...");
|
||||||
cy.get('input[label="Name"]').type("This is my Riot{enter}");
|
cy.get('input[label="Name"]').type("This is my Riot{enter}");
|
||||||
|
@ -169,6 +166,7 @@ describe("Spaces", () => {
|
||||||
|
|
||||||
cy.contains(".mx_RoomList .mx_RoomTile", "Sample Room").should("exist");
|
cy.contains(".mx_RoomList .mx_RoomTile", "Sample Room").should("exist");
|
||||||
cy.contains(".mx_SpaceHierarchy_list .mx_SpaceHierarchy_roomTile", "Sample Room").should("exist");
|
cy.contains(".mx_SpaceHierarchy_list .mx_SpaceHierarchy_roomTile", "Sample Room").should("exist");
|
||||||
|
cy.get(".mx_LeftPanel_outerWrapper").percySnapshotElement("Left panel with default avatar space");
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should allow user to invite another to a space", () => {
|
it("should allow user to invite another to a space", () => {
|
||||||
|
|
|
@ -277,14 +277,11 @@ $activeBorderColor: $primary-content;
|
||||||
.mx_BaseAvatar:not(.mx_UserMenu_userAvatar_BaseAvatar) .mx_BaseAvatar_initial {
|
.mx_BaseAvatar:not(.mx_UserMenu_userAvatar_BaseAvatar) .mx_BaseAvatar_initial {
|
||||||
color: $secondary-content;
|
color: $secondary-content;
|
||||||
border-radius: 8px;
|
border-radius: 8px;
|
||||||
background-color: $panel-actions;
|
|
||||||
font-size: $font-15px !important; /* override inline style */
|
|
||||||
font-weight: $font-semi-bold;
|
font-weight: $font-semi-bold;
|
||||||
line-height: $font-18px;
|
line-height: $font-18px;
|
||||||
|
/* override inline styles which are part of the default avatar style as these uses a monochrome style */
|
||||||
& + .mx_BaseAvatar_image {
|
background-color: $panel-actions !important;
|
||||||
visibility: hidden;
|
font-size: $font-15px !important;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.mx_SpaceTreeLevel {
|
.mx_SpaceTreeLevel {
|
||||||
|
|
|
@ -25,6 +25,8 @@ limitations under the License.
|
||||||
|
|
||||||
.mx_UserMenu_userAvatar {
|
.mx_UserMenu_userAvatar {
|
||||||
position: relative;
|
position: relative;
|
||||||
|
/* without this a default avatar will cause this to be 4px oversized and out of alignment */
|
||||||
|
display: inherit;
|
||||||
|
|
||||||
.mx_BaseAvatar {
|
.mx_BaseAvatar {
|
||||||
pointer-events: none; /* makes the avatar non-draggable */
|
pointer-events: none; /* makes the avatar non-draggable */
|
||||||
|
|
|
@ -15,7 +15,7 @@ See the License for the specific language governing permissions and
|
||||||
limitations under the License.
|
limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import React, { useCallback, useContext, useEffect, useState } from "react";
|
import React, { CSSProperties, useCallback, useContext, useEffect, useState } from "react";
|
||||||
import classNames from "classnames";
|
import classNames from "classnames";
|
||||||
import { ResizeMethod } from "matrix-js-sdk/src/@types/partials";
|
import { ResizeMethod } from "matrix-js-sdk/src/@types/partials";
|
||||||
import { ClientEvent } from "matrix-js-sdk/src/client";
|
import { ClientEvent } from "matrix-js-sdk/src/client";
|
||||||
|
@ -51,6 +51,7 @@ interface IProps {
|
||||||
inputRef?: React.RefObject<HTMLImageElement & HTMLSpanElement>;
|
inputRef?: React.RefObject<HTMLImageElement & HTMLSpanElement>;
|
||||||
className?: string;
|
className?: string;
|
||||||
tabIndex?: number;
|
tabIndex?: number;
|
||||||
|
style?: CSSProperties;
|
||||||
}
|
}
|
||||||
|
|
||||||
const calculateUrls = (url: string | undefined, urls: string[] | undefined, lowBandwidth: boolean): string[] => {
|
const calculateUrls = (url: string | undefined, urls: string[] | undefined, lowBandwidth: boolean): string[] => {
|
||||||
|
@ -132,10 +133,17 @@ const BaseAvatar: React.FC<IProps> = (props) => {
|
||||||
onClick,
|
onClick,
|
||||||
inputRef,
|
inputRef,
|
||||||
className,
|
className,
|
||||||
|
style: parentStyle,
|
||||||
resizeMethod: _unused, // to keep it from being in `otherProps`
|
resizeMethod: _unused, // to keep it from being in `otherProps`
|
||||||
...otherProps
|
...otherProps
|
||||||
} = props;
|
} = props;
|
||||||
|
|
||||||
|
const style = {
|
||||||
|
...parentStyle,
|
||||||
|
width: toPx(width),
|
||||||
|
height: toPx(height),
|
||||||
|
};
|
||||||
|
|
||||||
const [imageUrl, onError] = useImageUrl({ url, urls });
|
const [imageUrl, onError] = useImageUrl({ url, urls });
|
||||||
|
|
||||||
if (!imageUrl && defaultToInitialLetter && name) {
|
if (!imageUrl && defaultToInitialLetter && name) {
|
||||||
|
@ -151,10 +159,7 @@ const BaseAvatar: React.FC<IProps> = (props) => {
|
||||||
className={classNames("mx_BaseAvatar", className)}
|
className={classNames("mx_BaseAvatar", className)}
|
||||||
onClick={onClick}
|
onClick={onClick}
|
||||||
inputRef={inputRef}
|
inputRef={inputRef}
|
||||||
style={{
|
style={style}
|
||||||
width: toPx(width),
|
|
||||||
height: toPx(height),
|
|
||||||
}}
|
|
||||||
>
|
>
|
||||||
{avatar}
|
{avatar}
|
||||||
</AccessibleButton>
|
</AccessibleButton>
|
||||||
|
@ -165,10 +170,7 @@ const BaseAvatar: React.FC<IProps> = (props) => {
|
||||||
className={classNames("mx_BaseAvatar", className)}
|
className={classNames("mx_BaseAvatar", className)}
|
||||||
ref={inputRef}
|
ref={inputRef}
|
||||||
{...otherProps}
|
{...otherProps}
|
||||||
style={{
|
style={style}
|
||||||
width: toPx(width),
|
|
||||||
height: toPx(height),
|
|
||||||
}}
|
|
||||||
role="presentation"
|
role="presentation"
|
||||||
>
|
>
|
||||||
{avatar}
|
{avatar}
|
||||||
|
@ -185,10 +187,7 @@ const BaseAvatar: React.FC<IProps> = (props) => {
|
||||||
src={imageUrl}
|
src={imageUrl}
|
||||||
onClick={onClick}
|
onClick={onClick}
|
||||||
onError={onError}
|
onError={onError}
|
||||||
style={{
|
style={style}
|
||||||
width: toPx(width),
|
|
||||||
height: toPx(height),
|
|
||||||
}}
|
|
||||||
title={title}
|
title={title}
|
||||||
alt={_t("Avatar")}
|
alt={_t("Avatar")}
|
||||||
inputRef={inputRef}
|
inputRef={inputRef}
|
||||||
|
@ -202,10 +201,7 @@ const BaseAvatar: React.FC<IProps> = (props) => {
|
||||||
className={classNames("mx_BaseAvatar mx_BaseAvatar_image", className)}
|
className={classNames("mx_BaseAvatar mx_BaseAvatar_image", className)}
|
||||||
src={imageUrl}
|
src={imageUrl}
|
||||||
onError={onError}
|
onError={onError}
|
||||||
style={{
|
style={style}
|
||||||
width: toPx(width),
|
|
||||||
height: toPx(height),
|
|
||||||
}}
|
|
||||||
title={title}
|
title={title}
|
||||||
alt=""
|
alt=""
|
||||||
ref={inputRef}
|
ref={inputRef}
|
||||||
|
|
|
@ -7,7 +7,7 @@ exports[`MemberAvatar matches the snapshot 1`] = `
|
||||||
class="mx_BaseAvatar mx_BaseAvatar_image"
|
class="mx_BaseAvatar mx_BaseAvatar_image"
|
||||||
data-testid="avatar-img"
|
data-testid="avatar-img"
|
||||||
src="http://this.is.a.url//placekitten.com/400/400"
|
src="http://this.is.a.url//placekitten.com/400/400"
|
||||||
style="color: pink;"
|
style="color: pink; width: 35px; height: 35px;"
|
||||||
title="Hover title"
|
title="Hover title"
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
Loading…
Reference in a new issue