remove most bits

This commit is contained in:
Bruno Windels 2020-12-07 19:06:26 +01:00
parent 685950ba43
commit 1f43db2a5b
113 changed files with 0 additions and 21001 deletions

View File

@ -1,4 +0,0 @@
module.exports = {
preset: 'ts-jest',
testEnvironment: 'node',
};

View File

@ -1,16 +0,0 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<meta
name="description"
content="A client-side matrix link redirection service"
/>
<title>Matrix.to</title>
</head>
<body>
<noscript>You need to enable JavaScript to run this app.</noscript>
<div id="root"></div>
</body>
</html>

View File

@ -1,42 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import './color-scheme';
#root {
background-color: $app-background;
background-image: url('./imgs/background.svg');
background-repeat: no-repeat;
background-size: cover;
}
@mixin spacer {
width: 100%;
flex-grow: 0;
flex-shrink: 0;
}
.topSpacer {
@include spacer;
height: 10vh;
}
.bottomSpacer {
@include spacer;
height: 10vh;
}

View File

@ -1,76 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useState, useEffect } from 'react';
import SingleColumn from './layouts/SingleColumn';
import CreateLinkTile from './components/CreateLinkTile';
import MatrixTile from './components/MatrixTile';
import Tile from './components/Tile';
import LinkRouter from './pages/LinkRouter';
import './App.scss';
import GlobalContext from './contexts/GlobalContext';
/* eslint-disable no-restricted-globals */
const App: React.FC = () => {
let page = (
<>
<CreateLinkTile />
</>
);
const [hash, setHash] = useState(location.hash);
console.log(`Link for ${hash}`);
useEffect(() => {
// Some hacky uri decoding
if (location.href.split('/').length > 4) {
location.href = decodeURIComponent(location.href);
}
window.onhashchange = () => setHash(location.hash);
}, []);
if (hash) {
if (hash.startsWith('#/')) {
page = <LinkRouter link={hash.slice(2)} />;
} else {
page = (
<Tile>
Links should be in the format {location.host}/#/{'<'}
matrix-resource-identifier{'>'}
</Tile>
);
}
}
return (
<GlobalContext>
<SingleColumn>
<div className="topSpacer" />
{page}
<MatrixTile isLink={!!location.hash} />
<div className="bottomSpacer" />
</SingleColumn>
</GlobalContext>
);
};
export default App;

View File

@ -1,25 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
$app-background: #f4f4f4;
$background: #ffffff;
$foreground: #000000;
$font: #333333;
$grey: #666666;
$accent: #0098d4;
$error: #d6001c;
$link: #0098d4;
$borders: #f4f4f4;

View File

@ -1,20 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@mixin error {
color: $error;
border-color: $error;
}

View File

@ -1,11 +0,0 @@
@mixin unreal-focus {
outline-width: 2px;
outline-style: solid;
outline-color: Highlight;
/* WebKit gets its native focus styles. */
@media (-webkit-min-device-pixel-ratio: 0) {
outline-color: -webkit-focus-ring-color;
outline-style: auto;
}
}

View File

@ -1,106 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import {
LinkedClient,
Maturity,
ClientKind,
ClientId,
Platform,
AppleStoreLink,
PlayStoreLink,
FDroidLink,
} from './types';
import { LinkKind } from '../parser/types';
import logo from '../imgs/element.svg';
export const Element: LinkedClient = {
kind: ClientKind.LINKED_CLIENT,
name: 'Element',
author: 'Element',
logo: logo,
homepage: 'https://element.io',
maturity: Maturity.STABLE,
description: 'Fully-featured Matrix client',
platforms: [Platform.Desktop, Platform.Android, Platform.iOS],
experimental: false,
clientId: ClientId.Element,
toUrl: (link) => {
const params = link.arguments.originalParams.toString();
const prefixedParams = params ? `?${params}` : '';
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
return new URL(
`https://app.element.io/#/room/${link.identifier}${prefixedParams}`
);
case LinkKind.UserId:
return new URL(
`https://app.element.io/#/user/${link.identifier}${prefixedParams}`
);
case LinkKind.Permalink:
return new URL(
`https://app.element.io/#/room/${link.identifier}${prefixedParams}`
);
case LinkKind.GroupId:
return new URL(
`https://app.element.io/#/group/${link.identifier}${prefixedParams}`
);
}
},
linkSupport: () => true,
installLinks: [
new AppleStoreLink('vector', 'id1083446067'),
new PlayStoreLink('im.vector.app'),
new FDroidLink('im.vector.app'),
],
};
export const ElementDevelop: LinkedClient = {
kind: ClientKind.LINKED_CLIENT,
name: 'Element Develop',
author: 'Element',
logo: logo,
homepage: 'https://element.io',
maturity: Maturity.STABLE,
description: 'Fully-featured Matrix client for the Web',
platforms: [Platform.Desktop],
experimental: true,
clientId: ClientId.ElementDevelop,
toUrl: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
return new URL(
`https://develop.element.io/#/room/${link.identifier}`
);
case LinkKind.UserId:
return new URL(
`https://develop.element.io/#/user/${link.identifier}`
);
case LinkKind.Permalink:
return new URL(
`https://develop.element.io/#/room/${link.identifier}`
);
case LinkKind.GroupId:
return new URL(
`https://develop.element.io/#/group/${link.identifier}`
);
}
},
linkSupport: () => true,
installLinks: [],
};

View File

@ -1,75 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { TextClient, Maturity, ClientKind, ClientId, Platform } from './types';
import { LinkKind } from '../parser/types';
import logo from '../imgs/fractal.png';
const Fractal: TextClient = {
kind: ClientKind.TEXT_CLIENT,
name: 'Fractal',
logo: logo,
author: 'Daniel Garcia Moreno',
homepage: 'https://github.com/poljar/weechat-matrix',
maturity: Maturity.BETA,
experimental: false,
platforms: [Platform.Desktop],
clientId: ClientId.Fractal,
toInviteString: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
case LinkKind.UserId:
return (
<span>
Click the '+' button in the top right and paste the
identifier
</span>
);
default:
return <span>Fractal doesn't support this kind of link</span>;
}
},
copyString: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
case LinkKind.UserId:
return `${link.identifier}`;
default:
return '';
}
},
linkSupport: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
case LinkKind.UserId:
return true;
default:
return false;
}
},
description: 'Fractal is a Matrix Client written in Rust',
installLinks: [],
};
export default Fractal;

View File

@ -1,92 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { TextClient, Maturity, ClientKind, ClientId, Platform } from './types';
import { LinkKind } from '../parser/types';
import logo from '../imgs/nheko.svg';
const Nheko: TextClient = {
kind: ClientKind.TEXT_CLIENT,
name: 'Nheko',
logo: logo,
author: 'mujx, red_sky, deepbluev7, Konstantinos Sideris',
homepage: 'https://github.com/Nheko-Reborn/nheko',
maturity: Maturity.BETA,
experimental: false,
platforms: [Platform.Desktop],
clientId: ClientId.Nheko,
toInviteString: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
return (
<span>
Type{' '}
<code>
/join{' '}
<b className="matrixIdentifier">
{link.identifier}
</b>
</code>
</span>
);
case LinkKind.UserId:
return (
<span>
Type{' '}
<code>
/invite{' '}
<b className="matrixIdentifier">
{link.identifier}
</b>
</code>
</span>
);
default:
return <span>Nheko doesn't support this kind of link</span>;
}
},
copyString: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
return `/join ${link.identifier}`;
case LinkKind.UserId:
return `/invite ${link.identifier}`;
default:
return '';
}
},
linkSupport: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
case LinkKind.UserId:
return true;
default:
return false;
}
},
description:
'A native desktop app for Matrix that feels more like a mainstream chat app.',
installLinks: [],
};
export default Nheko;

View File

@ -1,92 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { TextClient, Maturity, ClientKind, ClientId, Platform } from './types';
import { LinkKind } from '../parser/types';
import logo from '../imgs/weechat.svg';
const Weechat: TextClient = {
kind: ClientKind.TEXT_CLIENT,
name: 'Weechat',
logo: logo,
author: 'Poljar',
homepage: 'https://github.com/poljar/weechat-matrix',
maturity: Maturity.LATE_BETA,
experimental: false,
platforms: [Platform.Desktop],
clientId: ClientId.WeeChat,
toInviteString: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
return (
<span>
Type{' '}
<code>
/join{' '}
<b className="matrixIdentifier">
{link.identifier}
</b>
</code>
</span>
);
case LinkKind.UserId:
return (
<span>
Type{' '}
<code>
/invite{' '}
<b className="matrixIdentifier">
{link.identifier}
</b>
</code>
</span>
);
default:
return <span>Weechat doesn't support this kind of link</span>;
}
},
copyString: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
return `/join ${link.identifier}`;
case LinkKind.UserId:
return `/invite ${link.identifier}`;
default:
return '';
}
},
linkSupport: (link) => {
switch (link.kind) {
case LinkKind.Alias:
case LinkKind.RoomId:
case LinkKind.UserId:
return true;
default:
return false;
}
},
description: 'Command-line Matrix interface using Weechat',
installLinks: [],
};
export default Weechat;

View File

@ -1,45 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { Client } from './types';
import { Element, ElementDevelop } from './Element';
import Weechat from './Weechat';
import Nheko from './Nheko';
import Fractal from './Fractal';
/*
* All the supported clients of matrix.to
*/
const clients: Client[] = [Element, Weechat, Nheko, Fractal, ElementDevelop];
/*
* A map from sharer string to client.
* Configured by hand so we can change the mappings
* easily later.
*/
export const clientMap: { [key: string]: Client } = {
[Element.clientId]: Element,
[Weechat.clientId]: Weechat,
[ElementDevelop.clientId]: ElementDevelop,
[Nheko.clientId]: Nheko,
[Fractal.clientId]: Fractal,
};
/*
* All the supported clients of matrix.to
*/
export default clients;

View File

@ -1,168 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { SafeLink } from '../parser/types';
/*
* A collection of descriptive tags that can be added to
* a clients description.
*/
export enum Platform {
iOS = 'iOS',
Android = 'ANDROID',
Desktop = 'DESKTOP',
}
/*
* A collection of states used for describing a clients maturity.
*/
export enum Maturity {
ALPHA = 'ALPHA',
LATE_ALPHA = 'LATE ALPHA',
BETA = 'BETA',
LATE_BETA = 'LATE_BETA',
STABLE = 'STABLE',
}
/*
* Used for constructing the discriminated union of all client types.
*/
export enum ClientKind {
LINKED_CLIENT = 'LINKED_CLIENT',
TEXT_CLIENT = 'TEXT_CLIENT',
}
export enum ClientId {
Element = 'element.io',
ElementDevelop = 'develop.element.io',
WeeChat = 'weechat',
Nheko = 'nheko',
Fractal = 'fractal',
}
/**
* Define a native distribution channel for a client.
* E.g App store for apple, PlayStore or F-Droid for Android
*/
export interface InstallLink {
createInstallURL(deepLink: SafeLink) : string;
// in AppleStoreLink, we can set the cookie here for deeplinking
// onInstallChosen(deepLink: SafeLink);
platform: Platform;
channelId: string;
description: string;
}
export class AppleStoreLink implements InstallLink {
constructor(private org: string, private appId: string) {}
createInstallURL(deepLink: SafeLink) : string {
return `https://apps.apple.com/app/${encodeURIComponent(this.org)}/${encodeURIComponent(this.appId)}`;
}
get platform() : Platform {
return Platform.iOS;
}
get channelId(): string {
return "apple-app-store";
}
get description() {
return "Download on the App Store";
}
}
export class PlayStoreLink implements InstallLink {
constructor(private appId: string) {}
createInstallURL(deepLink: SafeLink) : string {
return `https://play.google.com/store/apps/details?id=${encodeURIComponent(this.appId)}&referrer=${encodeURIComponent(deepLink.originalLink)}`;
}
get platform() : Platform {
return Platform.Android;
}
get channelId(): string {
return "play-store";
}
get description() {
return "Get it on Google Play";
}
}
export class FDroidLink implements InstallLink {
constructor(private appId: string) {}
createInstallURL(deepLink: SafeLink) : string {
return `https://f-droid.org/packages/${encodeURIComponent(this.appId)}`;
}
get platform() : Platform {
return Platform.Android;
}
get channelId(): string {
return "fdroid";
}
get description() {
return "Get it on F-Droid";
}
}
/*
* The descriptive details of a client
*/
export interface ClientDescription {
name: string;
author: string;
homepage: string;
logo: string;
description: string;
platforms: Platform[];
maturity: Maturity;
clientId: ClientId;
experimental: boolean;
linkSupport: (link: SafeLink) => boolean;
installLinks: InstallLink[];
}
/*
* A client which can be opened using a link with the matrix resource.
*/
export interface LinkedClient extends ClientDescription {
kind: ClientKind.LINKED_CLIENT;
toUrl(parsedLink: SafeLink): URL;
}
/*
* A client which provides isntructions for how to access the descired
* resource.
*/
export interface TextClient extends ClientDescription {
kind: ClientKind.TEXT_CLIENT;
toInviteString(parsedLink: SafeLink): JSX.Element;
copyString(parsedLink: SafeLink): string;
}
/*
* A description for a client as well as a method for converting matrix.to
* links to the client's specific representation.
*/
export type Client = LinkedClient | TextClient;

View File

@ -1,29 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.avatar {
border-radius: 100%;
border: 1px solid $borders;
height: 60px;
width: 60px;
}
.avatarNoCrop {
border-radius: 0;
border: 0;
}

View File

@ -1,44 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// disable camelcase check because our object keys come
// from the matrix spec
/* eslint-disable @typescript-eslint/camelcase */
import React from 'react';
import { UserAvatar } from './Avatar';
export default {
title: 'Avatar',
parameters: {
design: {
type: 'figma',
url:
'https://www.figma.com/file/WSXjCGc1k6FVI093qhlzOP/04-Recieving-share-link?node-id=143%3A5853',
},
},
};
export const Default: React.FC<{}> = () => (
<UserAvatar
user={{
avatar_url: 'mxc://matrix.org/EqMZYbAYhREvHXvYFyfxOlkf',
displayname: 'Jorik Schellekens',
}}
userId="@jorik:matrix.org"
/>
);

View File

@ -1,121 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useEffect, useState } from 'react';
import classNames from 'classnames';
import { Group, Room, User } from '../matrix-cypher';
import useHSs from '../utils/getHS';
import { getThumbnailURI } from '../utils/cypher-wrapper';
import logo from '../imgs/chat-icon.svg';
import './Avatar.scss';
const AVATAR_SIZE = 96;
interface IProps {
className?: string;
avatarUrl: string;
label: string;
}
const Avatar: React.FC<IProps> = ({ className, avatarUrl, label }: IProps) => {
const [src, setSrc] = useState(avatarUrl);
useEffect(() => {
setSrc(avatarUrl ? avatarUrl : logo);
}, [avatarUrl]);
const _className = classNames('avatar', className, {
avatarNoCrop: src === logo,
});
return (
<img
src={src}
onError={(): void => setSrc(logo)}
alt={label}
className={_className}
/>
);
};
interface IPropsUserAvatar {
user: User;
userId: string;
}
export const UserAvatar: React.FC<IPropsUserAvatar> = ({
user,
userId,
}: IPropsUserAvatar) => {
const [hs] = useHSs({ identifier: userId });
return (
<Avatar
avatarUrl={getThumbnailURI(
hs,
AVATAR_SIZE,
AVATAR_SIZE,
user.avatar_url
)}
label={user.displayname ? user.displayname : userId}
/>
);
};
interface IPropsRoomAvatar {
room: Room;
}
export const RoomAvatar: React.FC<IPropsRoomAvatar> = ({
room,
}: IPropsRoomAvatar) => {
const [hs] = useHSs({ identifier: room.room_id });
return (
<Avatar
avatarUrl={getThumbnailURI(
hs,
AVATAR_SIZE,
AVATAR_SIZE,
room.avatar_url
)}
label={room.name || room.room_id}
/>
);
};
interface IPropsGroupAvatar {
group: Group;
groupId: string;
}
export const GroupAvatar: React.FC<IPropsGroupAvatar> = ({
group,
groupId,
}: IPropsGroupAvatar) => {
const [hs] = useHSs({ identifier: groupId });
return (
<Avatar
avatarUrl={getThumbnailURI(
hs,
AVATAR_SIZE,
AVATAR_SIZE,
group.avatar_url
)}
label={group.name}
/>
);
};
export default Avatar;

