Add Timezone sharing
Allows users to share their timezone
This commit is contained in:
parent
ac155bbf4c
commit
91e6205f49
4 changed files with 159 additions and 0 deletions
55
src/app/molecules/room-timezone/RoomTimezone.jsx
Normal file
55
src/app/molecules/room-timezone/RoomTimezone.jsx
Normal file
|
@ -0,0 +1,55 @@
|
|||
import React, { useState, useEffect, useCallback } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
import initMatrix from '../../../client/initMatrix';
|
||||
import Button from '../../atoms/button/Button';
|
||||
import Text from '../../atoms/text/Text';
|
||||
|
||||
import './RoomTimezone.scss';
|
||||
|
||||
function RoomTimezone({ roomId }) {
|
||||
const mx = initMatrix.matrixClient;
|
||||
const room = mx.getRoom(roomId);
|
||||
const userId = mx.getUserId();
|
||||
|
||||
const currentTimezone = room.currentState.getStateEvents('in.cinny.share_timezone', userId)?.event?.content?.user_timezone;
|
||||
|
||||
const [timezone, setTimezone] = useState(currentTimezone);
|
||||
|
||||
const clearTimezone = () => {
|
||||
mx.sendStateEvent(roomId, 'in.cinny.share_timezone', { }, userId);
|
||||
setTimezone(null);
|
||||
};
|
||||
|
||||
const shareTimezone = () => {
|
||||
const userTimezone = Intl.DateTimeFormat().resolvedOptions().timeZone;
|
||||
setTimezone(userTimezone);
|
||||
mx.sendStateEvent(roomId, 'in.cinny.share_timezone', { user_timezone: userTimezone }, userId);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="room-timezone__content">
|
||||
<Text className="room-timezone__message">Share your timezone</Text>
|
||||
<Text className="room-timezone__message" variant="b3">
|
||||
Sharing your timezone will allow other users in this room to see your local time.
|
||||
Keep in mind that sharing your timezone will share your approximate location.
|
||||
</Text>
|
||||
<Text className="room-timezone__message" variant="b2">
|
||||
{timezone ? `Currently shared timezone: ${timezone}` : 'You are not currently sharing a timezone'}
|
||||
</Text>
|
||||
<Button onClick={() => shareTimezone()} variant={timezone ? 'surface' : 'danger'}>
|
||||
{timezone ? 'Update Timezone' : 'Share Timezone'}
|
||||
</Button>
|
||||
|
||||
<Button onClick={() => clearTimezone()} disabled={!timezone}>
|
||||
Clear Shared Timezone
|
||||
</Button>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
RoomTimezone.propTypes = {
|
||||
roomId: PropTypes.string.isRequired,
|
||||
};
|
||||
|
||||
export default RoomTimezone;
|
84
src/app/molecules/room-timezone/RoomTimezone.scss
Normal file
84
src/app/molecules/room-timezone/RoomTimezone.scss
Normal file
|
@ -0,0 +1,84 @@
|
|||
@use '../../partials/flex';
|
||||
@use '../../partials/dir';
|
||||
@use '../../partials/text';
|
||||
|
||||
.room-timezone {
|
||||
&__message,
|
||||
& .setting-tile {
|
||||
margin: var(--sp-tight) var(--sp-normal);
|
||||
}
|
||||
& .setting-tile {
|
||||
margin-bottom: var(--sp-loose);
|
||||
}
|
||||
|
||||
&__alias-item {
|
||||
padding: var(--sp-extra-tight) var(--sp-normal);
|
||||
@extend .cp-fx__row--s-c;
|
||||
&.checkbox {
|
||||
@include dir.side(margin, 0 , var(--sp-tight));
|
||||
}
|
||||
& .text {
|
||||
@extend .cp-fx__item-one;
|
||||
@extend .cp-txt__ellipsis;
|
||||
color: var(--tc-surface-high);
|
||||
span {
|
||||
margin: 0 var(--sp-extra-tight);
|
||||
padding: 0 var(--sp-ultra-tight);
|
||||
color: var(--bg-surface);
|
||||
background-color: var(--tc-surface-low);
|
||||
border-radius: 4px;
|
||||
}
|
||||
}
|
||||
}
|
||||
&__item-btns {
|
||||
@include dir.side(margin, 48px, 0);
|
||||
& button {
|
||||
padding: var(--sp-ultra-tight) var(--sp-tight);
|
||||
margin-bottom: var(--sp-tight);
|
||||
@include dir.side(margin, 0, var(--sp-tight));
|
||||
}
|
||||
}
|
||||
|
||||
&__content {
|
||||
margin-bottom: var(--sp-normal);
|
||||
|
||||
& .checkbox {
|
||||
@include dir.side(margin, 0, var(--sp-tight));
|
||||
min-width: 20px;
|
||||
}
|
||||
& > button {
|
||||
margin: 0 var(--sp-normal);
|
||||
}
|
||||
}
|
||||
|
||||
&__form {
|
||||
padding: var(--sp-normal);
|
||||
padding-top: 0;
|
||||
display: flex;
|
||||
&-label {
|
||||
padding: var(--sp-normal) var(--sp-normal) var(--sp-ultra-tight);
|
||||
}
|
||||
}
|
||||
|
||||
&__input-wrapper {
|
||||
display: flex;
|
||||
@extend .cp-fx__item-one;
|
||||
@include dir.side(margin, 0, var(--sp-tight));
|
||||
|
||||
& .input-container {
|
||||
@extend .cp-fx__item-one;
|
||||
}
|
||||
}
|
||||
|
||||
&__input-status {
|
||||
padding: 0 var(--sp-normal);
|
||||
}
|
||||
&__valid {
|
||||
color: var(--tc-positive-high);
|
||||
padding-bottom: var(--sp-normal);
|
||||
}
|
||||
&__invalid {
|
||||
color: var(--tc-danger-high);
|
||||
padding-bottom: var(--sp-normal);
|
||||
}
|
||||
}
|
|
@ -39,6 +39,7 @@ import ChevronTopIC from '../../../../public/res/ic/outlined/chevron-top.svg';
|
|||
|
||||
import { useForceUpdate } from '../../hooks/useForceUpdate';
|
||||
import { confirmDialog } from '../../molecules/confirm-dialog/ConfirmDialog';
|
||||
import RoomTimezone from '../../molecules/room-timezone/RoomTimezone';
|
||||
|
||||
const tabText = {
|
||||
GENERAL: 'General',
|
||||
|
@ -120,6 +121,10 @@ function GeneralSettings({ roomId }) {
|
|||
<MenuHeader>Room addresses</MenuHeader>
|
||||
<RoomAliases roomId={roomId} />
|
||||
</div>
|
||||
<div className="room-settings__card">
|
||||
<MenuHeader>Timezones</MenuHeader>
|
||||
<RoomTimezone roomId={roomId} />
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -36,6 +36,7 @@ function RoomViewHeader({ roomId }) {
|
|||
let avatarSrc = mx.getRoom(roomId).getAvatarUrl(mx.baseUrl, 36, 36, 'crop');
|
||||
avatarSrc = isDM ? mx.getRoom(roomId).getAvatarFallbackMember()?.getAvatarUrl(mx.baseUrl, 36, 36, 'crop') : avatarSrc;
|
||||
const roomName = mx.getRoom(roomId).name;
|
||||
let partnerLocalTime = null;
|
||||
|
||||
const roomHeaderBtnRef = useRef(null);
|
||||
useEffect(() => {
|
||||
|
@ -72,6 +73,19 @@ function RoomViewHeader({ roomId }) {
|
|||
);
|
||||
};
|
||||
|
||||
if (isDM) {
|
||||
const room = mx.getRoom(roomId);
|
||||
const partner = room.getAvatarFallbackMember();
|
||||
const timezone = room.currentState.getStateEvents('in.cinny.share_timezone', partner.userId)?.event?.content?.user_timezone;
|
||||
const date = new Date();
|
||||
|
||||
try {
|
||||
partnerLocalTime = date.toLocaleTimeString([], { timeZone: timezone, hour: '2-digit', minute: '2-digit' });
|
||||
} catch {
|
||||
partnerLocalTime = null;
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<Header>
|
||||
<IconButton
|
||||
|
@ -93,6 +107,7 @@ function RoomViewHeader({ roomId }) {
|
|||
</TitleWrapper>
|
||||
<RawIcon src={ChevronBottomIC} />
|
||||
</button>
|
||||
<Text>{partnerLocalTime}</Text>
|
||||
<IconButton onClick={() => toggleRoomSettings(tabText.SEARCH)} tooltip="Search" src={SearchIC} />
|
||||
<IconButton className="room-header__drawer-btn" onClick={togglePeopleDrawer} tooltip="People" src={UserIC} />
|
||||
<IconButton className="room-header__members-btn" onClick={() => toggleRoomSettings(tabText.MEMBERS)} tooltip="Members" src={UserIC} />
|
||||
|
|
Loading…
Reference in a new issue