style(settings): flatten the permissions page into Dawn sections and swap the peek checkmarks for icons

This commit is contained in:
heaven 2026-06-04 12:26:30 +03:00
parent fa17029a45
commit e06ab508f9
2 changed files with 105 additions and 135 deletions

View file

@ -4,9 +4,8 @@ import { Badge, Box, Button, Chip, config, Icon, Icons, Menu, Spinner, Text } fr
import { useTranslation } from 'react-i18next'; import { useTranslation } from 'react-i18next';
import produce from 'immer'; import produce from 'immer';
import type { StateEvents } from 'matrix-js-sdk'; import type { StateEvents } from 'matrix-js-sdk';
import { SequenceCard } from '../../../components/sequence-card';
import { SequenceCardStyle } from '../styles.css';
import { SettingTile } from '../../../components/setting-tile'; import { SettingTile } from '../../../components/setting-tile';
import { SettingsSection } from '../../settings/SettingsSection';
import { import {
applyPermissionPower, applyPermissionPower,
getPermissionPower, getPermissionPower,
@ -120,14 +119,7 @@ export function PermissionGroups({
const powerChanges = value !== power; const powerChanges = value !== power;
return ( return (
<Box direction="Column" gap="100"> <SettingsSection label={t('RoomSettings.users')}>
<Text size="L400">{t('RoomSettings.users')}</Text>
<SequenceCard
variant="SurfaceVariant"
className={SequenceCardStyle}
direction="Column"
gap="400"
>
<SettingTile <SettingTile
title={t('RoomSettings.default_power')} title={t('RoomSettings.default_power')}
description={t('RoomSettings.default_power_desc')} description={t('RoomSettings.default_power_desc')}
@ -136,6 +128,60 @@ export function PermissionGroups({
powerLevelTags={powerLevelTags} powerLevelTags={powerLevelTags}
value={value} value={value}
onChange={(v) => handleChangePermission(USER_DEFAULT_LOCATION, v, power)} onChange={(v) => handleChangePermission(USER_DEFAULT_LOCATION, v, power)}
>
{(handleOpen, opened) => (
<Chip
variant={powerChanges ? 'Success' : 'Secondary'}
outlined={powerChanges}
fill="Soft"
radii="Pill"
aria-selected={opened}
disabled={!canEdit || applyingChanges}
after={
powerChanges && <Badge size="200" variant="Success" fill="Solid" radii="Pill" />
}
before={
canEdit && (
<Icon size="50" src={opened ? Icons.ChevronTop : Icons.ChevronBottom} />
)
}
onClick={handleOpen}
>
<Text size="B300" truncate>
{tag.name}
</Text>
</Chip>
)}
</PowerSwitcher>
}
/>
</SettingsSection>
);
};
return (
<>
{renderUserGroup()}
{permissionGroups.map((group, groupIndex) => (
<SettingsSection key={groupIndex} label={group.name}>
{group.items.map((item, itemIndex) => {
const power = getPermissionPower(powerLevels, item.location);
const powerUpdate = permissionUpdate.get(item.location);
const value = powerUpdate ?? power;
const tag = getPowerLevelTag(powerLevelTags, value);
const powerChanges = value !== power;
return (
<SettingTile
key={itemIndex}
title={item.name}
description={item.description}
after={
<PowerSwitcher
powerLevelTags={powerLevelTags}
value={value}
onChange={(v) => handleChangePermission(item.location, v, power)}
> >
{(handleOpen, opened) => ( {(handleOpen, opened) => (
<Chip <Chip
@ -160,85 +206,15 @@ export function PermissionGroups({
<Text size="B300" truncate> <Text size="B300" truncate>
{tag.name} {tag.name}
</Text> </Text>
{value < maxPower && <Text size="T200">{t('RoomSettings.and_above')}</Text>}
</Chip> </Chip>
)} )}
</PowerSwitcher> </PowerSwitcher>
} }
/> />
</SequenceCard>
</Box>
);
};
return (
<>
{renderUserGroup()}
{permissionGroups.map((group, groupIndex) => (
<Box key={groupIndex} direction="Column" gap="100">
<Text size="L400">{group.name}</Text>
{group.items.map((item, itemIndex) => {
const power = getPermissionPower(powerLevels, item.location);
const powerUpdate = permissionUpdate.get(item.location);
const value = powerUpdate ?? power;
const tag = getPowerLevelTag(powerLevelTags, value);
const powerChanges = value !== power;
return (
<SequenceCard
key={itemIndex}
variant="SurfaceVariant"
className={SequenceCardStyle}
direction="Column"
gap="400"
>
<SettingTile
title={item.name}
description={item.description}
after={
<PowerSwitcher
powerLevelTags={powerLevelTags}
value={value}
onChange={(v) => handleChangePermission(item.location, v, power)}
>
{(handleOpen, opened) => (
<Chip
variant={powerChanges ? 'Success' : 'Secondary'}
outlined={powerChanges}
fill="Soft"
radii="Pill"
aria-selected={opened}
disabled={!canEdit || applyingChanges}
after={
powerChanges && (
<Badge size="200" variant="Success" fill="Solid" radii="Pill" />
)
}
before={
canEdit && (
<Icon
size="50"
src={opened ? Icons.ChevronTop : Icons.ChevronBottom}
/>
)
}
onClick={handleOpen}
>
<Text size="B300" truncate>
{tag.name}
</Text>
{value < maxPower && (
<Text size="T200">{t('RoomSettings.and_above')}</Text>
)}
</Chip>
)}
</PowerSwitcher>
}
/>
</SequenceCard>
); );
})} })}
</Box> </SettingsSection>
))} ))}
{hasChanges && ( {hasChanges && (

View file

@ -14,11 +14,12 @@ import {
toRem, toRem,
config, config,
color, color,
Icon,
Icons,
} from 'folds'; } from 'folds';
import { SequenceCard } from '../../../components/sequence-card';
import { SequenceCardStyle } from '../styles.css';
import { getPowers, usePowerLevelTags } from '../../../hooks/usePowerLevelTags'; import { getPowers, usePowerLevelTags } from '../../../hooks/usePowerLevelTags';
import { SettingTile } from '../../../components/setting-tile'; import { SettingTile } from '../../../components/setting-tile';
import { SettingsSection } from '../../settings/SettingsSection';
import { getPermissionPower, IPowerLevels } from '../../../hooks/usePowerLevels'; import { getPermissionPower, IPowerLevels } from '../../../hooks/usePowerLevels';
import { useRoom } from '../../../hooks/useRoom'; import { useRoom } from '../../../hooks/useRoom';
import { PowerColorBadge, PowerIcon } from '../../../components/power'; import { PowerColorBadge, PowerIcon } from '../../../components/power';
@ -77,15 +78,20 @@ function PeekPermissions({ powerLevels, power, permissionGroups, children }: Pee
const hasPower = requiredPower <= power; const hasPower = requiredPower <= power;
return ( return (
<Text <Box key={itemIndex} alignItems="Center" gap="200">
key={itemIndex} <Icon
size="T200" size="50"
src={hasPower ? Icons.Check : Icons.Cross}
style={{ style={{
color: hasPower ? undefined : color.Critical.Main, color: hasPower ? color.Success.Main : color.Surface.OnContainer,
opacity: hasPower ? 1 : 0.4,
flexShrink: 0,
}} }}
> />
{hasPower ? '✅' : '❌'} {item.name} <Text size="T200" style={{ opacity: hasPower ? 1 : 0.6 }}>
{item.name}
</Text> </Text>
</Box>
); );
})} })}
</div> </div>
@ -120,19 +126,12 @@ export function Powers({ powerLevels, permissionGroups, onEdit }: PowersProps) {
creatorsTag.icon && getPowerTagIconSrc(mx, useAuthentication, creatorsTag.icon); creatorsTag.icon && getPowerTagIconSrc(mx, useAuthentication, creatorsTag.icon);
return ( return (
<Box direction="Column" gap="100"> <Box direction="Column" gap="700">
{creators.size > 0 && ( {creators.size > 0 && (
<SequenceCard <SettingsSection
variant="SurfaceVariant" label={t('RoomSettings.founders')}
className={SequenceCardStyle} footnote={t('RoomSettings.founders_desc')}
direction="Column"
gap="400"
> >
<SettingTile
title={t('RoomSettings.founders')}
description={t('RoomSettings.founders_desc')}
/>
<SettingTile> <SettingTile>
<Box gap="200" wrap="Wrap"> <Box gap="200" wrap="Wrap">
<Chip <Chip
@ -148,17 +147,13 @@ export function Powers({ powerLevels, permissionGroups, onEdit }: PowersProps) {
</Chip> </Chip>
</Box> </Box>
</SettingTile> </SettingTile>
</SequenceCard> </SettingsSection>
)} )}
<SequenceCard <SettingsSection
variant="SurfaceVariant" label={t('RoomSettings.power_levels')}
className={SequenceCardStyle} footnote={t('RoomSettings.power_levels_desc')}
direction="Column"
gap="400"
> >
<SettingTile <SettingTile
title={t('RoomSettings.power_levels')}
description={t('RoomSettings.power_levels_desc')}
after={ after={
onEdit && ( onEdit && (
<Box gap="200"> <Box gap="200">
@ -175,8 +170,7 @@ export function Powers({ powerLevels, permissionGroups, onEdit }: PowersProps) {
</Box> </Box>
) )
} }
/> >
<SettingTile>
<Box gap="200" wrap="Wrap"> <Box gap="200" wrap="Wrap">
{getPowers(powerLevelTags).map((power) => { {getPowers(powerLevelTags).map((power) => {
const tag = powerLevelTags[power]; const tag = powerLevelTags[power];
@ -208,7 +202,7 @@ export function Powers({ powerLevels, permissionGroups, onEdit }: PowersProps) {
})} })}
</Box> </Box>
</SettingTile> </SettingTile>
</SequenceCard> </SettingsSection>
</Box> </Box>
); );
} }