View File

@ -1,65 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.button {
width: 100%;
height: 48px;
border-radius: 24px;
border: 0;
background-color: $accent;
color: $background;
font-size: 15px;
font-weight: 500;
display: inline-flex;
justify-content: center;
align-items: center;
&:hover {
cursor: pointer;
}
position: relative;
.buttonIcon {
position: absolute;
height: 24px;
width: 24px;
left: 18px;
top: 12px;
}
}
.buttonSecondary {
background-color: $background;
color: $foreground;
border: 1px solid $foreground;
}
.errorButton:hover {
cursor: not-allowed;
}
.buttonHighlight {
background-color: $accent;
}

View File

@ -1,33 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { action } from '@storybook/addon-actions';
import { text } from '@storybook/addon-knobs';
import Button from './Button';
export default { title: 'Button' };
export const WithText: React.FC = () => (
<Button onClick={action('clicked')}>
{text('label', 'Hello Story Book')}
</Button>
);
export const Secondary: React.FC = () => (
<Button secondary>Secondary button</Button>
);

View File

@ -1,89 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import classnames from 'classnames';
import './Button.scss';
interface IProps extends React.ButtonHTMLAttributes<Element> {
// Briefly display these instead of the children onClick
flashChildren?: React.ReactNode;
secondary?: boolean;
icon?: string;
flashIcon?: string;
}
/**
* Like a normal button except it will flash content when clicked.
*/
const Button: React.FC<
IProps & React.RefAttributes<HTMLButtonElement>
> = React.forwardRef(
(
{
onClick,
children,
flashChildren,
className,
secondary,
icon,
flashIcon,
...props
}: IProps,
ref: React.Ref<HTMLButtonElement>
) => {
const [wasClicked, setWasClicked] = React.useState(false);
const wrappedOnClick: React.MouseEventHandler = (e) => {
if (onClick) {
onClick(e);
}
setWasClicked(true);
window.setTimeout(() => {
setWasClicked(false);
}, 1000);
};
const content = wasClicked && flashChildren ? flashChildren : children;
const classNames = classnames('button', className, {
buttonHighlight: wasClicked,
buttonSecondary: secondary,
});
const iconSrc = wasClicked && flashIcon ? flashIcon : icon;
const buttonIcon = icon ? (
<img className="buttonIcon" src={iconSrc} alt="" />
) : null;
return (
<button
className={classNames}
onClick={wrappedOnClick}
ref={ref}
{...props}
>
{buttonIcon}
{content}
</button>
);
}
);
export default Button;

View File

@ -1,22 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
.clientList {
display: grid;
row-gap: 20px;
list-style-type: none;
padding-inline-start: 0;
}

View File

@ -1,98 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useContext } from 'react';
import { UAContext } from '@quentin-sommer/react-useragent';
import { SafeLink } from '../parser/types';
import { ActionType, ClientContext } from '../contexts/ClientContext';
import Clients from '../clients';
import { Client, Platform } from '../clients/types';
import ClientTile from './ClientTile';
import './ClientList.scss';
interface IProps {
link: SafeLink;
rememberSelection: boolean;
}
const ClientList: React.FC<IProps> = ({ link, rememberSelection }: IProps) => {
const [
{ showOnlyDeviceClients, showExperimentalClients },
clientDispatcher,
] = useContext(ClientContext);
const { uaResults } = useContext(UAContext);
/*
* Function to decide whether a client is shown
*/
const showClient = (client: Client): boolean => {
let showClient = false;
if (!showOnlyDeviceClients || uaResults === {}) {
showClient = true;
}
for (const platform of client.platforms) {
switch (platform) {
case Platform.Desktop:
showClient = showClient || !(uaResults as any).mobile;
break;
case Platform.iOS:
showClient = showClient || (uaResults as any).ios;
break;
case Platform.Android:
showClient = showClient || (uaResults as any).android;
break;
}
}
if (!showExperimentalClients && client.experimental) {
showClient = false;
}
if (!client.linkSupport(link)) {
showClient = false;
}
return showClient;
};
const clientLi = (client: Client): JSX.Element => (
<li
key={client.clientId}
onClick={(): void =>
rememberSelection
? clientDispatcher({
action: ActionType.SetClient,
clientId: client.clientId,
})
: undefined
}
>
<ClientTile client={client} link={link} />
</li>
);
return (
<ul className="clientList">
{Clients.filter(showClient).map(clientLi)}
</ul>
);
};
export default ClientList;

View File

@ -1,27 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
.advanced {
display: grid;
row-gap: 20px;
.advancedOptions {
display: flex;
flex-direction: column;
align-items: flex-start;
}
}

View File

@ -1,88 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useContext, useState } from 'react';
import './ClientSelection.scss';
import { ActionType, ClientContext } from '../contexts/ClientContext';
import ClientList from './ClientList';
import { SafeLink } from '../parser/types';
import Button from './Button';
import StyledCheckbox from './StyledCheckbox';
interface IProps {
link: SafeLink;
}
const ClientSelection: React.FC<IProps> = ({ link }: IProps) => {
const [clientState, clientStateDispatch] = useContext(ClientContext);
const [rememberSelection, setRememberSelection] = useState(false);
const options = (
<div className="advancedOptions">
<StyledCheckbox
onChange={(): void => {
setRememberSelection(!rememberSelection);
}}
checked={rememberSelection}
>
Remember for future invites in this browser
</StyledCheckbox>
<StyledCheckbox
onChange={(): void => {
clientStateDispatch({
action: ActionType.ToggleShowOnlyDeviceClients,
});
}}
checked={clientState.showOnlyDeviceClients}
>
Show only clients suggested for this device
</StyledCheckbox>
<StyledCheckbox
onChange={(): void => {
clientStateDispatch({
action: ActionType.ToggleShowExperimentalClients,
});
}}
checked={clientState.showExperimentalClients}
>
Show experimental clients
</StyledCheckbox>
</div>
);
const clearSelection =
clientState.clientId !== null ? (
<Button
onClick={(): void =>
clientStateDispatch({
action: ActionType.ClearClient,
})
}
>
Clear my default client
</Button>
) : null;
return (
<div className="advanced">
{options}
<ClientList link={link} rememberSelection={rememberSelection} />
{clearSelection}
</div>
);
};
export default ClientSelection;

View File

@ -1,85 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.clientTile {
display: flex;
flex-direction: row;
align-items: flex-start;
min-height: 150px;
width: 100%;
color: $foreground;
> img {
flex-shrink: 0;
height: 116px;
width: 116px;
margin-right: 14px;
border-radius: 16px;
}
> div {
display: flex;
flex-direction: column;
justify-content: space-between;
h1 {
text-align: left;
font-size: 14px;
line-height: 24px;
}
p {
margin-right: 8px;
text-align: left;
}
.button {
height: 40px;
min-width: 130px;
max-width: 165px;
margin-top: 16px;
}
}
border-radius: 8px;
padding: 15px;
// For the chevron
position: relative;
&:hover {
background-color: $app-background;
}
.installLink {
display: inline-block;
height: 40px;
margin: 8px 16px 8px 0;
img {
height: 100%;
}
}
}
.clientTileLink {
position: relative;
width: 100%;
}

View File

@ -1,125 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useContext } from 'react';
import classNames from 'classnames';
import { UAContext } from '@quentin-sommer/react-useragent';
import { Client, ClientKind, Platform } from '../clients/types';
import { SafeLink } from '../parser/types';
import Tile from './Tile';
import Button from './Button';
import appStoreBadge from '../imgs/app-store-us-alt.svg';
import playStoreBadge from '../imgs/google-play-us.svg';
import fdroidBadge from '../imgs/fdroid-badge.png';
import './ClientTile.scss';
interface IProps {
client: Client;
link: SafeLink;
}
interface IInstallBadgeImages {
[index: string]: string;
}
const installBadgeImages : IInstallBadgeImages = {
"fdroid": fdroidBadge,
"apple-app-store": appStoreBadge,
"play-store": playStoreBadge
};
const ClientTile: React.FC<IProps> = ({ client, link }: IProps) => {
const inviteLine =
client.kind === ClientKind.TEXT_CLIENT ? (
<p>{client.toInviteString(link)}</p>
) : null;
const { uaResults } = useContext(UAContext);
const className = classNames('clientTile', {
clientTileLink: client.kind === ClientKind.LINKED_CLIENT,
});
let inviteButton: JSX.Element = <></>;
const matchingInstallLinks = client.installLinks.filter((installLink) => {
if ((uaResults as any).ios) {
return installLink.platform === Platform.iOS;
} else if ((uaResults as any).android) {
return installLink.platform === Platform.Android;
} else {
return false;
}
});
const hasNativeClient = matchingInstallLinks.length > 0;
let installButtons = undefined;
if (matchingInstallLinks.length) {
installButtons = <p>{matchingInstallLinks.map((installLink) => {
return <a
rel="noopener noreferrer"
aria-label={installLink.description}
key={installLink.channelId}
href={installLink.createInstallURL(link)}
className="installLink"
target="_blank">
<img src={installBadgeImages[installLink.channelId]} alt={installLink.description} />
</a>;
})}</p>;
}
if (client.kind === ClientKind.LINKED_CLIENT) {
inviteButton = <Button>Accept invite</Button>;
} else {
const copyString = client.copyString(link);
if (copyString !== '') {
inviteButton = (
<Button
onClick={() => navigator.clipboard?.writeText(copyString)}
flashChildren="Invite copied"
>
Copy invite
</Button>
);
}
}
let clientTile = (
<Tile className={className}>
<img src={client.logo} alt={client.name + ' logo'} />
<div>
<h1>{client.name}</h1>
<p>{client.description}</p>
{installButtons}
{inviteLine}
{inviteButton}
</div>
</Tile>
);
if (client.kind === ClientKind.LINKED_CLIENT) {
if (!hasNativeClient) {
clientTile = (
<a href={client.toUrl(link).toString()}>{clientTile}</a>
);
}
}
return clientTile;
};
export default ClientTile;

View File

@ -1,92 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.createLinkTile {
row-gap: 24px;
* {
width: 100%;
}
> form {
display: grid;
row-gap: 24px;
align-self: center;
}
> a {
color: $foreground;
font-weight: bold;
font-size: 24px;
line-height: 32px;
text-align: left;
text-decoration: underline;
}
.createLinkReset {
height: 40px;
width: 40px;
border-radius: 100%;
border: 1px solid lighten($grey, 50%);
background: $background;
padding: 6px;
position: relative;
> div {
// This is a terrible case of faking it till
// we make it. It will break. I'm so sorry
position: absolute;
display: none;
width: max-content;
top: -35px;
left: -17px;
border-radius: 30px;
padding: 5px 15px;
background: $background;
word-wrap: none;
}
img {
height: 100%;
width: 100%;
border: 0;
filter: invert(12%);
}
&:hover {
border: 0;
background: $foreground;
cursor: pointer;
> div {
display: block;
}
}
}
}

View File

@ -1,32 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import CreateLinkTile from './CreateLinkTile';
export default {
title: 'CreateLinkTile',
parameters: {
design: {
type: 'figma',
url:
'https://figma.com/file/WSXjCGc1k6FVI093qhlzOP/04-Recieving-share-link?node-id=59%3A1',
},
},
};
export const Default: React.FC = () => <CreateLinkTile />;

View File

@ -1,158 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useEffect, useRef } from 'react';
import { Formik, Form } from 'formik';
import Tile from './Tile';
import Button from './Button';
import Input from './Input';
import { parseHash } from '../parser/parser';
import { LinkKind } from '../parser/types';
import linkIcon from '../imgs/link.svg';
import copyIcon from '../imgs/copy.svg';
import tickIcon from '../imgs/tick.svg';
import refreshIcon from '../imgs/refresh.svg';
import './CreateLinkTile.scss';
interface ILinkNotCreatedTileProps {
setLink: React.Dispatch<React.SetStateAction<string>>;
}
interface FormValues {
identifier: string;
}
// Hacky use of types here
function validate(values: FormValues): Partial<FormValues> {
const errors: Partial<FormValues> = {};
if (values.identifier === '') {
errors.identifier = '';
return errors;
}
const parse = parseHash(values.identifier);
if (parse.kind === LinkKind.ParseFailed) {
errors.identifier =
"That identifier doesn't look right. Double check the details.";
}
return errors;
}
const LinkNotCreatedTile: React.FC<ILinkNotCreatedTileProps> = (
props: ILinkNotCreatedTileProps
) => {
return (
<Tile className="createLinkTile">
<h1>
Create shareable links to Matrix rooms, users or messages
without being tied to any app
</h1>
<Formik
initialValues={{
identifier: '',
}}
validate={validate}
onSubmit={(values): void => {
props.setLink(
document.location.protocol +
'//' +
document.location.host +
'/#/' +
values.identifier
);
}}
>
{(formik): JSX.Element => (
<Form>
<Input
name={'identifier'}
type={'text'}
placeholder="#room:example.com, @user:example.com"
autoFocus
/>
<Button
type="submit"
icon={linkIcon}
disabled={!!formik.errors.identifier}
className={
formik.errors.identifier ? 'errorButton' : ''
}
>
Create Link
</Button>
</Form>
)}
</Formik>
</Tile>
);
};
interface ILinkCreatedTileProps {
link: string;
setLink: React.Dispatch<React.SetStateAction<string>>;
}
const LinkCreatedTile: React.FC<ILinkCreatedTileProps> = (props) => {
const buttonRef = useRef<HTMLButtonElement>(null);
// Focus button on render
useEffect((): void => {
if (buttonRef && buttonRef.current) {
buttonRef.current.focus();
}
});
return (
<Tile className="createLinkTile">
<button
className="createLinkReset"
onClick={(): void => props.setLink('')}
>
<div>New link</div>
<img src={refreshIcon} alt="Go back to matrix.to home page" />
</button>
<a className="matrixIdentifier" href={props.link}>
{props.link}
</a>
<Button
flashChildren={'Copied'}
icon={copyIcon}
flashIcon={tickIcon}
onClick={(): void => {
navigator.clipboard?.writeText(props.link);
}}
ref={buttonRef}
>
Copy Link
</Button>
</Tile>
);
};
const CreateLinkTile: React.FC = () => {
const [link, setLink] = React.useState('');
if (!link) {
return <LinkNotCreatedTile setLink={setLink} />;
} else {
return <LinkCreatedTile link={link} setLink={setLink} />;
}
};
export default CreateLinkTile;

View File

@ -1,22 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
.defaultPreview {
.avatar {
border-radius: 0;
border: 0;
}
}

View File

@ -1,42 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { SafeLink } from '../parser/types';
import Avatar from './Avatar';
import './DefaultPreview.scss';
import genericRoomPreview from '../imgs/chat-icon.svg';
interface IProps {
link: SafeLink;
}
const DefaultPreview: React.FC<IProps> = ({ link }: IProps) => {
return (
<div className="defaultPreview">
<Avatar
avatarUrl={genericRoomPreview}
label={`Generic icon representing ${link.identifier}`}
/>
<h1 className="matrixIdentifier">{link.identifier}</h1>
</div>
);
};
export default DefaultPreview;

View File

@ -1,46 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../mixins';
.details {
display: flex;
> :first-child {
min-width: 100%;
}
> input[type='checkbox'] {
// Remove the OS's representation
display: none;
&.focus-visible {
& + img {
@include unreal-focus;
}
}
&:checked {
& + img {
transform: rotate(180deg);
}
}
}
&:hover {
cursor: pointer;
}
}

View File

@ -1,35 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import chevron from '../imgs/chevron-down.svg';
import './Details.scss';
interface IProps extends React.InputHTMLAttributes<Element> {
children?: React.ReactNode;
}
const Details: React.FC<IProps> = ({ children, ...props }: IProps) => (
<label className="details">
{children}
<input type="checkbox" {...props} />
<img src={chevron} alt="" />
</label>
);
export default Details;

View File

@ -1,35 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { Room, Event } from '../matrix-cypher';
import RoomPreview from './RoomPreview';
interface IProps {
room: Room;
event: Event;
}
const EventPreview: React.FC<IProps> = ({ room, event }: IProps) => (
<>
<RoomPreview room={room} />
<p>"{event.content}"</p>
<p>{event.sender}</p>
</>
);
export default EventPreview;

