Merge pull request #5 from Tymek-V/feat/channel-type-selector

Channel type selector
This commit is contained in:
haz
2026-02-15 02:03:30 +01:00
committed by GitHub
10 changed files with 140 additions and 39 deletions
+39 -24
View File
@@ -1,5 +1,5 @@
import React, { FormEventHandler, useCallback, useEffect, useState } from 'react';
import { MatrixError, Room } from 'matrix-js-sdk';
import { MatrixError, Room, JoinRule } from 'matrix-js-sdk';
import {
Box,
Button,
@@ -37,22 +37,40 @@ import {
CreateRoomKindSelector,
RoomVersionSelector,
useAdditionalCreators,
CreateRoomVoice,
} from '../../components/create-room';
import { RoomType, StateEvent } from '../../../types/matrix/room';
import { IPowerLevels } from '../../hooks/usePowerLevels';
import { CreateRoomVoiceSelector } from '../../components/create-room/CreateRoomVoiceSelector';
import { getRoomIconSrc } from '../../utils/room';
const getCreateRoomKindToIcon = (kind: CreateRoomKind) => {
if (kind === CreateRoomKind.Private) return Icons.HashLock;
if (kind === CreateRoomKind.Restricted) return Icons.Hash;
return Icons.HashGlobe;
const getCreateRoomKindToIcon = (kind: CreateRoomKind, voice?: CreateRoomVoice) => {
const isVoiceRoom = voice === CreateRoomVoice.VoiceRoom;
let joinRule: JoinRule = JoinRule.Public;
if (kind === CreateRoomKind.Restricted) joinRule = JoinRule.Restricted;
if (kind === CreateRoomKind.Private) joinRule = JoinRule.Knock;
return getRoomIconSrc(Icons, isVoiceRoom ? RoomType.Call : undefined, joinRule);
};
const getCreateRoomVoiceToIcon = (kind: CreateRoomVoice) => {
if (kind === CreateRoomVoice.VoiceRoom) return Icons.VolumeHigh;
return Icons.Hash;
};
type CreateRoomFormProps = {
defaultKind?: CreateRoomKind;
defaultVoice?: CreateRoomVoice;
space?: Room;
onCreate?: (roomId: string) => void;
};
export function CreateRoomForm({ defaultKind, space, onCreate }: CreateRoomFormProps) {
export function CreateRoomForm({
defaultKind,
defaultVoice,
space,
onCreate,
}: CreateRoomFormProps) {
const mx = useMatrixClient();
const alive = useAlive();
@@ -66,6 +84,7 @@ export function CreateRoomForm({ defaultKind, space, onCreate }: CreateRoomFormP
const allowRestricted = space && restrictedSupported(selectedRoomVersion);
const [voice, setVoice] = useState(defaultVoice ?? CreateRoomVoice.TextRoom);
const [kind, setKind] = useState(
defaultKind ?? allowRestricted ? CreateRoomKind.Restricted : CreateRoomKind.Private
);
@@ -74,7 +93,6 @@ export function CreateRoomForm({ defaultKind, space, onCreate }: CreateRoomFormP
useAdditionalCreators();
const [federation, setFederation] = useState(true);
const [encryption, setEncryption] = useState(false);
const [callRoom, setCallRoom] = useState(false);
const [knock, setKnock] = useState(false);
const [advance, setAdvance] = useState(false);
@@ -123,7 +141,7 @@ export function CreateRoomForm({ defaultKind, space, onCreate }: CreateRoomFormP
const powerOverrides: IPowerLevels = {
events: {},
};
if (callRoom) {
if (voice === CreateRoomVoice.VoiceRoom) {
roomType = RoomType.Call;
powerOverrides.events![StateEvent.GroupCallMemberPrefix] = 0;
}
@@ -150,6 +168,17 @@ export function CreateRoomForm({ defaultKind, space, onCreate }: CreateRoomFormP
return (
<Box as="form" onSubmit={handleSubmit} grow="Yes" direction="Column" gap="500">
{!space && (
<Box direction="Column" gap="100">
<Text size="L400">Type</Text>
<CreateRoomVoiceSelector
value={voice}
onSelect={setVoice}
disabled={disabled}
getIcon={getCreateRoomVoiceToIcon}
/>
</Box>
)}
<Box direction="Column" gap="100">
<Text size="L400">Access</Text>
<CreateRoomKindSelector
@@ -157,14 +186,14 @@ export function CreateRoomForm({ defaultKind, space, onCreate }: CreateRoomFormP
onSelect={setKind}
canRestrict={allowRestricted}
disabled={disabled}
getIcon={getCreateRoomKindToIcon}
getIcon={(roomKind) => getCreateRoomKindToIcon(roomKind, voice)}
/>
</Box>
<Box shrink="No" direction="Column" gap="100">
<Text size="L400">Name</Text>
<Input
required
before={<Icon size="100" src={getCreateRoomKindToIcon(kind)} />}
before={<Icon size="100" src={getCreateRoomKindToIcon(kind, voice)} />}
name="nameInput"
autoFocus
size="500"
@@ -184,20 +213,6 @@ export function CreateRoomForm({ defaultKind, space, onCreate }: CreateRoomFormP
disabled={disabled}
/>
</Box>
<SequenceCard
style={{ padding: config.space.S300 }}
variant="SurfaceVariant"
direction="Column"
gap="500"
>
<SettingTile
title="Call Room"
description="Enable this to create a room optimized for voice calls."
after={
<Switch variant="Primary" value={callRoom} onChange={setCallRoom} disabled={disabled} />
}
/>
</SequenceCard>
{kind === CreateRoomKind.Public && <CreateRoomAliasInput disabled={disabled} />}
@@ -23,12 +23,13 @@ import {
} from '../../state/hooks/createRoomModal';
import { CreateRoomModalState } from '../../state/createRoomModal';
import { stopPropagation } from '../../utils/keyboard';
import { CreateRoomVoice } from '../../components/create-room/types';
type CreateRoomModalProps = {
state: CreateRoomModalState;
};
function CreateRoomModal({ state }: CreateRoomModalProps) {
const { spaceId } = state;
const { spaceId, voice } = state;
const closeDialog = useCloseCreateRoomModal();
const allJoinedRooms = useAllJoinedRoomsSet();
@@ -57,7 +58,7 @@ function CreateRoomModal({ state }: CreateRoomModalProps) {
}}
>
<Box grow="Yes">
<Text size="H4">New Room</Text>
<Text size="H4">New {voice === CreateRoomVoice.VoiceRoom && 'Voice '}Room</Text>
</Box>
<Box shrink="No">
<IconButton size="300" radii="300" onClick={closeDialog}>
@@ -74,7 +75,7 @@ function CreateRoomModal({ state }: CreateRoomModalProps) {
direction="Column"
gap="500"
>
<CreateRoomForm space={space} onCreate={closeDialog} />
<CreateRoomForm space={space} onCreate={closeDialog} defaultVoice={voice} />
</Box>
</Scroll>
</Box>
+13 -3
View File
@@ -36,6 +36,7 @@ import { useMediaAuthentication } from '../../hooks/useMediaAuthentication';
import { useOpenCreateRoomModal } from '../../state/hooks/createRoomModal';
import { useOpenCreateSpaceModal } from '../../state/hooks/createSpaceModal';
import { AddExistingModal } from '../add-existing';
import { CreateRoomVoice } from '../../components/create-room/types';
function SpaceProfileLoading() {
return (
@@ -249,8 +250,8 @@ function AddRoomButton({ item }: { item: HierarchyItem }) {
setCords(evt.currentTarget.getBoundingClientRect());
};
const handleCreateRoom = () => {
openCreateRoomModal(item.roomId);
const handleCreateRoom = (voice?: CreateRoomVoice) => {
openCreateRoomModal(item.roomId, voice);
setCords(undefined);
};
@@ -281,10 +282,19 @@ function AddRoomButton({ item }: { item: HierarchyItem }) {
radii="300"
variant="Primary"
fill="None"
onClick={handleCreateRoom}
onClick={() => handleCreateRoom(CreateRoomVoice.TextRoom)}
>
<Text size="T300">New Room</Text>
</MenuItem>
<MenuItem
size="300"
radii="300"
variant="Primary"
fill="None"
onClick={() => handleCreateRoom(CreateRoomVoice.VoiceRoom)}
>
<Text size="T300">New Voice Room</Text>
</MenuItem>
<MenuItem size="300" radii="300" fill="None" onClick={handleAddExisting}>
<Text size="T300">Existing Room</Text>
</MenuItem>