improve lobby

This commit is contained in:
Gimle Larpes 2025-06-29 20:01:25 +02:00
parent a55065b1de
commit 64fc3066a1
3 changed files with 87 additions and 21 deletions

View file

@ -162,6 +162,7 @@ export function Lobby() {
const screenSize = useScreenSizeContext(); const screenSize = useScreenSizeContext();
const [onTop, setOnTop] = useState(true); const [onTop, setOnTop] = useState(true);
const [closedCategories, setClosedCategories] = useAtom(useClosedLobbyCategoriesAtom()); const [closedCategories, setClosedCategories] = useAtom(useClosedLobbyCategoriesAtom());
const roomToParents = useAtomValue(roomToParentsAtom);
const [sidebarItems] = useSidebarItems( const [sidebarItems] = useSidebarItems(
useOrphanSpaces(mx, allRoomsAtom, useAtomValue(roomToParentsAtom)) useOrphanSpaces(mx, allRoomsAtom, useAtomValue(roomToParentsAtom))
); );
@ -193,6 +194,36 @@ export function Lobby() {
[mx] [mx]
); );
/**
* Recursively checks if a given parentId (or all its ancestors) is in a closed category.
*
* @param spaceId - The root space ID.
* @param parentId - The parent space ID to start the check from.
* @returns True if parentId or all ancestors is in a closed category.
*/
const getInClosedCategories = useCallback(
(spaceId: string, parentId: string): boolean => {
if (closedCategories.has(makeLobbyCategoryId(spaceId, parentId))) {
return true;
}
const parentParentIds = roomToParents.get(parentId);
if (!parentParentIds || parentParentIds.size === 0) {
return false;
}
let anyOpen = false;
parentParentIds.forEach((id) => {
if (!getInClosedCategories(spaceId, id)) {
anyOpen = true;
}
});
return !anyOpen;
},
[closedCategories, roomToParents]
);
const [draggingItem, setDraggingItem] = useState<HierarchyItem>(); const [draggingItem, setDraggingItem] = useState<HierarchyItem>();
const hierarchy = useSpaceHierarchy( const hierarchy = useSpaceHierarchy(
space.roomId, space.roomId,
@ -200,9 +231,9 @@ export function Lobby() {
getRoom, getRoom,
useCallback( useCallback(
(childId) => (childId) =>
closedCategories.has(makeLobbyCategoryId(space.roomId, childId)) || getInClosedCategories(space.roomId, childId) ||
(draggingItem ? 'space' in draggingItem : false), (draggingItem ? 'space' in draggingItem : false),
[closedCategories, space.roomId, draggingItem] [draggingItem, getInClosedCategories, space.roomId]
) )
); );
@ -476,14 +507,20 @@ export function Lobby() {
const item = hierarchy[vItem.index]; const item = hierarchy[vItem.index];
if (!item) return null; if (!item) return null;
const nextSpaceId = hierarchy[vItem.index + 1]?.space.roomId; const nextSpaceId = hierarchy[vItem.index + 1]?.space.roomId;
const categoryId = makeLobbyCategoryId(space.roomId, item.space.roomId); const categoryId = makeLobbyCategoryId(space.roomId, item.space.roomId);
const inClosedCategory = getInClosedCategories(
space.roomId,
item.space.roomId
);
const paddingLeft = `calc((${item.space.depth} - 1) * ${config.space.S200})`;
return ( return (
<VirtualTile <VirtualTile
virtualItem={vItem} virtualItem={vItem}
style={{ style={{
paddingTop: vItem.index === 0 ? 0 : config.space.S500, paddingTop: vItem.index === 0 ? 0 : config.space.S500,
paddingLeft,
}} }}
ref={virtualizer.measureElement} ref={virtualizer.measureElement}
key={vItem.index} key={vItem.index}
@ -498,8 +535,7 @@ export function Lobby() {
canEditSpaceChild={canEditSpaceChild} canEditSpaceChild={canEditSpaceChild}
categoryId={categoryId} categoryId={categoryId}
closed={ closed={
closedCategories.has(categoryId) || inClosedCategory || (draggingItem ? 'space' in draggingItem : false)
(draggingItem ? 'space' in draggingItem : false)
} }
handleClose={handleCategoryClick} handleClose={handleCategoryClick}
draggingItem={draggingItem} draggingItem={draggingItem}

View file

@ -15,6 +15,9 @@ import {
MenuItem, MenuItem,
RectCords, RectCords,
config, config,
IconButton,
TooltipProvider,
Tooltip,
} from 'folds'; } from 'folds';
import FocusTrap from 'focus-trap-react'; import FocusTrap from 'focus-trap-react';
import classNames from 'classnames'; import classNames from 'classnames';
@ -350,15 +353,42 @@ function AddSpaceButton({ item }: { item: HierarchyItem }) {
</FocusTrap> </FocusTrap>
} }
> >
<Chip {item.parentId === undefined ? (
variant="SurfaceVariant" <Chip
radii="Pill" variant="SurfaceVariant"
before={<Icon src={Icons.Plus} size="50" />} radii="Pill"
onClick={handleAddSpace} before={<Icon src={Icons.Plus} size="50" />}
aria-pressed={!!cords} onClick={handleAddSpace}
> aria-pressed={!!cords}
<Text size="B300">Add Space</Text> >
</Chip> <Text size="B300">Add Space</Text>
</Chip>
) : (
<TooltipProvider
position="Bottom"
offset={4}
tooltip={
<Tooltip>
<Text>Add Space</Text>
</Tooltip>
}
>
{(triggerRef) => (
<IconButton
ref={triggerRef}
onClick={handleAddSpace}
aria-pressed={!!cords}
aria-label="Add Space"
variant="SurfaceVariant"
fill="None"
size="300"
radii="300"
>
<Icon size="50" src={Icons.SpacePlus} />
</IconButton>
)}
</TooltipProvider>
)}
</PopOut> </PopOut>
); );
} }
@ -473,7 +503,7 @@ export const SpaceItemCard = as<'div', SpaceItemCardProps>(
{canEditChild && ( {canEditChild && (
<Box shrink="No" alignItems="Inherit" gap="200"> <Box shrink="No" alignItems="Inherit" gap="200">
<AddRoomButton item={item} /> <AddRoomButton item={item} />
{item.parentId === undefined && <AddSpaceButton item={item} />} <AddSpaceButton item={item} />
</Box> </Box>
)} )}
</Box> </Box>

View file

@ -314,11 +314,11 @@ export function Space() {
); );
/** /**
* Recursively checks if a given parentId (and its ancestors) is in a closed category. * Recursively checks if a given parentId (or all its ancestors) is in a closed category.
* *
* @param spaceId - The root space ID. * @param spaceId - The root space ID.
* @param parentId - The parent space ID to start the check from. * @param parentId - The parent space ID to start the check from.
* @returns True if parentId or any ancestor is in a closed category. * @returns True if parentId or all ancestors is in a closed category.
*/ */
const getInClosedCategories = useCallback( const getInClosedCategories = useCallback(
(spaceId: string, parentId: string): boolean => { (spaceId: string, parentId: string): boolean => {
@ -331,14 +331,14 @@ export function Space() {
return false; return false;
} }
let closed = false; let anyOpen = false;
parentParentIds.forEach((id) => { parentParentIds.forEach((id) => {
if (getInClosedCategories(spaceId, id)) { if (!getInClosedCategories(spaceId, id)) {
closed = true; anyOpen = true;
} }
}); });
return closed; return !anyOpen;
}, },
[closedCategories, roomToParents] [closedCategories, roomToParents]
); );