View File

@ -1,31 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.fakeProgress {
width: 100%;
height: 4px;
background-color: lighten($grey, 50%);
border-radius: 4px;
> div {
width: 60%;
height: 100%;
background-color: $foreground;
border-radius: 4px;
}
}

View File

@ -1,27 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import './FakeProgress.scss';
const FakeProgress = () => (
<div className="fakeProgress">
<div />
</div>
);
export default FakeProgress;

View File

@ -1,34 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.footer {
display: grid;
grid-auto-flow: column;
justify-content: center;
column-gap: 5px;
font-size: 11px;
* {
color: $font;
}
.textButton {
margin: 0;
padding: 0;
}
}

View File

@ -1,65 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useContext } from 'react';
import HSContext, {
HSOptions,
ActionType as HSACtionType,
} from '../contexts/HSContext';
import ClientContext, {
ActionType as ClientActionType,
} from '../contexts/ClientContext';
import TextButton from './TextButton';
import './Footer.scss';
const Footer: React.FC = () => {
const [hsState, hsDispatch] = useContext(HSContext);
const [clientState, clientDispatch] = useContext(ClientContext);
const clear =
hsState.option !== HSOptions.Unset || clientState.clientId !== null ? (
<>
{' · '}
<TextButton
onClick={(): void => {
hsDispatch({
action: HSACtionType.Clear,
});
clientDispatch({
action: ClientActionType.ClearClient,
});
}}
>
Clear preferences
</TextButton>
</>
) : null;
return (
<div className="footer">
<a href="https://github.com/matrix-org/matrix.to">GitHub project</a>
{' · '}
<a href="https://github.com/matrix-org/matrix.to/tree/main/src/clients">
Add your app
</a>
{clear}
</div>
);
};
export default Footer;

View File

@ -1,26 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
.groupPreview {
> .avatar {
margin-bottom: 8px;
}
> h1 {
font-size: 24px;
margin-bottom: 4px;
}
}

View File

@ -1,45 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { Group } from '../matrix-cypher';
import { GroupAvatar } from './Avatar';
import './GroupPreview.scss';
interface IProps {
group: Group;
groupId: string;
}
const GroupPreview: React.FC<IProps> = ({ group, groupId }: IProps) => {
const description = group.long_description
? group.long_description
: group.short_description
? group.short_description
: null;
return (
<div className="groupPreview">
<GroupAvatar group={group} groupId={groupId}/>
<h1>{group.name}</h1>
{description ? <p>{description}</p> : null}
</div>
);
};
export default GroupPreview;

View File

@ -1,57 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.homeserverOptions {
display: grid;
row-gap: 20px;
background: $app-background;
text-align: left;
> * {
width: 100%;
}
.homeserverOptionsDescription {
width: 100%;
display: flex;
flex-direction: row;
justify-content: space-between;
> p {
flex-grow: 1;
}
> img {
flex-shrink: 0;
flex-grow: 0;
background-color: $background;
height: 62px;
width: 62px;
padding: 11px;
border-radius: 100%;
margin-left: 14px;
}
}
form {
display: grid;
row-gap: 25px;
}
}

View File

@ -1,42 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import HomeserverOptions from './HomeserverOptions';
import { LinkKind } from '../parser/types';
export default {
title: 'HomeserverOptions',
parameters: {
design: {
type: 'figma',
url:
'https://figma.com/file/WSXjCGc1k6FVI093qhlzOP/04-Recieving-share-link?node-id=143%3A5853',
},
},
};
export const Default: React.FC = () => (
<HomeserverOptions
link={{
identifier: '#banter:matrix.org',
arguments: { vias: [], originalParams: new URLSearchParams() },
kind: LinkKind.Alias,
originalLink: 'This is all made up',
}}
/>
);

View File

@ -1,130 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useContext, useState } from 'react';
import { Formik, Form } from 'formik';
import { string } from 'zod';
import Tile from './Tile';
import HSContext, { TempHSContext, ActionType } from '../contexts/HSContext';
import icon from '../imgs/telecom-mast.svg';
import Button from './Button';
import Input from './Input';
import StyledCheckbox from './StyledCheckbox';
import { SafeLink } from '../parser/types';
import './HomeserverOptions.scss';
interface IProps {
link: SafeLink;
}
interface FormValues {
HSUrl: string;
}
function validateURL(values: FormValues): Partial<FormValues> {
const errors: Partial<FormValues> = {};
try {
string().url().parse(values.HSUrl);
} catch {
errors.HSUrl =
'This must be a valid homeserver URL, starting with https://';
}
return errors;
}
const HomeserverOptions: React.FC<IProps> = ({ link }: IProps) => {
const HSStateDispatcher = useContext(HSContext)[1];
const TempHSStateDispatcher = useContext(TempHSContext)[1];
const [rememberSelection, setRemeberSelection] = useState(false);
// Select which disaptcher to use based on whether we're writing
// the choice to localstorage
const dispatcher = rememberSelection
? HSStateDispatcher
: TempHSStateDispatcher;
const hsInput = (
<Formik
initialValues={{
HSUrl: '',
}}
validate={validateURL}
onSubmit={({ HSUrl }): void =>
dispatcher({ action: ActionType.SetHS, HSURL: HSUrl })
}
>
{({ values, errors }): JSX.Element => (
<Form>
<Input
muted={!values.HSUrl}
type="text"
name="HSUrl"
placeholder="Preferred homeserver URL"
/>
{values.HSUrl && !errors.HSUrl ? (
<Button secondary type="submit">
Use {values.HSUrl}
</Button>
) : null}
</Form>
)}
</Formik>
);
return (
<Tile className="homeserverOptions">
<div className="homeserverOptionsDescription">
<div>
<h3>
About&nbsp;
<span className="matrixIdentifier">
{link.identifier}
</span>
</h3>
<p>
A homeserver will show you metadata about the link, like
a description. Homeservers will be able to relate your
IP to things you've opened invites for in matrix.to.
</p>
</div>
<img
src={icon}
alt="Icon making it clear that connections may be made with external services"
/>
</div>
<StyledCheckbox
checked={rememberSelection}
onChange={(e): void => setRemeberSelection(e.target.checked)}
>
Remember my choice
</StyledCheckbox>
<Button
secondary
onClick={(): void => {
dispatcher({ action: ActionType.SetAny });
}}
>
Use any homeserver
</Button>
{hsInput}
</Tile>
);
};
export default HomeserverOptions;

View File

@ -1,50 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
@import '../error';
.input {
width: 100%;
padding: 12px;
background: $background;
border: 1px solid $foreground;
border-radius: 16px;
font: lighten($grey, 60%);
font-size: 14px;
line-height: 24px;
&.error {
@include error;
}
&:focus {
border: 1px solid $font;
font: $font;
}
}
.inputError {
@include error;
text-align: center;
}
.inputMuted {
border-color: lighten($grey, 60%);
}

View File

@ -1,45 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { withDesign } from 'storybook-addon-designs';
import { Formik, Form } from 'formik';
import Input from './Input';
export default {
title: 'Input',
parameters: {
design: {
type: 'figma',
url:
'https://figma.com/file/WSXjCGc1k6FVI093qhlzOP/04-Recieving-share-link?node-id=59%3A1',
},
},
decorators: [withDesign],
};
export const Default: React.FC = () => (
<Formik initialValues={{}} onSubmit={(): void => {}}>
<Form>
<Input
name="Example input"
type="text"
placeholder="Write something"
/>
</Form>
</Formik>
);

View File

@ -1,50 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import classnames from 'classnames';
import { useField } from 'formik';
import './Input.scss';
interface IProps extends React.InputHTMLAttributes<HTMLElement> {
name: string;
type: string;
muted?: boolean;
}
const Input: React.FC<IProps> = ({ className, muted, ...props }) => {
const [field, meta] = useField(props);
const errorBool = meta.touched && meta.value !== '' && meta.error;
const error = errorBool ? (
<div className="inputError">{meta.error}</div>
) : null;
const classNames = classnames('input', className, {
error: errorBool,
inputMuted: !!muted,
});
return (
<>
<input type="text" className={classNames} {...field} {...props} />
{error}
</>
);
};
export default Input;

View File

@ -1,39 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.inviteTile {
display: grid;
row-gap: 24px;
.inviteTileClientSelection {
margin: 0 auto;
display: grid;
justify-content: space-between;
row-gap: 20px;
h2 + p {
color: $foreground;
}
}
hr {
width: 100%;
margin: 0;
}
}

View File

@ -1,123 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// disable camelcase check because our object keys come
// from the matrix spec
/* eslint-disable @typescript-eslint/camelcase */
import React from 'react';
import InviteTile from './InviteTile';
import UserPreview, { InviterPreview } from './UserPreview';
import RoomPreview, { RoomPreviewWithTopic } from './RoomPreview';
import Clients from '../clients';
import { LinkKind, SafeLink } from '../parser/types';
export default {
title: 'InviteTile',
parameters: {
design: {
type: 'figma',
url:
'https://figma.com/file/WSXjCGc1k6FVI093qhlzOP/04-Recieving-share-link?node-id=59%3A334',
},
},
};
const userLink: SafeLink = {
kind: LinkKind.UserId,
identifier: '@jorik:matrix.org',
arguments: {
vias: [],
originalParams: new URLSearchParams(),
},
originalLink: 'asdfsadf',
};
const roomLink: SafeLink = {
kind: LinkKind.Alias,
identifier: '#element-dev:matrix.org',
arguments: {
vias: [],
originalParams: new URLSearchParams(),
},
originalLink: 'asdfsadf',
};
export const withLink: React.FC<{}> = () => (
<InviteTile client={Clients[0]} link={userLink}>
This is an invite with a link
</InviteTile>
);
export const withInstruction: React.FC<{}> = () => (
<InviteTile client={Clients[0]} link={userLink}>
This is an invite with an instruction
</InviteTile>
);
export const withUserPreview: React.FC<{}> = () => (
<InviteTile client={Clients[0]} link={userLink}>
<UserPreview
user={{
avatar_url: 'mxc://matrix.org/EqMZYbAYhREvHXvYFyfxOlkf',
displayname: 'Nicholas Briteli',
}}
userId="@nicholasbritelli:matrix.org"
/>
</InviteTile>
);
export const withRoomPreviewAndRoomTopic: React.FC<{}> = () => (
<InviteTile client={Clients[0]} link={roomLink}>
<RoomPreviewWithTopic
room={{
aliases: ['#murrays:cheese.bar'],
avatar_url: 'mxc://bleeker.street/CHEDDARandBRIE',
guest_can_join: false,
name: 'CHEESE',
num_joined_members: 37,
room_id: '!ol19s:bleecker.street',
topic: 'Tasty tasty cheese',
world_readable: true,
}}
/>
</InviteTile>
);
export const withRoomPreviewAndInviter: React.FC<{}> = () => (
<InviteTile client={Clients[0]} link={roomLink}>
<InviterPreview
user={{
avatar_url: 'mxc://matrix.org/EqMZYbAYhREvHXvYFyfxOlkf',
displayname: 'Nicholas Briteli',
}}
userId="@nicholasbritelli:matrix.org"
/>
<RoomPreview
room={{
aliases: ['#murrays:cheese.bar'],
avatar_url: 'mxc://bleeker.street/CHEDDARandBRIE',
guest_can_join: false,
name: 'CHEESE',
num_joined_members: 37,
room_id: '!ol19s:bleecker.street',
topic: 'Tasty tasty cheese',
world_readable: true,
}}
/>
</InviteTile>
);

View File

@ -1,120 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useState } from 'react';
import './InviteTile.scss';
import Tile from './Tile';
import LinkButton from './LinkButton';
import Button from './Button';
import ClientSelection from './ClientSelection';
import { Client, ClientKind } from '../clients/types';
import { SafeLink } from '../parser/types';
import TextButton from './TextButton';
interface IProps {
children?: React.ReactNode;
client: Client | null;
link: SafeLink;
}
const InviteTile: React.FC<IProps> = ({ children, client, link }: IProps) => {
const [showAdvanced, setShowAdvanced] = useState(false);
let invite: React.ReactNode;
let advanced: React.ReactNode;
if (client === null) {
invite = showAdvanced ? null : (
<Button onClick={(): void => setShowAdvanced(!showAdvanced)}>
Accept invite
</Button>
);
} else {
let inviteUseString: string;
switch (client.kind) {
case ClientKind.LINKED_CLIENT:
invite = (
<LinkButton href={client.toUrl(link).toString()}>
Accept invite
</LinkButton>
);
inviteUseString = `Accepting will open this link in ${client.name}.`;
break;
case ClientKind.TEXT_CLIENT:
// TODO: copy to clipboard
invite = <p>{client.toInviteString(link)}</p>;
navigator.clipboard?.writeText(client.copyString(link));
inviteUseString = `These are instructions for ${client.name}.`;
break;
}
const advancedButton = (
<p>
{inviteUseString}
<TextButton
onClick={(): void => setShowAdvanced(!showAdvanced)}
>
Change client
</TextButton>
</p>
);
invite = (
<>
{invite}
{advancedButton}
</>
);
}
if (showAdvanced) {
if (client === null) {
advanced = (
<>
<hr />
<h2>Almost done!</h2>
<p>Great, pick a client below to confirm and continue</p>
<ClientSelection link={link} />
</>
);
} else {
advanced = (
<>
<hr />
<h4>Change app</h4>
<ClientSelection link={link} />
</>
);
}
}
advanced = advanced ? (
<div className="inviteTileClientSelection">{advanced}</div>
) : null;
return (
<>
<Tile className="inviteTile">
{children}
{invite}
{advanced}
</Tile>
</>
);
};
export default InviteTile;

View File

@ -1,23 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import ClientTile from './InvitingClientTile';
export default { title: 'ClientTile' };
export const Element = <ClientTile clientName={'element.io'} />;

View File

@ -1,58 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import Tile from './Tile';
import { clientMap } from '../clients';
import './MatrixTile.scss';
interface IProps {
clientName: string;
}
const InvitingClientTile: React.FC<IProps> = ({ clientName }: IProps) => {
const client = clientMap[clientName];
if (!client) {
return (
<Tile className="matrixTile">
{/* TODO: add gh link */}
<p>
The client that created this link "{clientName}" is not a
recognised client. If this is a mistake and you'd like a
nice advertisement for it here please{' '}
<a href="https://github.com/matrix-org/matrix.to">
open a pr
</a>
.
</p>
</Tile>
);
}
return (
<Tile className="matrixTile">
<img src={client.logo} alt={client.name} />
<h2>
Invite created with <a href={client.homepage}>{client.name}</a>
</h2>
<div>{client.description}</div>
</Tile>
);
};
export default InvitingClientTile;

View File

@ -1,34 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import classnames from 'classnames';
import './Button.scss';
interface IProps extends React.LinkHTMLAttributes<HTMLElement> {}
const LinkButton: React.FC<IProps> = ({
className,
children,
...props
}: IProps) => (
<a className={classnames('button', className)} {...props}>
{children}
</a>
);
export default LinkButton;

View File

