From 85b1f166e8fb122d7db8a69c9c659164de6e9823 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Thu, 12 Aug 2021 12:03:14 +0100 Subject: [PATCH] post-merge tidy up --- res/css/structures/_SpaceHierarchy.scss | 8 +- src/components/structures/SpaceHierarchy.tsx | 264 ++++++++++--------- src/i18n/strings/en_EN.json | 8 +- 3 files changed, 154 insertions(+), 126 deletions(-) diff --git a/res/css/structures/_SpaceHierarchy.scss b/res/css/structures/_SpaceHierarchy.scss index 0cefaf252f..74dfb5da6b 100644 --- a/res/css/structures/_SpaceHierarchy.scss +++ b/res/css/structures/_SpaceHierarchy.scss @@ -116,6 +116,12 @@ limitations under the License. } } + .mx_SpaceHierarchy_list { + list-style: none; + padding: 0; + margin: 0; + } + .mx_SpaceHierarchy_roomCount { > h3 { display: inline; @@ -264,7 +270,7 @@ limitations under the License. } } - li.mx_SpaceRoomDirectory_roomTileWrapper { + li.mx_SpaceHierarchy_roomTileWrapper { list-style: none; } diff --git a/src/components/structures/SpaceHierarchy.tsx b/src/components/structures/SpaceHierarchy.tsx index 120f82f717..a0d4d9c42a 100644 --- a/src/components/structures/SpaceHierarchy.tsx +++ b/src/components/structures/SpaceHierarchy.tsx @@ -23,15 +23,18 @@ import React, { useState, KeyboardEvent, KeyboardEventHandler, + useContext, + SetStateAction, + Dispatch, } from "react"; import { Room } from "matrix-js-sdk/src/models/room"; import { RoomHierarchy } from "matrix-js-sdk/src/room-hierarchy"; import { EventType, RoomType } from "matrix-js-sdk/src/@types/event"; import { IHierarchyRelation, IHierarchyRoom } from "matrix-js-sdk/src/@types/spaces"; +import { MatrixClient } from "matrix-js-sdk/src/matrix"; import classNames from "classnames"; import { sortBy } from "lodash"; -import { MatrixClientPeg } from "../../MatrixClientPeg"; import dis from "../../dispatcher/dispatcher"; import defaultDispatcher from "../../dispatcher/dispatcher"; import { _t } from "../../languageHandler"; @@ -53,12 +56,13 @@ import { Action } from "../../dispatcher/actions"; import { Key } from "../../Keyboard"; import { IState, RovingTabIndexProvider, useRovingTabIndex } from "../../accessibility/RovingTabIndex"; import { getDisplayAliasForRoom } from "./RoomDirectory"; +import MatrixClientContext from "../../contexts/MatrixClientContext"; interface IProps { space: Room; initialText?: string; additionalButtons?: ReactNode; - showRoom(hierarchy: RoomHierarchy, roomId: string, autoJoin?: boolean): void; + showRoom(cli: MatrixClient, hierarchy: RoomHierarchy, roomId: string, autoJoin?: boolean): void; } interface ITileProps { @@ -81,7 +85,7 @@ const Tile: React.FC = ({ numChildRooms, children, }) => { - const cli = MatrixClientPeg.get(); + const cli = useContext(MatrixClientContext); const joinedRoom = cli.getRoom(room.room_id)?.getMyMembership() === "join" ? cli.getRoom(room.room_id) : null; const name = joinedRoom?.name || room.name || room.canonical_alias || room.aliases?.[0] || (room.room_type === RoomType.Space ? _t("Unnamed Space") : _t("Unnamed Room")); @@ -238,7 +242,7 @@ const Tile: React.FC = ({ handled = true; if (showChildren) { const childSection = ref.current?.nextElementSibling; - childSection?.querySelector(".mx_SpaceRoomDirectory_roomTile")?.focus(); + childSection?.querySelector(".mx_SpaceHierarchy_roomTile")?.focus(); } else { toggleShowChildren(); } @@ -253,7 +257,7 @@ const Tile: React.FC = ({ } return
  • @@ -274,12 +278,12 @@ const Tile: React.FC = ({
  • ; }; -export const showRoom = (hierarchy: RoomHierarchy, roomId: string, autoJoin = false) => { +export const showRoom = (cli: MatrixClient, hierarchy: RoomHierarchy, roomId: string, autoJoin = false) => { const room = hierarchy.roomMap.get(roomId); // Don't let the user view a room they won't be able to either peek or join: // fail earlier so they don't have to click back to the directory. - if (MatrixClientPeg.get().isGuest()) { + if (cli.isGuest()) { if (!room.world_readable && !room.guest_can_join) { dis.dispatch({ action: "require_registration" }); return; @@ -322,7 +326,7 @@ export const HierarchyLevel = ({ onViewRoomClick, onToggleClick, }: IHierarchyLevelProps) => { - const cli = MatrixClientPeg.get(); + const cli = useContext(MatrixClientContext); const space = cli.getRoom(root.room_id); const hasPermissions = space?.currentState.maySendStateEvent(EventType.SpaceChild, cli.getUserId()); @@ -462,14 +466,107 @@ const useIntersectionObserver = (callback: () => void) => { }; }; +interface IManageButtonsProps { + hierarchy: RoomHierarchy; + selected: Map>; + setSelected: Dispatch>>>; + setError: Dispatch>; +} + +const ManageButtons = ({ hierarchy, selected, setSelected, setError }: IManageButtonsProps) => { + const cli = useContext(MatrixClientContext); + + const [removing, setRemoving] = useState(false); + const [saving, setSaving] = useState(false); + + const selectedRelations = Array.from(selected.keys()).flatMap(parentId => { + return [ + ...selected.get(parentId).values(), + ].map(childId => [parentId, childId]) as [string, string][]; + }); + + const selectionAllSuggested = selectedRelations.every(([parentId, childId]) => { + return hierarchy.isSuggested(parentId, childId); + }); + + const disabled = !selectedRelations.length || removing || saving; + + let Button: React.ComponentType> = AccessibleButton; + let props = {}; + if (!selectedRelations.length) { + Button = AccessibleTooltipButton; + props = { + tooltip: _t("Select a room below first"), + yOffset: -40, + }; + } + + return <> + + + ; +}; + const SpaceHierarchy = ({ space, initialText = "", showRoom, additionalButtons, }: IProps) => { - const cli = MatrixClientPeg.get(); - const userId = cli.getUserId(); + const cli = useContext(MatrixClientContext); const [query, setQuery] = useState(initialText); const [selected, setSelected] = useState(new Map>()); // Map> @@ -502,8 +599,6 @@ const SpaceHierarchy = ({ }, [rooms, hierarchy, query]); const [error, setError] = useState(""); - const [removing, setRemoving] = useState(false); - const [saving, setSaving] = useState(false); const loaderRef = useIntersectionObserver(loadMore); @@ -511,13 +606,29 @@ const SpaceHierarchy = ({ return

    { _t("Your server does not support showing space hierarchies.") }

    ; } - const onKeyDown = (ev: KeyboardEvent, state: IState) => { - if (ev.key === Key.ARROW_DOWN && ev.currentTarget.classList.contains("mx_SpaceRoomDirectory_search")) { + const onKeyDown = (ev: KeyboardEvent, state: IState): void => { + if (ev.key === Key.ARROW_DOWN && ev.currentTarget.classList.contains("mx_SpaceHierarchy_search")) { state.refs[0]?.current?.focus(); } }; - // TODO loading state/error state + const onToggleClick = (parentId: string, childId: string): void => { + setError(""); + if (!selected.has(parentId)) { + setSelected(new Map(selected.set(parentId, new Set([childId])))); + return; + } + + const parentSet = selected.get(parentId); + if (!parentSet.has(childId)) { + setSelected(new Map(selected.set(parentId, new Set([...parentSet, childId])))); + return; + } + + parentSet.delete(childId); + setSelected(new Map(selected.set(parentId, new Set(parentSet)))); + }; + return { ({ onKeyDownHandler }) => { let content: JSX.Element; @@ -526,93 +637,11 @@ const SpaceHierarchy = ({ if (loading && !rooms.length) { content = ; } else { - let manageButtons; - if (space.getMyMembership() === "join" && space.currentState.maySendStateEvent(EventType.SpaceChild, userId)) { - const selectedRelations = Array.from(selected.keys()).flatMap(parentId => { - return [ - ...selected.get(parentId).values(), - ].map(childId => [parentId, childId]) as [string, string][]; - }); - - const selectionAllSuggested = selectedRelations.every(([parentId, childId]) => { - return hierarchy.isSuggested(parentId, childId); - }); - - const disabled = !selectedRelations.length || removing || saving; - - let Button: React.ComponentType> = AccessibleButton; - let props = {}; - if (!selectedRelations.length) { - Button = AccessibleTooltipButton; - props = { - tooltip: _t("Select a room below first"), - yOffset: -40, - }; - } - - manageButtons = <> - - - ; - } + const hasPermissions = space?.getMyMembership() === "join" && + space.currentState.maySendStateEvent(EventType.SpaceChild, cli.getUserId()); let results: JSX.Element; if (filteredRoomSet.size) { - const hasPermissions = space?.currentState.maySendStateEvent(EventType.SpaceChild, cli.getUserId()); - results = <> { - setError(""); - if (!selected.has(parentId)) { - setSelected(new Map(selected.set(parentId, new Set([childId])))); - return; - } - - const parentSet = selected.get(parentId); - if (!parentSet.has(childId)) { - setSelected(new Map(selected.set(parentId, new Set([...parentSet, childId])))); - return; - } - - parentSet.delete(childId); - setSelected(new Map(selected.set(parentId, new Set(parentSet)))); - } : undefined} + onToggleClick={hasPermissions ? onToggleClick : undefined} onViewRoomClick={(roomId, autoJoin) => { - showRoom(hierarchy, roomId, autoJoin); + showRoom(cli, hierarchy, roomId, autoJoin); }} /> ; @@ -659,13 +673,25 @@ const SpaceHierarchy = ({

    { query.trim() ? _t("Results") : _t("Rooms and spaces") }

    { additionalButtons } - { manageButtons } + { hasPermissions && ( + + ) } { error &&
    { error }
    } -
      +
        { results }
      { loader } @@ -674,7 +700,7 @@ const SpaceHierarchy = ({ return <> create a new room.": "If you can't find the room you're looking for, ask for an invite or create a new room.", - "Create room": "Create room", "Private space": "Private space", " invites you": " invites you", "To view %(spaceName)s, turn on the Spaces beta": "To view %(spaceName)s, turn on the Spaces beta",