@ -1,193 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useState, useEffect, useContext } from 'react';
import { getEvent, client } from '../matrix-cypher';
import { RoomPreviewWithTopic } from './RoomPreview';
import InviteTile from './InviteTile';
import { SafeLink, LinkKind } from '../parser/types';
import UserPreview, { WrappedInviterPreview } from './UserPreview';
import EventPreview from './EventPreview';
import GroupPreview from './GroupPreview';
import HomeserverOptions from './HomeserverOptions';
import DefaultPreview from './DefaultPreview';
import Details from './Details';
import { clientMap } from '../clients';
import {
getRoomFromId,
getRoomFromAlias,
getRoomFromPermalink,
getUser,
getGroup,
} from '../utils/cypher-wrapper';
import { ClientContext } from '../contexts/ClientContext';
import useHSs from '../utils/getHS';
interface IProps {
link: SafeLink;
}
const invite = async ({
clientAddress,
link,
}: {
clientAddress: string;
link: SafeLink;
}): Promise<JSX.Element> => {
// TODO: replace with client fetch
switch (link.kind) {
case LinkKind.Alias:
return (
<RoomPreviewWithTopic
room={
await getRoomFromAlias(clientAddress, link.identifier)
}
/>
);
case LinkKind.RoomId:
return (
<RoomPreviewWithTopic
room={await getRoomFromId(clientAddress, link.identifier)}
/>
);
case LinkKind.UserId:
return (
<UserPreview
user={await getUser(clientAddress, link.identifier)}
userId={link.identifier}
/>
);
case LinkKind.Permalink:
return (
<EventPreview
room={await getRoomFromPermalink(clientAddress, link)}
event={
await getEvent(
await client(clientAddress),
link.roomLink,
link.eventId
)
}
/>
);
case LinkKind.GroupId:
return (
<GroupPreview
group={await getGroup(clientAddress, link.identifier)}
groupId={link.identifier}
/>
);
default:
// Todo Implement events
return <></>;
}
};
interface PreviewProps extends IProps {
client: string;
}
const Preview: React.FC<PreviewProps> = ({ link, client }: PreviewProps) => {
const [content, setContent] = useState(<DefaultPreview link={link} />);
// TODO: support multiple clients with vias
useEffect(() => {
(async (): Promise<void> =>
setContent(
await invite({
clientAddress: client,
link,
})
))();
}, [link, client]);
return content;
};
const LinkPreview: React.FC<IProps> = ({ link }: IProps) => {
let content: JSX.Element;
const [showHSOptions, setShowHSOPtions] = useState(false);
const hses = useHSs({ link });
if (!hses.length) {
content = (
<>
<DefaultPreview link={link} />
<Details
checked={showHSOptions}
onChange={(): void => setShowHSOPtions(!showHSOptions)}
>
<span>
About&nbsp;
<span className="matrixIdentifier">
{link.identifier}
</span>
</span>
</Details>
</>
);
if (showHSOptions) {
content = (
<>
{content}
<HomeserverOptions link={link} />
</>
);
}
} else {
content = <Preview link={link} client={hses[0]} />;
}
const [{ clientId }] = useContext(ClientContext);
// Select which client to link to
const displayClientId = clientId
? clientId
: link.arguments.client
? link.arguments.client
: null;
const client = displayClientId ? clientMap[displayClientId] : null;
const sharer = link.arguments.sharer ? (
<WrappedInviterPreview
link={{
kind: LinkKind.UserId,
identifier: link.arguments.sharer,
arguments: { vias: [], originalParams: new URLSearchParams() },
originalLink: '',
}}
/>
) : (
<p style={{ margin: '0 0 10px 0' }}>You're invited to join</p>
);
return (
<InviteTile client={client} link={link}>
{sharer}
{content}
</InviteTile>
);
};
export default LinkPreview;

View File

@ -1,24 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
.matrixTile {
background: none;
box-shadow: none;
row-gap: 16px;
padding: 0 40px;
justify-items: left;
text-align: left;
}

View File

@ -1,23 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import MatrixTile from './MatrixTile';
export default { title: 'MatrixTile' };
export const Default: React.FC = () => <MatrixTile />;

View File

@ -1,53 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import Tile from './Tile';
import Footer from './Footer';
import logo from '../imgs/matrix-logo.svg';
import './MatrixTile.scss';
interface IProps {
isLink?: boolean;
}
const MatrixTile: React.FC<IProps> = ({ isLink }: IProps) => {
const copy = isLink ? (
<div>
This invite uses <a href="https://matrix.org">Matrix</a>, an open
network for secure, decentralized communication.
</div>
) : (
<div>
Matrix.to is a stateless URL redirecting service for the{' '}
<a href="https://matrix.org">Matrix</a> ecosystem.
</div>
);
return (
<div>
<Tile className="matrixTile">
<img src={logo} alt="matrix-logo" />
{copy}
<Footer />
</Tile>
</div>
);
};
export default MatrixTile;

View File

@ -1,30 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
.roomPreview {
> .avatar {
margin-bottom: 8px;
}
> h1 {
font-size: 24px;
margin-bottom: 4px;
}
}
.roomTopic {
padding-top: 8px;
}

View File

@ -1,60 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { Room } from '../matrix-cypher';
import { RoomAvatar } from './Avatar';
import './RoomPreview.scss';
interface IProps {
room: Room;
}
const RoomPreview: React.FC<IProps> = ({ room }: IProps) => {
const roomAlias = room.canonical_alias
? room.canonical_alias
: room.aliases
? room.aliases[0]
: room.room_id;
const members =
room.num_joined_members > 0 ? (
<p>{room.num_joined_members.toLocaleString()} members</p>
) : null;
return (
<div className="roomPreview">
<RoomAvatar room={room} />
<h1 className="matrixIdentifier">
{room.name ? room.name : roomAlias}
</h1>
{members}
<p className="matrixIdentifier">{roomAlias}</p>
</div>
);
};
export const RoomPreviewWithTopic: React.FC<IProps> = ({ room }: IProps) => {
const topic = room.topic ? <p className="roomTopic">{room.topic}</p> : null;
return (
<>
<RoomPreview room={room} />
{topic}
</>
);
};
export default RoomPreview;

View File

@ -1,59 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
@import '../mixins';
.styledCheckbox {
display: flex;
align-items: center;
input[type='checkbox'] {
display: none;
&:checked + div {
background: $foreground;
img {
display: block;
}
}
&.focus-visible {
& + div {
@include unreal-focus;
}
}
}
.styledCheckboxWrapper {
display: flex;
margin-right: 5px;
border: 2px solid $foreground;
box-sizing: border-box;
border-radius: 4px;
height: 16px;
width: 16px;
img {
height: 100%;
width: 100%;
display: none;
}
}
}

View File

@ -1,41 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
/*
* Stolen from the matrix-react-sdk
*/
import React from 'react';
import tick from '../imgs/tick.svg';
import './StyledCheckbox.scss';
interface IProps extends React.InputHTMLAttributes<HTMLInputElement> {}
const StyledCheckbox: React.FC<IProps> = ({
children,
className,
...otherProps
}: IProps) => (
<label className="styledCheckbox">
<input {...otherProps} type="checkbox" />
{/* Using the div to center the image */}
<div className="styledCheckboxWrapper">
<img src={tick} alt="" />
</div>
{children}
</label>
);
export default StyledCheckbox;

View File

@ -1,31 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.textButton {
background: none;
border: none;
color: $link;
font-style: normal;
font-weight: normal;
font-size: 14px;
line-height: 24px;
&:hover {
cursor: pointer;
}
}

View File

@ -1,34 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import TextButton from './TextButton';
export default {
title: 'TextButton',
parameters: {
design: {
type: 'figma',
url:
'https://figma.com/file/WSXjCGc1k6FVI093qhlzOP/04-Recieving-share-link?node-id=149%3A10756',
},
},
};
export const Default: React.FC = () => (
<TextButton>This is a button?</TextButton>
);

View File

@ -1,30 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import classnames from 'classnames';
import './TextButton.scss';
const TextButton: React.FC<React.ButtonHTMLAttributes<Element>> = ({
className,
...props
}) => {
return (
<button className={classnames('textButton', className)} {...props} />
);
};
export default TextButton;

View File

@ -1,35 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.tile {
background-color: $background;
border-radius: 16px;
box-shadow: 0px 18px 24px rgba(0, 0, 0, 0.06);
padding: 2rem;
display: grid;
justify-items: center;
text-align: center;
p {
color: $grey;
}
transition: width 2s, height 2s, transform 2s;
}

View File

@ -1,38 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import Tile from './Tile';
export default {
title: 'Tile',
parameters: {
design: {
type: 'figma',
url:
'https://figma.com/file/WSXjCGc1k6FVI093qhlzOP/04-Recieving-share-link?node-id=143%3A5853',
},
},
};
export const Default: React.FC = () => (
<Tile>
<h1>This is a tile</h1>
<p>Some text</p>
<p>Note the rounded corners</p>
</Tile>
);

View File

@ -1,35 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import classnames from 'classnames';
import './Tile.scss';
interface IProps {
className?: string;
children: React.ReactNode;
}
const Tile: React.FC<IProps> = (props: IProps) => {
return (
<div className={classnames('tile', props.className)}>
{props.children}
</div>
);
};
export default Tile;

View File

@ -1,85 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import '../color-scheme';
.userPreview {
width: 100%;
> .avatar {
margin-bottom: 8px;
}
h1 {
font-size: 24px;
margin-bottom: 4px;
}
p {
margin-bottom: 16px;
}
hr {
width: 100%;
margin: 0;
opacity: 0.2;
}
}
.miniUserPreview {
width: 100%;
display: flex;
flex-direction: row;
align-items: center;
border: 1px solid $app-background;
border-radius: 16px;
padding: 6px 16px;
> div {
flex-grow: 1;
text-align: left;
}
h1 {
font-weight: normal;
font-size: 14px;
line-height: 20px;
text-align: left;
}
p {
line-height: 20px;
}
.avatar {
flex-grow: 0;
flex-shrink: 0;
height: 32px;
width: 32px;
}
&.centeredMiniUserPreview {
h1 {
width: unset;
text-align: center;
}
img {
display: none;
}
}
}

View File

@ -1,100 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useState, useEffect } from 'react';
import { client, User, getUserDetails } from '../matrix-cypher';
import classNames from 'classnames';
import icon from '../imgs/chat-icon.svg';
import Avatar, { UserAvatar } from './Avatar';
import useHSs from '../utils/getHS';
import { UserId } from '../parser/types';
import './UserPreview.scss';
interface IProps {
user: User;
userId: string;
}
const UserPreview: React.FC<IProps> = ({ user, userId }: IProps) => (
<div className="userPreview">
<UserAvatar user={user} userId={userId} />
<h1>{user.displayname} invites you to connect</h1>
<p>{userId}</p>
<hr />
</div>
);
export default UserPreview;
interface InviterPreviewProps {
user?: User;
userId: string;
}
export const InviterPreview: React.FC<InviterPreviewProps> = ({
user,
userId,
}: InviterPreviewProps) => {
const avatar = user ? (
<UserAvatar user={user} userId={userId} />
) : (
<Avatar
className="avatarNoCrop"
label={`Placeholder icon for ${userId}`}
avatarUrl={icon}
/>
);
const className = classNames('miniUserPreview', {
centeredMiniUserPreview: !user,
});
return (
<div className={className}>
<div>
<h1>
Invited by{' '}
<b className="matrixIdentifier">
{user ? user.displayname : userId}
</b>
</h1>
{user ? <p className="matrixIdentifier">{userId}</p> : null}
</div>
{avatar}
</div>
);
};
interface WrappedInviterProps {
link: UserId;
}
export const WrappedInviterPreview: React.FC<WrappedInviterProps> = ({
link,
}: WrappedInviterProps) => {
const [user, setUser] = useState<User | undefined>(undefined);
const hss = useHSs({ link });
useEffect(() => {
if (hss.length) {
client(hss[0])
.then((c) => getUserDetails(c, link.identifier))
.then(setUser)
.catch((x) => console.log("couldn't fetch user preview", x));
}
}, [hss, link]);
return <InviterPreview user={user} userId={link.identifier} />;
};

View File

@ -1,108 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { object, string, boolean, TypeOf } from 'zod';
import { ClientId } from '../clients/types';
import { persistReducer } from '../utils/localStorage';
const STATE_SCHEMA = object({
clientId: string().nullable(),
showOnlyDeviceClients: boolean(),
showExperimentalClients: boolean(),
});
type State = TypeOf<typeof STATE_SCHEMA>;
// Actions are a discriminated union.
export enum ActionType {
SetClient = 'SET_CLIENT',
ClearClient = 'CLEAR_CLIENT',
ToggleShowOnlyDeviceClients = 'TOGGLE_SHOW_ONLY_DEVICE_CLIENTS',
ToggleShowExperimentalClients = 'TOGGLE_SHOW_EXPERIMENTAL_CLIENTS',
}
interface SetClient {
action: ActionType.SetClient;
clientId: ClientId;
}
interface ClearClient {
action: ActionType.ClearClient;
}
interface ToggleShowOnlyDeviceClients {
action: ActionType.ToggleShowOnlyDeviceClients;
}
interface ToggleShowExperimentalClients {
action: ActionType.ToggleShowExperimentalClients;
}
export type Action =
| SetClient
| ClearClient
| ToggleShowOnlyDeviceClients
| ToggleShowExperimentalClients;
const INITIAL_STATE: State = {
clientId: null,
showOnlyDeviceClients: true,
showExperimentalClients: false,
};
export const [initialState, reducer] = persistReducer(
'default-client',
INITIAL_STATE,
STATE_SCHEMA,
(state: State, action: Action): State => {
switch (action.action) {
case ActionType.SetClient:
return {
...state,
clientId: action.clientId,
};
case ActionType.ToggleShowOnlyDeviceClients:
return {
...state,
showOnlyDeviceClients: !state.showOnlyDeviceClients,
};
case ActionType.ToggleShowExperimentalClients:
return {
...state,
showExperimentalClients: !state.showExperimentalClients,
};
case ActionType.ClearClient:
return {
...state,
clientId: null,
};
}
}
);
// The defualt reducer needs to be overwritten with the one above
// after it's been put through react's useReducer
export const ClientContext = React.createContext<
[State, React.Dispatch<Action>]
>([initialState, (): void => {}]);
export default ClientContext;
// Quick rename to make importing easier
export const ClientProvider = ClientContext.Provider;
export const ClientConsumer = ClientContext.Consumer;

View File

@ -1,49 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React, { useReducer } from 'react';
import { UserAgentProvider } from '@quentin-sommer/react-useragent';
import {
ClientProvider,
reducer as clientReducer,
initialState as clientInitialState,
} from './ClientContext';
import {
HSProvider,
reducer as HSReducer,
initialState as HSInitialState,
unpersistedReducer as HSTempReducer,
TempHSProvider,
} from './HSContext';
interface IProps {
children: React.ReactNode;
}
export default ({ children }: IProps): JSX.Element => (
<UserAgentProvider ua={window.navigator.userAgent}>
<ClientProvider value={useReducer(clientReducer, clientInitialState)}>
<HSProvider value={useReducer(HSReducer, HSInitialState)}>
<TempHSProvider
value={useReducer(HSTempReducer, HSInitialState)}
>
{children}
</TempHSProvider>
</HSProvider>
</ClientProvider>
</UserAgentProvider>
);

View File

@ -1,120 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import { string, object, union, literal, TypeOf } from 'zod';
import { persistReducer } from '../utils/localStorage';
export enum HSOptions {
// The homeserver contact policy hasn't
// been set yet.
Unset = 'UNSET',
// Matrix.to should only contact a single provided homeserver
TrustedHSOnly = 'TRUSTED_CLIENT_ONLY',
// Matrix.to may contact any homeserver it requires
Any = 'ANY',
}
const STATE_SCHEMA = union([
object({
option: literal(HSOptions.Unset),
}),
object({
option: literal(HSOptions.Any),
}),
object({
option: literal(HSOptions.TrustedHSOnly),
hs: string(),
}),
]);
export type State = TypeOf<typeof STATE_SCHEMA>;
// TODO: rename actions to something with more meaning out of context
export enum ActionType {
SetHS = 'SET_HS',
SetAny = 'SET_ANY',
Clear = 'CLEAR',
}
export interface SetHS {
action: ActionType.SetHS;
HSURL: string;
}
export interface SetAny {
action: ActionType.SetAny;
}
export interface Clear {
action: ActionType.Clear;
}
export type Action = SetHS | SetAny | Clear;
export const INITIAL_STATE: State = {
option: HSOptions.Unset,
};
export const unpersistedReducer = (_state: State, action: Action): State => {
switch (action.action) {
case ActionType.SetAny:
return {
option: HSOptions.Any,
};
case ActionType.SetHS:
return {
option: HSOptions.TrustedHSOnly,
hs: action.HSURL,
};
case ActionType.Clear:
return {
option: HSOptions.Unset,
};
}
};
export const [initialState, reducer] = persistReducer(
'home-server-options',
INITIAL_STATE,
STATE_SCHEMA,
unpersistedReducer
);
// The defualt reducer needs to be overwritten with the one above
// after it's been put through react's useReducer
const HSContext = React.createContext<[State, React.Dispatch<Action>]>([
initialState,
(): void => {},
]);
export default HSContext;
// Quick rename to make importing easier
export const HSProvider = HSContext.Provider;
export const HSConsumer = HSContext.Consumer;
// The defualt reducer needs to be overwritten with the one above
// after it's been put through react's useReducer
// The temp reducer is for unpersisted choices with regards to GDPR
export const TempHSContext = React.createContext<
[State, React.Dispatch<Action>]
>([INITIAL_STATE, (): void => {}]);
// Quick rename to make importing easier
export const TempHSProvider = TempHSContext.Provider;
export const TempHSConsumer = TempHSContext.Consumer;

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 13 KiB

View File

@ -1,226 +0,0 @@
<svg width="1440" height="1505" viewBox="0 0 1440 1505" fill="none" xmlns="http://www.w3.org/2000/svg">
<g clip-path="url(#clip0)">
<g opacity="0.26">
<path opacity="0.26" d="M1027.99 602.979C1262.01 860.194 1465.48 1242.7 1528.69 1544.36C1592.2 1847.63 1503.31 2018.17 1310.8 1964.61C1117.48 1910.83 851.081 1638.68 658.35 1297.66C466.355 957.9 378.93 607.541 443.1 434.715C506.167 264.833 707.508 296.249 938.653 512.115C968.31 539.852 998.261 570.239 1027.99 602.979Z" stroke="url(#paint0_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1044.18 604.303C1277.61 867.698 1476.23 1255.51 1532.89 1558.78C1589.85 1863.67 1493.74 2031.71 1297.33 1973.07C1100.11 1914.14 833.789 1635 645.032 1288.91C457.01 944.068 376.871 591.501 447.59 420.442C517.133 252.325 723.184 289.112 954.844 511.085C984.648 539.632 1014.53 570.827 1044.18 604.303Z" stroke="url(#paint1_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1060.81 606.069C1293.5 875.644 1486.97 1268.6 1536.79 1573.27C1586.9 1879.56 1483.51 2045.03 1283.27 1981.09C1082.22 1916.94 816.124 1630.66 631.709 1279.64C447.955 930.015 375.249 575.389 452.665 406.316C528.757 240.112 739.517 282.417 971.546 510.496C1001.42 539.779 1031.3 571.784 1060.81 606.069Z" stroke="url(#paint2_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1077.88 608.276C1309.61 883.958 1497.64 1281.99 1540.46 1587.91C1583.51 1895.45 1472.69 2058.05 1268.62 1988.82C1063.75 1919.29 798.166 1626.02 618.239 1270.22C439.048 915.668 374.068 559.276 458.328 392.263C541.117 228.12 756.587 276.09 988.836 510.349C1018.64 540.441 1048.44 573.255 1077.88 608.276Z" stroke="url(#paint3_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1095.4 610.925C1325.96 892.714 1508.24 1295.6 1543.86 1602.56C1579.62 1911.12 1461.21 2070.71 1253.4 1996.03C1044.7 1921.06 779.774 1620.73 604.704 1260.22C430.223 901.101 373.265 543.09 464.516 378.432C554.148 216.569 774.329 270.278 1006.5 510.644C1036.31 541.545 1066.11 575.168 1095.4 610.925Z" stroke="url(#paint4_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1113.28 614.089C1342.51 901.984 1518.76 1309.58 1546.94 1617.42C1575.2 1926.87 1449.14 2083.21 1237.57 2002.94C1025.12 1922.38 761.152 1615.14 591.086 1250.06C421.609 886.313 372.967 526.904 471.209 364.747C567.832 205.385 792.575 264.907 1024.68 511.453C1054.48 543.163 1084.14 577.522 1113.28 614.089Z" stroke="url(#paint5_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1131.6 617.694C1359.29 911.622 1529.21 1323.86 1549.67 1632.28C1570.2 1942.39 1436.27 2095.28 1221.02 2009.42C1004.88 1923.19 741.947 1608.96 577.253 1239.47C413.148 871.378 373.042 510.718 478.496 351.283C582.184 194.497 811.636 260.051 1043.3 512.704C1073.1 545.224 1102.68 580.392 1131.6 617.694Z" stroke="url(#paint6_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1150.29 621.814C1376.21 921.702 1539.51 1338.35 1552.02 1647.21C1564.6 1957.77 1422.72 2106.98 1203.79 2015.38C983.98 1923.41 722.443 1602.26 563.342 1228.43C404.83 856.074 373.554 494.531 486.367 337.966C597.267 184.049 831.282 255.71 1062.5 514.543C1092.23 547.799 1121.59 583.703 1150.29 621.814Z" stroke="url(#paint7_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1169.43 626.449C1393.36 932.296 1549.74 1353.14 1554.08 1662.3C1558.42 1973.07 1408.52 2118.46 1186.06 2021.04C962.716 1923.19 702.724 1595.12 549.436 1217.25C396.738 840.622 374.514 478.418 494.833 324.869C613.018 173.969 851.596 251.884 1082.15 516.823C1111.73 550.888 1140.95 587.528 1169.43 626.449Z" stroke="url(#paint8_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1188.93 631.527C1410.65 943.26 1559.82 1368.15 1555.77 1677.31C1551.73 1988.08 1393.58 2129.42 1167.59 2026.05C940.711 1922.23 682.485 1587.33 535.38 1205.48C388.863 824.953 375.984 462.233 503.883 312.069C629.574 164.406 872.567 248.721 1102.24 519.694C1131.75 554.421 1160.74 591.944 1188.93 631.527Z" stroke="url(#paint9_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1208.87 637.192C1428.24 954.737 1569.83 1383.53 1557.1 1692.39C1544.37 2002.95 1377.91 2139.94 1148.53 2030.61C918.192 1920.76 662.027 1579.09 521.323 1193.41C381.135 809.134 377.971 446.194 513.523 299.414C646.794 155.209 894.276 245.925 1122.85 523.005C1152.21 558.615 1180.98 596.799 1208.87 637.192Z" stroke="url(#paint10_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1229.18 643.371C1445.9 966.729 1579.62 1399.12 1558.05 1707.55C1536.42 2017.66 1361.5 2150.17 1128.73 2034.65C895.012 1918.7 641.127 1570.26 507.12 1180.9C373.702 793.021 380.399 430.154 523.752 287.126C664.676 146.526 916.573 243.865 1143.89 526.904C1173.11 563.249 1201.66 602.243 1229.18 643.371Z" stroke="url(#paint11_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1249.94 650.066C1463.79 979.089 1589.26 1414.87 1558.65 1722.63C1527.81 2032.01 1344.43 2159.8 1108.35 2038.11C871.318 1915.91 619.936 1560.84 492.994 1168.03C366.493 776.761 383.345 414.188 534.645 275.06C683.37 138.286 939.609 242.319 1165.46 531.391C1194.52 568.546 1222.78 608.276 1249.94 650.066Z" stroke="url(#paint12_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1271.06 657.351C1481.74 991.965 1598.75 1430.98 1558.79 1737.78C1518.61 2046.21 1326.54 2169.07 1087.3 2041.13C847.033 1912.6 598.447 1550.91 478.791 1154.86C359.502 760.354 386.877 398.37 546.199 263.288C702.871 130.561 963.305 241.437 1187.53 536.395C1216.31 574.359 1244.27 614.825 1271.06 657.351Z" stroke="url(#paint13_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1292.55 665.149C1499.92 1005.28 1608.1 1447.31 1558.5 1752.94C1508.68 2060.19 1307.93 2177.83 1065.52 2043.56C822.088 1908.62 576.52 1540.39 464.443 1141.32C352.734 743.726 390.853 382.552 558.417 251.811C723.11 123.277 987.739 241.142 1210.05 542.06C1238.61 580.686 1266.2 621.961 1292.55 665.149Z" stroke="url(#paint14_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1314.47 673.537C1518.24 1019.11 1617.22 1463.87 1557.91 1768.1C1498.23 2073.94 1288.64 2186.14 1043.15 2045.4C796.623 1904.06 554.44 1529.35 450.163 1127.42C346.328 726.878 395.413 366.955 571.218 240.702C744.007 116.656 1012.83 241.585 1233.01 548.314C1261.27 587.677 1288.57 629.687 1314.47 673.537Z" stroke="url(#paint15_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1336.7 682.587C1536.64 1033.54 1626.13 1480.72 1556.73 1783.25C1486.97 2087.33 1268.48 2193.94 1019.97 2046.65C770.502 1898.76 531.85 1517.65 435.816 1113.07C340.149 709.956 400.566 351.43 584.688 229.96C765.718 110.549 1038.59 242.614 1256.41 555.157C1284.45 595.328 1311.31 638.001 1336.7 682.587Z" stroke="url(#paint16_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1359.36 692.151C1555.18 1048.32 1634.81 1497.79 1555.18 1798.34C1475.12 2100.5 1247.58 2201.15 996.27 2047.24C743.931 1892.66 509.106 1505.36 421.534 1098.35C334.257 692.813 406.228 336.053 598.885 219.512C788.232 105.031 1065.08 244.38 1280.4 562.588C1308.07 603.495 1334.49 646.903 1359.36 692.151Z" stroke="url(#paint17_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1382.32 702.304C1573.8 1063.55 1643.27 1515 1553.12 1813.27C1462.46 2113.16 1225.8 2207.7 971.765 2047.09C716.629 1885.81 485.999 1492.42 407.185 1083.12C328.665 675.523 412.483 320.823 613.751 209.506C811.56 100.101 1092.23 246.808 1304.76 570.754C1332.06 612.323 1358.04 656.394 1382.32 702.304Z" stroke="url(#paint18_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1405.73 713.12C1592.57 1079.37 1651.51 1532.51 1550.62 1828.28C1449.22 2125.59 1203.35 2213.81 946.599 2046.43C688.815 1878.38 462.6 1478.88 392.837 1067.67C323.442 658.087 419.329 305.741 629.281 199.868C835.626 95.8343 1120.05 249.972 1329.63 579.436C1356.49 621.815 1381.96 666.548 1405.73 713.12Z" stroke="url(#paint19_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1429.42 724.524C1611.33 1095.7 1659.53 1550.24 1547.6 1843.22C1435.16 2137.73 1180.02 2219.33 920.768 2045.1C660.407 1870.22 438.903 1464.82 378.559 1051.85C318.51 640.502 426.834 290.879 645.469 190.671C860.424 92.229 1148.53 253.944 1354.8 588.927C1381.37 631.967 1406.31 677.363 1429.42 724.524Z" stroke="url(#paint20_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1453.49 736.589C1630.25 1112.48 1667.19 1568.2 1544.15 1858C1420.45 2149.43 1155.96 2224.11 894.279 2043.04C631.49 1861.24 414.99 1450.04 364.36 1035.67C313.951 622.844 434.933 276.237 662.472 181.915C886.111 89.2121 1177.82 258.653 1380.63 599.006C1406.68 642.783 1431.04 688.84 1453.49 736.589Z" stroke="url(#paint21_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1477.91 749.245C1649.23 1129.77 1674.69 1586.22 1540.24 1872.72C1405.06 2160.69 1131.16 2228.3 867.12 2040.32C602.05 1851.53 390.848 1434.66 350.226 1019.11C309.752 605.04 443.612 261.818 680.129 173.603C912.525 86.9324 1207.69 264.098 1406.83 609.749C1432.36 654.261 1456.13 700.907 1477.91 749.245Z" stroke="url(#paint22_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1502.64 762.635C1668.29 1147.57 1681.84 1604.62 1535.69 1887.36C1388.8 2171.58 1105.41 2231.83 839.233 2036.86C571.956 1841.08 366.346 1418.69 336.101 1002.19C305.929 587.161 452.961 247.617 698.456 165.803C939.757 85.3863 1238.24 270.425 1433.32 621.299C1458.42 666.4 1481.6 713.708 1502.64 762.635Z" stroke="url(#paint23_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1527.74 776.614C1687.35 1165.89 1688.68 1623.08 1530.75 1901.78C1371.95 2182.02 1078.99 2234.63 810.753 2032.52C541.415 1829.6 341.767 1401.92 322.118 984.681C302.47 569.135 463.042 233.638 717.589 158.445C967.794 84.5771 1269.51 277.488 1460.4 633.439C1484.91 679.202 1507.43 727.172 1527.74 776.614Z" stroke="url(#paint24_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1553.05 791.255C1706.41 1184.66 1695.15 1641.77 1525.09 1916.13C1354.14 2191.96 1051.54 2236.76 781.463 2027.59C510.212 1817.54 316.745 1384.63 308.061 967.097C299.451 551.036 473.711 219.953 737.383 151.676C996.566 84.5034 1301.45 285.434 1487.78 646.461C1511.77 692.813 1533.62 741.298 1553.05 791.255Z" stroke="url(#paint25_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1578.73 806.632C1725.47 1204.01 1701.41 1660.61 1519.05 1930.33C1335.74 2201.52 1023.5 2238.16 751.66 2021.78C478.642 1804.52 291.725 1366.6 294.3 948.924C296.802 532.863 485.045 206.636 757.989 145.349C1026.3 85.1659 1334.05 294.19 1515.67 659.999C1539 707.087 1560.12 756.161 1578.73 806.632Z" stroke="url(#paint26_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1604.71 822.671C1744.6 1223.8 1707.22 1679.66 1512.36 1944.38C1316.46 2210.57 994.506 2238.82 721.046 2015.23C446.41 1790.76 266.409 1347.99 280.539 930.53C294.594 514.69 497.113 193.54 779.329 139.61C1056.76 86.6367 1367.31 303.827 1543.93 674.419C1566.59 722.021 1586.9 771.684 1604.71 822.671Z" stroke="url(#paint27_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1630.98 839.372C1763.74 1244.1 1712.74 1698.79 1505.14 1958.21C1296.44 2219.03 964.776 2238.68 689.845 2007.87C413.81 1776.12 240.874 1328.71 266.925 911.769C292.829 496.371 509.771 180.812 801.407 134.46C1088.04 88.9179 1401.24 314.349 1572.55 689.576C1594.56 737.767 1614.06 787.944 1630.98 839.372Z" stroke="url(#paint28_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1657.48 856.736C1782.8 1264.92 1717.82 1717.99 1497.27 1971.82C1275.55 2226.98 934.089 2237.65 657.833 1999.63C380.474 1760.59 215.118 1308.63 253.385 892.566C291.504 478.051 523.238 168.378 824.22 129.898C1120.05 92.0815 1435.82 325.826 1601.55 705.468C1622.89 754.247 1641.58 804.866 1657.48 856.736Z" stroke="url(#paint29_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1684.26 874.91C1801.78 1286.26 1722.53 1737.49 1488.88 1985.29C1253.98 2234.41 902.667 2235.95 625.307 1990.59C346.77 1744.19 189.289 1288.03 240.065 873.07C290.695 459.732 537.368 156.386 847.842 125.927C1152.94 96.0556 1471.07 338.188 1630.98 722.096C1651.51 771.465 1669.32 822.599 1684.26 874.91Z" stroke="url(#paint30_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1711.27 893.67C1820.77 1308.04 1726.87 1756.99 1479.83 1998.38C1231.54 2241.1 870.434 2233.23 592.045 1980.5C312.551 1726.75 163.238 1266.47 226.893 853.131C290.327 441.337 552.233 144.687 872.127 122.615C1186.58 100.91 1506.91 351.503 1660.64 739.532C1680.44 789.416 1697.36 841.065 1711.27 893.67Z" stroke="url(#paint31_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1738.5 913.241C1839.61 1330.41 1730.7 1776.63 1470.19 2011.41C1208.28 2247.36 837.319 2229.85 558.193 1969.76C277.89 1708.58 137.113 1244.47 213.941 832.972C290.474 423.018 567.834 133.504 897.295 119.967C1221.09 106.65 1543.41 365.777 1690.74 757.78C1709.72 808.178 1725.69 860.268 1738.5 913.241Z" stroke="url(#paint32_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1766.02 933.474C1858.45 1353.21 1734.23 1796.35 1459.96 2024.06C1184.22 2252.95 803.394 2225.51 523.68 1957.99C242.788 1689.37 110.842 1221.74 201.136 812.371C291.137 404.624 584.244 122.689 923.198 117.98C1256.41 113.345 1580.57 381.007 1721.2 776.835C1739.31 827.748 1754.25 880.206 1766.02 933.474Z" stroke="url(#paint33_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1793.69 954.516C1877.14 1376.54 1737.24 1816.29 1449.07 2036.49C1159.34 2257.88 768.73 2220.28 488.574 1945.41C207.241 1669.36 84.567 1198.34 188.623 791.549C292.311 386.304 601.314 112.314 949.908 116.655C1292.54 120.996 1618.32 397.193 1751.96 796.7C1769.18 848.054 1783.09 900.88 1793.69 954.516Z" stroke="url(#paint34_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1821.58 976.22C1895.68 1400.37 1739.82 1836.15 1437.51 2048.56C1133.59 2262.15 733.114 2214.03 452.737 1931.72C171.183 1648.32 58.076 1174.13 176.261 770.286C294.005 367.984 619.197 102.382 977.358 116.067C1329.41 129.604 1656.66 414.409 1783.02 817.3C1799.28 869.17 1812.16 922.364 1821.58 976.22Z" stroke="url(#paint35_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1849.62 998.66C1914.08 1424.65 1741.88 1856.09 1425.3 2060.33C1107.03 2265.68 696.764 2206.89 416.313 1917.16C134.759 1626.32 31.5131 1149.27 164.195 748.729C296.289 349.737 637.818 92.964 1005.62 116.287C1367.09 139.242 1695.67 432.729 1814.37 838.857C1829.68 891.094 1841.45 944.583 1849.62 998.66Z" stroke="url(#paint36_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1877.8 1021.91C1932.33 1449.45 1743.43 1876.1 1412.42 2071.81C1079.65 2268.55 659.526 2198.8 379.297 1901.71C97.8897 1603.36 4.94593 1123.73 152.346 726.877C299.084 331.564 657.245 83.9876 1034.61 117.169C1405.5 149.763 1735.11 451.931 1846.01 861.149C1860.29 913.755 1870.89 967.537 1877.8 1021.91Z" stroke="url(#paint37_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1906.21 1045.82C1950.51 1474.68 1744.53 1896.12 1398.88 2082.92C1051.39 2270.68 621.478 2189.68 341.69 1885.15C60.6513 1579.38 -21.622 1097.47 140.717 704.732C302.54 313.465 677.48 75.6009 1064.41 118.862C1444.73 161.388 1775.22 472.312 1877.95 884.326C1891.12 937.299 1900.54 991.376 1906.21 1045.82Z" stroke="url(#paint38_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1934.69 1070.54C1968.39 1500.43 1745.05 1916.2 1384.68 2093.66C1022.32 2272.08 582.699 2179.52 303.426 1867.64C23.0499 1554.44 -48.3321 1070.47 129.387 682.218C306.517 295.514 698.456 67.7286 1095.03 121.364C1484.76 174.043 1815.91 493.722 1910.11 908.385C1922.18 961.652 1930.42 1015.95 1934.69 1070.54Z" stroke="url(#paint39_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1963.32 1096C1986.13 1526.63 1745.12 1936.29 1369.82 2104.04C992.449 2272.67 543.11 2168.41 264.721 1849.1C-14.9201 1528.54 -74.8957 1042.8 118.498 659.484C311.156 277.635 720.314 60.4446 1126.46 124.675C1525.61 187.801 1857.13 516.235 1942.56 933.253C1953.46 986.815 1960.37 1041.33 1963.32 1096Z" stroke="url(#paint40_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M1992.02 1122.26C2003.57 1553.33 1744.61 1956.37 1354.14 2114.04C961.613 2272.52 502.634 2156.2 225.275 1829.6C-53.2619 1501.61 -101.537 1014.48 107.826 636.455C316.379 259.904 742.905 53.7497 1158.61 128.795C1567.11 202.59 1898.85 539.779 1975.09 958.93C1984.88 1012.79 1990.54 1067.45 1992.02 1122.26Z" stroke="url(#paint41_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
<path opacity="0.26" d="M2020.79 1149.2C2020.79 1580.41 1743.5 1976.39 1337.88 2123.46C930.117 2271.35 461.498 2142.81 185.39 1808.86C-91.8961 1473.66 -128.102 985.346 97.5236 613.136C322.193 242.249 766.306 47.6461 1191.51 133.801C1609.42 218.558 1941.02 564.503 2007.91 985.493C2016.52 1039.64 2020.79 1094.46 2020.79 1149.2Z" stroke="url(#paint42_linear)" stroke-opacity="0.5" stroke-miterlimit="10"/>
</g>
</g>
<defs>
<linearGradient id="paint0_linear" x1="985.633" y1="325.888" x2="985.633" y2="1974.38" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint1_linear" x1="985.644" y1="315.588" x2="985.644" y2="1984.65" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint2_linear" x1="985.667" y1="305.466" x2="985.667" y2="1994.71" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint3_linear" x1="985.745" y1="295.445" x2="985.745" y2="2004.63" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint4_linear" x1="985.811" y1="285.689" x2="985.811" y2="2014.24" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint5_linear" x1="985.893" y1="276.126" x2="985.893" y2="2023.79" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint6_linear" x1="985.932" y1="266.75" x2="985.932" y2="2033.08" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint7_linear" x1="985.934" y1="257.604" x2="985.934" y2="2042.09" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint8_linear" x1="985.952" y1="248.661" x2="985.952" y2="2051.01" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint9_linear" x1="985.954" y1="240.04" x2="985.954" y2="2059.54" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint10_linear" x1="985.935" y1="231.549" x2="985.935" y2="2067.84" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint11_linear" x1="985.894" y1="223.397" x2="985.894" y2="2075.94" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint12_linear" x1="985.853" y1="215.451" x2="985.853" y2="2083.67" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint13_linear" x1="985.78" y1="207.783" x2="985.78" y2="2091.22" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint14_linear" x1="985.655" y1="200.339" x2="985.655" y2="2098.48" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint15_linear" x1="985.579" y1="193.255" x2="985.579" y2="2105.48" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint16_linear" x1="985.428" y1="186.433" x2="985.428" y2="2112.18" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint17_linear" x1="985.288" y1="179.882" x2="985.288" y2="2118.57" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint18_linear" x1="985.116" y1="173.645" x2="985.116" y2="2124.54" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint19_linear" x1="984.964" y1="167.714" x2="984.964" y2="2130.35" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint20_linear" x1="984.807" y1="162.115" x2="984.807" y2="2135.86" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint21_linear" x1="984.669" y1="156.799" x2="984.669" y2="2140.99" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint22_linear" x1="984.581" y1="151.807" x2="984.581" y2="2145.83" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint23_linear" x1="984.47" y1="147.17" x2="984.47" y2="2150.37" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint24_linear" x1="984.413" y1="142.818" x2="984.413" y2="2154.54" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint25_linear" x1="984.278" y1="138.833" x2="984.278" y2="2158.44" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint26_linear" x1="984.286" y1="135.096" x2="984.286" y2="2162.04" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint27_linear" x1="984.263" y1="131.706" x2="984.263" y2="2165.35" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint28_linear" x1="984.295" y1="128.646" x2="984.295" y2="2168.32" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint29_linear" x1="984.293" y1="125.905" x2="984.293" y2="2170.95" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint30_linear" x1="984.353" y1="123.444" x2="984.353" y2="2173.38" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint31_linear" x1="984.425" y1="121.309" x2="984.425" y2="2175.36" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint32_linear" x1="984.506" y1="119.477" x2="984.506" y2="2177.26" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint33_linear" x1="984.625" y1="117.921" x2="984.625" y2="2178.83" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint34_linear" x1="984.762" y1="116.604" x2="984.762" y2="2180.17" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint35_linear" x1="984.858" y1="115.562" x2="984.858" y2="2181.23" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint36_linear" x1="984.956" y1="114.82" x2="984.956" y2="2182.09" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint37_linear" x1="985.041" y1="114.2" x2="985.041" y2="2182.8" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint38_linear" x1="985.161" y1="113.81" x2="985.161" y2="2183.32" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint39_linear" x1="985.213" y1="113.588" x2="985.213" y2="2183.7" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint40_linear" x1="985.322" y1="113.5" x2="985.322" y2="2183.99" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint41_linear" x1="985.357" y1="113.5" x2="985.357" y2="2184.22" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<linearGradient id="paint42_linear" x1="985.395" y1="113.578" x2="985.395" y2="2184.23" gradientUnits="userSpaceOnUse">
<stop stop-color="#999999"/>
<stop offset="1" stop-color="#7D92FF"/>
</linearGradient>
<clipPath id="clip0">
<rect width="1440" height="1505" fill="white"/>
</clipPath>
</defs>
</svg>

Before

Width:  |  Height:  |  Size: 26 KiB

View File

@ -1,4 +0,0 @@
<svg width="36" height="38" viewBox="0 0 36 38" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M19.4184 32.9995C20.2122 31.5062 20.6613 29.8061 20.6613 28.0024C20.6613 22.0566 15.7808 17.2365 9.76039 17.2365C6.93884 17.2365 4.36767 18.2952 2.43193 20.0323C2.21698 18.9773 2.10413 17.8851 2.10413 16.7666C2.10413 7.78278 9.38427 0.5 18.3648 0.5C27.3453 0.5 34.6254 7.78278 34.6254 16.7666C34.6254 19.283 34.0542 21.6659 33.0345 23.7928L35.874 33.0245C36.1106 33.7938 35.3879 34.5131 34.6198 34.273L25.4569 31.4085C23.6119 32.3044 21.5722 32.8617 19.4184 32.9995Z" fill="black"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M8.8203 37.1184C13.4204 37.1184 17.1495 33.4167 17.1495 28.8504C17.1495 24.2842 13.4204 20.5825 8.8203 20.5825C4.22021 20.5825 0.491095 24.2842 0.491095 28.8504C0.491095 30.1291 0.783484 31.3399 1.30551 32.4206L0.126628 36.2238C-0.111642 36.9925 0.609435 37.7134 1.37807 37.475L5.18834 36.293C6.28601 36.8218 7.51826 37.1184 8.8203 37.1184Z" fill="black"/>
</svg>

Before

Width:  |  Height:  |  Size: 1.0 KiB

View File

@ -1,3 +0,0 @@
<svg width="18" height="18" viewBox="0 0 18 18" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M6 7.5L9 10.5L12 7.5" stroke="black" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
</svg>

Before

Width:  |  Height:  |  Size: 217 B

View File

@ -1,4 +0,0 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M9.5 15H6C4.89543 15 4 14.1046 4 13V6C4 4.89543 4.89543 4 6 4H13C14.1046 4 15 4.89543 15 6V9.5" stroke="white" stroke-width="1.5"/>
<rect x="9" y="9" width="11" height="11" rx="2" stroke="white" stroke-width="1.5"/>
</svg>

Before

Width:  |  Height:  |  Size: 328 B

View File

@ -1,6 +0,0 @@
<svg width="64" height="64" viewBox="0 0 64 64" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M25.28 10.88C25.28 9.28942 26.5694 8 28.16 8C38.7639 8 47.36 16.5961 47.36 27.2C47.36 28.7906 46.0706 30.08 44.48 30.08C42.8894 30.08 41.6 28.7906 41.6 27.2C41.6 19.7773 35.5827 13.76 28.16 13.76C26.5694 13.76 25.28 12.4706 25.28 10.88Z" fill="#0DBD8B"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M38.72 53.12C38.72 54.7106 37.4306 56 35.84 56C25.2361 56 16.64 47.4039 16.64 36.8C16.64 35.2094 17.9294 33.92 19.52 33.92C21.1105 33.92 22.4 35.2094 22.4 36.8C22.4 44.2227 28.4173 50.24 35.84 50.24C37.4306 50.24 38.72 51.5294 38.72 53.12Z" fill="#0DBD8B"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M10.88 38.72C9.28942 38.72 8 37.4306 8 35.84C8 25.2361 16.5961 16.64 27.2 16.64C28.7906 16.64 30.08 17.9294 30.08 19.52C30.08 21.1105 28.7906 22.4 27.2 22.4C19.7773 22.4 13.76 28.4173 13.76 35.84C13.76 37.4306 12.4706 38.72 10.88 38.72Z" fill="#0DBD8B"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M53.12 25.28C54.7106 25.28 56 26.5694 56 28.16C56 38.7639 47.4039 47.36 36.8 47.36C35.2094 47.36 33.92 46.0706 33.92 44.48C33.92 42.8895 35.2094 41.6 36.8 41.6C44.2227 41.6 50.24 35.5827 50.24 28.16C50.24 26.5694 51.5294 25.28 53.12 25.28Z" fill="#0DBD8B"/>
</svg>

Before

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 26 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 8.6 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 18 KiB

View File

@ -1,3 +0,0 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M12.5285 6.54089L13.0273 6.04207C14.4052 4.66426 16.6259 4.65104 17.9874 6.01253C19.349 7.37402 19.3357 9.59466 17.9579 10.9725L15.5878 13.3425C14.21 14.7203 11.9893 14.7335 10.6277 13.372M11.4717 17.4589L10.9727 17.9579C9.59481 19.3357 7.37409 19.349 6.01256 17.9875C4.65102 16.626 4.66426 14.4053 6.04211 13.0275L8.41203 10.6577C9.78988 9.27988 12.0106 9.26665 13.3721 10.6281" stroke="white" stroke-width="2" stroke-linecap="round"/>
</svg>

Before

Width:  |  Height:  |  Size: 549 B

View File

@ -1,10 +0,0 @@
<svg width="66" height="28" viewBox="0 0 66 28" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M0.975097 0.640961V27.359H2.89517V28H0.238281V0H2.89517V0.640961H0.975097Z" fill="#2D2D2D"/>
<path d="M8.37266 9.11071V10.4628H8.4111C8.7712 9.94812 9.20494 9.54849 9.71306 9.26518C10.2208 8.98235 10.8029 8.84036 11.4586 8.84036C12.0885 8.84036 12.664 8.96298 13.1846 9.2074C13.7054 9.45223 14.1009 9.88336 14.371 10.5015C14.6665 10.0638 15.0683 9.67744 15.5764 9.34266C16.0842 9.00804 16.6852 8.84036 17.3797 8.84036C17.9069 8.84036 18.3953 8.90487 18.8457 9.03365C19.2955 9.16242 19.6812 9.36843 20.0027 9.65166C20.3239 9.93515 20.5746 10.3053 20.755 10.7621C20.9349 11.2196 21.025 11.7698 21.025 12.4139V19.0966H18.2861V13.4373C18.2861 13.1027 18.2734 12.7872 18.2475 12.4908C18.2216 12.1949 18.1512 11.9375 18.0354 11.7183C17.9196 11.4996 17.7491 11.3256 17.5243 11.1967C17.2993 11.0684 16.9938 11.0037 16.6081 11.0037C16.2225 11.0037 15.9106 11.0782 15.6727 11.2257C15.4346 11.374 15.2483 11.5673 15.1134 11.8052C14.9784 12.0438 14.8884 12.314 14.8435 12.6168C14.7982 12.9192 14.7759 13.2252 14.7759 13.5342V19.0966H12.0372V13.4955C12.0372 13.1994 12.0305 12.9063 12.0181 12.6168C12.005 12.3269 11.9506 12.0598 11.8539 11.815C11.7575 11.5706 11.5967 11.374 11.3717 11.2257C11.1467 11.0782 10.8156 11.0037 10.3785 11.0037C10.2497 11.0037 10.0794 11.0327 9.86746 11.0908C9.65528 11.1487 9.44941 11.2584 9.25027 11.4191C9.05071 11.5802 8.88053 11.812 8.73908 12.1143C8.59754 12.4171 8.5269 12.8128 8.5269 13.3021V19.0966H5.78833V9.11071H8.37266Z" fill="#2D2D2D"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M23.8596 9.55506C23.4223 9.81286 23.0621 10.1539 22.7794 10.5789C22.4962 11.0036 22.3357 11.5382 22.2974 12.1818H25.036C25.0872 11.6412 25.2676 11.2547 25.5761 11.023C25.8847 10.7912 26.309 10.6752 26.8491 10.6752C27.0931 10.6752 27.3215 10.6917 27.5338 10.7234C27.7458 10.7558 27.9322 10.8202 28.093 10.9167C28.2537 11.0132 28.3823 11.1487 28.4787 11.3224C28.5752 11.4962 28.6233 11.7313 28.6233 12.0273C28.6359 12.3108 28.5523 12.5264 28.3726 12.6745C28.1924 12.8227 27.9483 12.9352 27.6397 13.0124C27.3311 13.0897 26.9774 13.1477 26.5789 13.1864C26.1802 13.225 25.7753 13.2766 25.3638 13.3408C24.9523 13.4056 24.5441 13.4923 24.1392 13.6016C23.734 13.711 23.374 13.8752 23.0592 14.094C22.7437 14.3131 22.4867 14.6059 22.2876 14.9731C22.0879 15.3398 21.9884 15.8067 21.9884 16.3731C21.9884 16.8879 22.0753 17.3326 22.2489 17.706C22.4225 18.0793 22.6635 18.3884 22.9722 18.6327C23.2807 18.8778 23.6406 19.0579 24.0522 19.1739C24.4636 19.2896 24.9072 19.3476 25.3831 19.3476C26.0003 19.3476 26.6046 19.2572 27.1963 19.0774C27.7873 18.897 28.3018 18.5815 28.739 18.1308C28.7517 18.2983 28.7741 18.4625 28.8065 18.6232C28.8385 18.7843 28.8804 18.9418 28.932 19.0965H31.7091C31.5805 18.8906 31.4903 18.5815 31.4393 18.1693C31.3877 17.7573 31.362 17.3264 31.362 16.8751V11.6798C31.362 11.0745 31.227 10.5883 30.957 10.2214C30.6868 9.85459 30.3398 9.56787 29.9155 9.36194C29.4911 9.15619 29.0217 9.0176 28.5074 8.94652C27.9931 8.87594 27.4854 8.84036 26.9838 8.84036C26.431 8.84036 25.8812 8.89531 25.3348 9.00463C24.7882 9.1142 24.2966 9.2976 23.8596 9.55506ZM27.6302 14.5965C27.8293 14.5578 28.0159 14.5096 28.1893 14.4518C28.363 14.3937 28.5076 14.3134 28.6235 14.21V15.2339C28.6235 15.3884 28.6072 15.5944 28.5754 15.8519C28.5431 16.1098 28.4562 16.3636 28.3149 16.6146C28.1732 16.8659 27.9548 17.0817 27.6592 17.2618C27.3632 17.4423 26.9455 17.5322 26.4055 17.5322C26.1868 17.5322 25.9747 17.5129 25.7692 17.4742C25.5632 17.4358 25.3833 17.368 25.2291 17.2715C25.0748 17.175 24.9525 17.0431 24.8625 16.8754C24.7724 16.7084 24.7275 16.502 24.7275 16.2576C24.7275 16.0001 24.7724 15.7876 24.8625 15.6201C24.9525 15.4531 25.0713 15.3145 25.2194 15.205C25.3671 15.0956 25.5407 15.0089 25.7402 14.9441C25.9393 14.88 26.1418 14.828 26.3476 14.7897C26.566 14.7511 26.7846 14.719 27.0034 14.693C27.2219 14.6674 27.4308 14.6352 27.6302 14.5965Z" fill="#2D2D2D"/>
<path d="M38.5753 9.11176V10.9467H36.5696V15.8914C36.5696 16.3547 36.6467 16.6639 36.8011 16.8183C36.9552 16.9728 37.264 17.05 37.7268 17.05C37.8812 17.05 38.0288 17.0437 38.1704 17.0307C38.3117 17.0181 38.4468 16.9985 38.5753 16.9729V19.0975C38.3439 19.1362 38.0866 19.1618 37.8039 19.1749C37.521 19.1873 37.2446 19.194 36.9746 19.194C36.5503 19.194 36.1484 19.1649 35.7692 19.1069C35.3897 19.0491 35.0555 18.9367 34.7663 18.7691C34.4769 18.602 34.2486 18.3635 34.0816 18.0544C33.9143 17.7457 33.8308 17.3399 33.8308 16.8375V10.9467H32.1722V9.11176H33.8308V6.11795H36.5696V9.11176H38.5753Z" fill="#2D2D2D"/>
<path d="M42.4905 9.11088V10.9652H42.5291C42.6575 10.6559 42.831 10.3697 43.0498 10.1055C43.2684 9.84179 43.519 9.61625 43.8019 9.42953C44.0845 9.24315 44.3869 9.09824 44.7086 8.99491C45.0297 8.89207 45.3642 8.84036 45.7115 8.84036C45.8914 8.84036 46.0905 8.87278 46.3093 8.93705V11.4868C46.1806 11.4608 46.0263 11.4382 45.8465 11.4191C45.6663 11.3997 45.4928 11.39 45.3256 11.39C44.8242 11.39 44.3999 11.474 44.0529 11.6411C43.7057 11.8086 43.4262 12.0369 43.2139 12.3267C43.0018 12.6166 42.8504 12.9544 42.7605 13.3408C42.6706 13.727 42.6256 14.1457 42.6256 14.5963V19.0966H39.8869V9.11088H42.4905Z" fill="#2D2D2D"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M47.467 5.3064V7.56622H50.2059V5.3064H47.467ZM50.2054 19.0974V9.11166H47.4665V19.0974H50.2054Z" fill="#2D2D2D"/>
<path d="M51.6319 9.1106H54.7563L56.5115 11.7181L58.2473 9.1106H61.2753L57.9966 13.7849L61.6805 19.0964H58.5559L56.4729 15.9482L54.3898 19.0964H51.3235L54.9107 13.843L51.6319 9.1106Z" fill="#2D2D2D"/>
<path d="M65.0246 27.359V0.640961H63.1046V0H65.7616V28H63.1046V27.359H65.0246Z" fill="#2D2D2D"/>
</svg>

Before

Width:  |  Height:  |  Size: 5.5 KiB

View File

@ -1,155 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="1024"
height="1024"
viewBox="0 0 270.93333 270.93333"
version="1.1"
id="svg8"
inkscape:version="0.92.4 5da689c313, 2019-01-14"
sodipodi:docname="nheko.svg"
inkscape:export-filename="/home/nicolas/Dokumente/devel/open-source/nheko/resources/nheko-rebuild-round-corners.svg.png"
inkscape:export-xdpi="130.048"
inkscape:export-ydpi="130.048">
<defs
id="defs2" />
<sodipodi:namedview
id="base"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="0.35355339"
inkscape:cx="852.07808"
inkscape:cy="-60.410565"
inkscape:document-units="mm"
inkscape:current-layer="layer2"
showgrid="true"
inkscape:window-width="1920"
inkscape:window-height="1019"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="1"
showguides="true"
inkscape:snap-grids="true"
gridtolerance="10"
inkscape:snap-bbox="false"
inkscape:bbox-paths="true"
inkscape:snap-global="true"
inkscape:bbox-nodes="true"
inkscape:lockguides="false"
units="px">
<sodipodi:guide
position="0,0"
orientation="0,793.70079"
id="guide4797"
inkscape:locked="false" />
<sodipodi:guide
position="0,297"
orientation="1122.5197,0"
id="guide4803"
inkscape:locked="false" />
<inkscape:grid
type="axonomgrid"
id="grid4805"
units="px"
empspacing="2"
snapvisiblegridlinesonly="true"
spacingy="1.0583333" />
<sodipodi:guide
position="0,0"
orientation="0,755.90551"
id="guide4807"
inkscape:locked="false" />
<sodipodi:guide
position="200,0"
orientation="-755.90551,0"
id="guide4809"
inkscape:locked="false" />
<sodipodi:guide
position="200,200"
orientation="0,-755.90551"
id="guide4811"
inkscape:locked="false" />
<inkscape:grid
type="xygrid"
id="grid871"
empspacing="2"
color="#d43fff"
opacity="0.1254902"
empcolor="#cf3fff"
empopacity="0.25098039"
units="px"
spacingx="1.0583333"
spacingy="1.0583333"
enabled="false" />
</sodipodi:namedview>
<metadata
id="metadata5">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title />
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:groupmode="layer"
id="layer2"
inkscape:label="Logo"
style="display:inline"
transform="translate(0,-26.066668)">
<circle
id="path3792"
cx="135.46666"
cy="161.53333"
style="display:inline;fill:#333333;fill-opacity:1;stroke:none;stroke-width:0.3584221"
inkscape:transform-center-x="-57.929751"
inkscape:transform-center-y="532.03976"
inkscape:export-xdpi="96.000008"
inkscape:export-ydpi="96.000008"
r="135.46666" />
<path
style="fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.32663074px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
d="M 48.965212,110.73276 H 239.52342 c 4.88824,0 4.88824,0 0,8.46688 L 180.59519,221.2662 c -4.6188,8.00001 -4.6188,8.00001 -9.50702,8.00001 h -19.55294 c -4.88824,0 -4.88824,0 -0.26944,-8.00001 l 44.2635,-76.66608 h -29.41224 l -43.91123,76.19952 c -4.88823,8.46657 -4.88823,8.46657 -9.77646,8.46657 H 29.329398 l 49.299816,-84.66609 h -49.29982 z"
id="path4834"
inkscape:connector-curvature="0"
sodipodi:nodetypes="ccccccccccccccc"
inkscape:export-xdpi="96.000008"
inkscape:export-ydpi="96.000008" />
<path
style="fill:#c0def5;fill-opacity:1;stroke:none;stroke-width:0.3584221px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
d="M 97.764652,110.73276 H 127.09406 L 58.658797,229.26621 H 29.329398 Z"
id="path4836"
inkscape:connector-curvature="0"
sodipodi:nodetypes="ccccc"
inkscape:export-xdpi="96.000008"
inkscape:export-ydpi="96.000008" />
<path
style="fill:#87aade;fill-opacity:1;stroke:none;stroke-width:0.3584221px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
d="M 58.658797,229.26621 127.09406,110.73276 h 29.3294 L 87.988193,229.26621 Z"
id="path4838"
inkscape:connector-curvature="0"
sodipodi:nodetypes="ccccc"
inkscape:export-xdpi="96.000008"
inkscape:export-ydpi="96.000008" />
</g>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
style="display:inline"
transform="translate(0,-26.066668)" />
</svg>

Before

Width:  |  Height:  |  Size: 5.2 KiB

View File

@ -1,3 +0,0 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M17.6498 6.35001C16.0198 4.72001 13.7098 3.78001 11.1698 4.04001C7.49978 4.41001 4.47978 7.39001 4.06978 11.06C3.51978 15.91 7.26978 20 11.9998 20C15.1898 20 17.9298 18.13 19.2098 15.44C19.5298 14.77 19.0498 14 18.3098 14C17.9398 14 17.5898 14.2 17.4298 14.53C16.2998 16.96 13.5898 18.5 10.6298 17.84C8.40978 17.35 6.61978 15.54 6.14978 13.32C5.30978 9.44001 8.25978 6.00001 11.9998 6.00001C13.6598 6.00001 15.1398 6.69001 16.2198 7.78001L14.7098 9.29001C14.0798 9.92001 14.5198 11 15.4098 11H18.9998C19.5498 11 19.9998 10.55 19.9998 10V6.41001C19.9998 5.52001 18.9198 5.07001 18.2898 5.70001L17.6498 6.35001Z" fill="white"/>
</svg>

Before

Width:  |  Height:  |  Size: 738 B

View File

@ -1,3 +0,0 @@
<svg width="27" height="42" viewBox="0 0 27 42" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M13.5 0.771484C6.05481 0.771484 0 6.8263 0 14.2715C0 19.1178 2.5543 23.3676 6.39844 25.7465C6.49799 25.8206 6.6118 25.8733 6.7327 25.9013C6.8536 25.9293 6.97899 25.932 7.10099 25.9092C7.22299 25.8865 7.33896 25.8387 7.44162 25.769C7.54428 25.6993 7.63141 25.609 7.69753 25.504C7.76366 25.399 7.80735 25.2814 7.82587 25.1587C7.84438 25.036 7.83732 24.9108 7.80512 24.7909C7.77292 24.6711 7.71629 24.5592 7.63877 24.4623C7.56126 24.3653 7.46454 24.2855 7.35469 24.2277C4.02199 22.1654 1.8 18.4852 1.8 14.2715C1.8 7.79909 7.02761 2.57148 13.5 2.57148C19.9724 2.57148 25.2 7.79909 25.2 14.2715C25.2 18.4852 22.978 22.1654 19.6453 24.2277C19.5355 24.2855 19.4387 24.3653 19.3612 24.4623C19.2837 24.5592 19.2271 24.6711 19.1949 24.7909C19.1627 24.9108 19.1556 25.036 19.1741 25.1587C19.1926 25.2814 19.2363 25.399 19.3025 25.504C19.3686 25.609 19.4557 25.6993 19.5584 25.769C19.661 25.8387 19.777 25.8865 19.899 25.9092C20.021 25.932 20.1464 25.9293 20.2673 25.9013C20.3882 25.8733 20.502 25.8206 20.6016 25.7465C24.4457 23.3676 27 19.1178 27 14.2715C27 6.8263 20.9452 0.771484 13.5 0.771484ZM13.5 6.17148C9.03715 6.17148 5.4 9.80863 5.4 14.2715C5.4 16.7729 6.53578 19.0162 8.325 20.5011C8.41424 20.5855 8.51978 20.6506 8.63514 20.6926C8.75049 20.7346 8.87323 20.7526 8.99578 20.7454C9.11834 20.7383 9.23814 20.7061 9.3478 20.6509C9.45746 20.5957 9.55467 20.5187 9.63346 20.4245C9.71224 20.3304 9.77093 20.2211 9.80591 20.1034C9.8409 19.9857 9.85144 19.8621 9.83689 19.7402C9.82234 19.6183 9.78301 19.5007 9.72131 19.3945C9.65961 19.2884 9.57685 19.196 9.47812 19.123C8.08472 17.9666 7.2 16.2292 7.2 14.2715C7.2 10.7814 10.0099 7.97148 13.5 7.97148C16.9901 7.97148 19.8 10.7814 19.8 14.2715C19.8 16.2292 18.9153 17.9666 17.5219 19.123C17.4231 19.196 17.3404 19.2884 17.2787 19.3945C17.217 19.5007 17.1777 19.6183 17.1631 19.7402C17.1486 19.8621 17.1591 19.9857 17.1941 20.1034C17.2291 20.2211 17.2878 20.3304 17.3665 20.4245C17.4453 20.5187 17.5425 20.5957 17.6522 20.6509C17.7619 20.7061 17.8817 20.7383 18.0042 20.7454C18.1268 20.7526 18.2495 20.7346 18.3649 20.6926C18.4802 20.6506 18.5858 20.5855 18.675 20.5011C20.4642 19.0162 21.6 16.7729 21.6 14.2715C21.6 9.80863 17.9628 6.17148 13.5 6.17148ZM13.5 11.1215C11.771 11.1215 10.35 12.5424 10.35 14.2715C10.35 15.5207 11.0844 16.6165 12.15 17.1262L3.65625 40.048C3.61467 40.1588 3.59532 40.2768 3.59932 40.395C3.60331 40.5133 3.63057 40.6297 3.67953 40.7374C3.72849 40.8452 3.7982 40.9422 3.88468 41.023C3.97115 41.1038 4.0727 41.1668 4.18352 41.2084C4.29433 41.2499 4.41225 41.2692 4.53054 41.2652C4.64882 41.2612 4.76516 41.2339 4.8729 41.185C4.98064 41.136 5.07768 41.0662 5.15847 40.9797C5.23926 40.8932 5.30222 40.7917 5.34375 40.6809L7.12969 35.8715H19.8703L21.6562 40.6809C21.6978 40.7917 21.7607 40.8932 21.8415 40.9797C21.9223 41.0662 22.0194 41.136 22.1271 41.185C22.2348 41.2339 22.3512 41.2612 22.4695 41.2652C22.5877 41.2692 22.7057 41.2499 22.8165 41.2084C22.9273 41.1668 23.0288 41.1038 23.1153 41.023C23.2018 40.9422 23.2715 40.8452 23.3205 40.7374C23.3694 40.6297 23.3967 40.5133 23.4007 40.395C23.4047 40.2768 23.3853 40.1588 23.3438 40.048L14.85 17.1262C15.9156 16.6165 16.65 15.5207 16.65 14.2715C16.65 12.5424 15.229 11.1215 13.5 11.1215ZM13.5 12.9215C14.2562 12.9215 14.85 13.5152 14.85 14.2715C14.85 15.0277 14.2562 15.6215 13.5 15.6215C12.7438 15.6215 12.15 15.0277 12.15 14.2715C12.15 13.5152 12.7438 12.9215 13.5 12.9215ZM13.5 18.659L15.5391 24.1715H11.4609L13.5 18.659ZM13.8516 25.9715H16.2L16.9453 27.9684L13.8516 25.9715ZM10.7437 26.098L15.3984 29.1074L9.61875 29.1213L10.7437 26.0979V26.098ZM18.0422 30.9074L18.9844 33.4527L12.9797 30.9215L18.0422 30.9075V30.9074ZM8.87344 31.1324L15.8062 34.0715H7.79062L8.87344 31.1324Z" fill="black"/>
</svg>

Before

Width:  |  Height:  |  Size: 3.7 KiB

View File

@ -1,3 +0,0 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M5.5 12.5L8.84497 15.845C9.71398 16.714 11.1538 16.601 11.8767 15.6071L18.5 6.5" stroke="white" stroke-width="2" stroke-linecap="round"/>
</svg>

Before

Width:  |  Height:  |  Size: 250 B

View File

@ -1,170 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
inkscape:export-ydpi="797.66998"
inkscape:export-xdpi="797.66998"
inkscape:export-filename="/tmp/weechat512.png"
inkscape:version="1.0 (4035a4fb49, 2020-05-01)"
sodipodi:docname="weechat2.svg"
width="64"
height="64"
version="1.1"
id="svg8">
<sodipodi:namedview
inkscape:current-layer="svg8"
inkscape:window-maximized="1"
inkscape:window-y="42"
inkscape:window-x="148"
inkscape:cy="32"
inkscape:cx="11.643564"
inkscape:zoom="12.625"
showgrid="false"
id="namedview1443"
inkscape:window-height="968"
inkscape:window-width="1638"
inkscape:pageshadow="2"
inkscape:pageopacity="0"
guidetolerance="10"
gridtolerance="10"
objecttolerance="10"
borderopacity="1"
bordercolor="#666666"
pagecolor="#ffffff" />
<defs
id="defs2">
<linearGradient
id="linearGradient891">
<stop
style="stop-color:#0e16be;stop-opacity:1;"
offset="0"
id="stop887" />
<stop
style="stop-color:#63a4e1;stop-opacity:1"
offset="1"
id="stop889" />
</linearGradient>
<linearGradient
id="linearGradient883">
<stop
style="stop-color:#008726;stop-opacity:1;"
offset="0"
id="stop879" />
<stop
style="stop-color:#7ecc6f;stop-opacity:1"
offset="1"
id="stop881" />
</linearGradient>
<linearGradient
xlink:href="#linearGradient883"
id="linearGradient885"
x1="115.09375"
y1="42.862499"
x2="26.987501"
y2="42.862499"
gradientUnits="userSpaceOnUse" />
<linearGradient
xlink:href="#linearGradient891"
id="linearGradient893"
x1="60.854168"
y1="97.102089"
x2="60.854168"
y2="62.706253"
gradientUnits="userSpaceOnUse" />
<filter
style="color-interpolation-filters:sRGB"
id="filter5519">
<feFlood
flood-opacity="0.60422568746132421"
flood-color="rgb(0,0,0)"
result="flood"
id="feFlood5509" />
<feComposite
in="flood"
in2="SourceGraphic"
operator="in"
result="composite1"
id="feComposite5511" />
<feGaussianBlur
in="composite1"
stdDeviation="0.5"
result="blur"
id="feGaussianBlur5513" />
<feOffset
dx="1.9"
dy="1.4"
result="offset"
id="feOffset5515" />
<feComposite
in="SourceGraphic"
in2="offset"
operator="over"
result="fbSourceGraphic"
id="feComposite5517" />
</filter>
<filter
style="color-interpolation-filters:sRGB"
id="filter5531">
<feFlood
flood-opacity="0.60101983098700495"
flood-color="rgb(0,0,0)"
result="flood"
id="feFlood5521" />
<feComposite
in="flood"
in2="SourceGraphic"
operator="in"
result="composite1"
id="feComposite5523" />
<feGaussianBlur
in="composite1"
stdDeviation="0.5"
result="blur"
id="feGaussianBlur5525" />
<feOffset
dx="1.9"
dy="1.4"
result="offset"
id="feOffset5527" />
<feComposite
in="SourceGraphic"
in2="offset"
operator="over"
result="fbSourceGraphic"
id="feComposite5529" />
</filter>
</defs>
<metadata
id="metadata5">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
id="layer2"
style="display:inline"
transform="translate(-59.26667,-59.26667)">
<path
style="fill:url(#linearGradient885);fill-opacity:1;stroke:none;stroke-width:0.26458335px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;filter:url(#filter5519)"
d="m 121.70834,29.368751 -68.262505,1.5875 c -6.711747,0.156087 -13.464507,2.719336 -18.785501,7.005035 -5.124508,4.228038 -8.190215,10.463836 -9.7895,16.807465 l 24.341667,-1.058333 c 0.214884,-2.67862 1.733902,-5.109484 3.689147,-6.885223 1.76299,-1.5286 4.013062,-2.554657 6.365024,-2.639795 l 58.472918,-2.116649 z"
id="path195"
transform="matrix(0.47244092,0,0,0.47244092,59.26667,59.26667)" />
<path
style="fill:url(#linearGradient893);fill-opacity:1;stroke:none;stroke-width:0.26458335px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;filter:url(#filter5531)"
d="m 22.489584,61.647918 -10.31875,27.252084 c -1.362514,3.598435 -1.128016,8.11836 1.70141,10.913234 3.337143,3.296424 8.403518,3.779984 12.85067,3.374224 l 72.495838,-6.614541 16.139588,-47.625001 -20.637504,0.79375 -12.435417,35.189584 -11.112501,0.79375 12.435417,-35.454167 -22.225,1.058333 -13.229167,36.512501 -7.408314,0.264613 c -2.145162,0.07662 -3.30664,-2.908063 -2.645853,-4.76253 l 8.202083,-23.01875 z"
id="path32"
transform="matrix(0.47244092,0,0,0.47244092,59.26667,59.26667)" />
</g>
</svg>

Before

Width:  |  Height:  |  Size: 5.5 KiB

View File

@ -1,75 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
@import 'color-scheme';
// CSS reset
* {
box-sizing: border-box;
margin: 0;
}
// Styling for universal elements
html,
body,
#root {
height: 100%;
width: 100%;
font-family: Helvetica Neue, Helvetica, Arial, sans-serif;
font-style: normal;
font-size: 14px;
line-height: 24px;
color: $font;
overflow: auto;
}
h1 {
font-weight: bold;
font-size: 24px;
line-height: 32px;
text-align: left;
color: $foreground;
}
h4 {
text-align: left;
width: 100%;
}
a {
color: $link;
text-decoration: none;
}
hr {
border: 1px solid lighten($grey, 50);
margin: 0 40px;
}
// Suppress focus ring on form controls for mouse users
[data-whatintent='mouse'] *:focus {
outline: none;
}
.matrixIdentifier {
word-break: break-all;
}

View File

@ -1,12 +0,0 @@
import 'what-input';
import React from 'react';
import ReactDOM from 'react-dom';
import './index.scss';
import App from './App';
ReactDOM.render(
<React.StrictMode>
<App />
</React.StrictMode>,
document.getElementById('root')
);

View File

@ -1,29 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
.singleColumnLayout {
height: 100%;
padding: 0 1em;
margin: 0 auto;
max-width: 480px;
display: grid;
row-gap: 60px;
align-items: center;
}

View File

@ -1,29 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import React from 'react';
import './SingleColumn.scss';
interface IProps {
children?: React.ReactNode;
}
const SingleColumn: React.FC<IProps> = (props: IProps) => {
return <div className="singleColumnLayout">{props.children}</div>;
};
export default SingleColumn;

View File

@ -1,19 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
export * from './matrix-cypher';
export * from './utils';
export * from './schemas';

View File

@ -1,211 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the 'License');
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an 'AS IS' BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
/* eslint-disable import/first */
// eslint-disable-next-line @typescript-eslint/ban-ts-ignore
// @ts-ignore
import any from 'promise.any';
any.shim();
import VersionSchema from './schemas/VersionSchema';
import WellKnownSchema from './schemas/WellKnownSchema';
import UserSchema, { User } from './schemas/UserSchema';
import RoomAliasSchema, { RoomAlias } from './schemas/RoomAliasSchema';
import PublicRoomsSchema, {
PublicRooms,
Room,
} from './schemas/PublicRoomsSchema';
import EventSchema, { Event } from './schemas/EventSchema';
import GroupSchema, { Group } from './schemas/GroupSchema';
import { ensure } from './utils/promises';
import { prefixFetch, parseJSON } from './utils/fetch';
/*
* A client is a resolved homeserver name wrapped in a lambda'd fetch
*/
export type Client = (path: string) => Promise<Response>;
/*
* Confirms that the target homeserver is properly configured and operational
*/
export const validateHS = (host: string): Promise<string> =>
prefixFetch(host)('/_matrix/client/versions')
.then(parseJSON)
.then(VersionSchema.parse)
.then(() => host);
/*
* Discovers the correct domain name for the host according to the spec's
* discovery rules
*/
export const discoverServer = (host: string): Promise<string> =>
prefixFetch(host)('/.well-known/matrix/client')
.then((resp) =>
resp.ok
? resp
.json()
.then(WellKnownSchema.parse)
.then((content) => {
if (content === undefined) return host;
else if (
'm.homeserver' in content &&
content['m.homeserver']
) {
return content['m.homeserver'].base_url;
} else {
return host;
}
})
: ensure(resp.status === 404, () => host)
)
.then(validateHS);
/*
* Takes a hs domain and resolves it to it's current domain and returns a
* client
*/
export async function client(host: string): Promise<Client> {
return prefixFetch(await discoverServer(host));
}
/*
* Gets the details for a user
*/
export function getUserDetails(client: Client, userId: string): Promise<User> {
return client(`/_matrix/client/r0/profile/${userId}`)
.then(parseJSON)
.then(UserSchema.parse);
}
/*
* Gets the roomId of a room by resolving it's alias
*/
export function getRoomIdFromAlias(
client: Client,
roomAlias: string
): Promise<RoomAlias> {
const encodedRoomAlias = encodeURIComponent(roomAlias);
return client(`/_matrix/client/r0/directory/room/${encodedRoomAlias}`)
.then(parseJSON)
.then(RoomAliasSchema.parse);
}
/*
* Similar to getPubliRooms however id doesn't confirm the data returned from
* the hs is correct
*
* This is used because the room list can be huge and validating it all takes
* a long time
*/
export function getPublicRoomsUnsafe(client: Client): Promise<PublicRooms> {
// TODO: Do not assume server will return all results in one go
return client('/_matrix/client/r0/publicRooms').then(parseJSON);
}
/*
* Gets a list of all public rooms on a hs
*/
export function getPublicRooms(client: Client): Promise<PublicRooms> {
return getPublicRoomsUnsafe(client).then(PublicRoomsSchema.parse);
}
/*
* Searches the public rooms of a homeserver for the metadata of a particular
*/
export function searchPublicRooms(
client: Client,
roomId: string
): Promise<Room> {
// we use the unsage version here because the safe one is sloooow
return getPublicRoomsUnsafe(client).then((rooms) => {
const [match] = rooms.chunk.filter((chunk) => chunk.room_id === roomId);
return match !== undefined
? Promise.resolve(match)
: Promise.reject(
new Error(
`This server knowns no public room with id ${roomId}`
)
);
});
}
/*
* Gets the details of a room if that room is public
*/
export function getRoomDetails(
clients: Client[],
roomId: string
): Promise<Room> {
// eslint-disable-next-line @typescript-eslint/ban-ts-ignore
// @ts-ignore
return Promise.any(
clients.map((client) => searchPublicRooms(client, roomId))
);
}
/*
* Gets the details of an event from the homeserver
*/
export async function getEvent(
client: Client,
roomIdOrAlias: string,
eventId: string
): Promise<Event> {
return client(`/_matrix/client/r0/rooms/${roomIdOrAlias}/event/${eventId}`)
.then(parseJSON)
.then(EventSchema.parse);
}
/*
* Gets community information
*/
export async function getGroupDetails(
client: Client,
groupId: string
): Promise<Group> {
return client(`/_matrix/client/r0/groups/${groupId}/profile`)
.then(parseJSON)
.then(GroupSchema.parse);
}
export function getThumbnailURI(
clientURL: string,
mxcId: string,
height: number,
width: number,
): string {
const mxcParse = mxcId.match(/mxc:\/\/(?<server>.+)\/(?<mediaId>.+)/);
if (!mxcParse || !mxcParse.groups) {
throw new Error(`mxc invalid. mxc: ${mxcId}`);
}
// eslint-disable-next-line max-len
return `https://${clientURL}/_matrix/media/r0/thumbnail/${mxcParse.groups.server}/${mxcParse.groups.mediaId}?height=${height}&width=${width}&method=crop`;
}
/*
* Gets an mxc resource
*/
export function convertMXCtoMediaQuery(clientURL: string, mxc: string): string {
// mxc://matrix.org/EqMZYbAYhREvHXvYFyfxOlkf
const matches = mxc.match(/mxc:\/\/(.+)\/(.+)/);
if (!matches) {
throw new Error(`mxc invalid: ${JSON.stringify({ mxc })}`);
}
return `${clientURL}/_matrix/media/r0/download/${matches[1]}/${matches[2]}`;
}

View File

@ -1,30 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { object, string, TypeOf } from 'zod';
const EventSchema = object({
content: object({}).nonstrict(),
type: string(),
event_id: string(),
sender: string(),
origin_server_ts: string(),
unsigned: object({}).nonstrict().optional(),
room_id: string(),
}).nonstrict();
export type Event = TypeOf<typeof EventSchema>;
export default EventSchema;

View File

@ -1,27 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { object, string, TypeOf } from 'zod';
const GroupSchema = object({
name: string(),
avatar_url: string().optional(),
short_description: string().optional(),
long_description: string().optional(),
});
export type Group = TypeOf<typeof GroupSchema>;
export default GroupSchema;

View File

@ -1,41 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { object, array, string, boolean, number, TypeOf } from 'zod';
export const RoomSchema = object({
aliases: array(string()).optional(),
canonical_alias: string().optional(),
name: string().optional(),
num_joined_members: number(),
room_id: string(),
topic: string().optional(),
world_readable: boolean(),
guest_can_join: boolean(),
avatar_url: string().optional(),
}).nonstrict();
const PublicRoomsSchema = object({
chunk: array(RoomSchema),
next_batch: string().optional(),
prev_batch: string().optional(),
total_room_count_estimate: number().optional(),
}).nonstrict();
export type Room = TypeOf<typeof RoomSchema>;
export type PublicRooms = TypeOf<typeof PublicRoomsSchema>;
export default PublicRoomsSchema;

View File

@ -1,25 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { object, array, string, TypeOf } from 'zod';
const RoomAliasSchema = object({
room_id: string(),
servers: array(string()),
}).nonstrict();
export type RoomAlias = TypeOf<typeof RoomAliasSchema>;
export default RoomAliasSchema;

View File

@ -1,25 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { object, string, TypeOf } from 'zod';
const UserSchema = object({
avatar_url: string().optional(),
displayname: string().optional(),
}).nonstrict();
export type User = TypeOf<typeof UserSchema>;
export default UserSchema;

View File

@ -1,21 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { object, string, array } from 'zod';
export default object({
versions: array(string()),
}).nonstrict()

View File

@ -1,29 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
import { object, string, TypeOf } from 'zod';
const WellKnownSchema = object({
'm.homeserver': object({
base_url: string().url(),
}),
'm.identity_server': object({
base_url: string().url(),
}).optional(),
}).nonstrict();
export type WellKnown = TypeOf<typeof WellKnownSchema>;
export default WellKnownSchema;

View File

@ -1,24 +0,0 @@
/*
Copyright 2020 The Matrix.org Foundation C.I.C.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
export * from './EventSchema';
export * from './GroupSchema';
export * from './PublicRoomsSchema';
export * from './RoomAliasSchema';
export * from './UserSchema';
export * from './VersionSchema';
export * from './WellKnownSchema';
export * from './index';

Some files were not shown because too many files have changed in this diff Show More