feat(login): new login screen design #466

This commit is contained in:
Paul Makles 2021-12-25 23:18:37 +00:00 committed by GitHub
commit e4440f127a
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
13 changed files with 497 additions and 161 deletions

6
disabled-js.svg Normal file
View file

@ -0,0 +1,6 @@
<svg width="225" height="161" viewBox="0 0 225 161" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M69.6951 15.0002L20.9951 63.7002L69.6951 112.4L81.7601 100.325L45.1301 63.6952L81.7601 27.0652L69.6951 15.0002ZM132.955 112.39L181.655 63.6902L132.955 14.9902L120.89 27.0652L157.52 63.6952L120.89 100.325L132.955 112.39Z" fill="white"/>
<path d="M197 73H137C133.686 73 131 75.6863 131 79V139C131 142.314 133.686 145 137 145H197C200.314 145 203 142.314 203 139V79C203 75.6863 200.314 73 197 73Z" fill="#242424"/>
<path d="M191 79H143C139.686 79 137 81.6863 137 85V133C137 136.314 139.686 139 143 139H191C194.314 139 197 136.314 197 133V85C197 81.6863 194.314 79 191 79Z" fill="#D14F4F"/>
<path d="M181.5 95.5L153.5 123.5M153.5 95.5L181.5 123.5L153.5 95.5Z" stroke="white" stroke-width="5" stroke-linecap="round"/>
</svg>

After

Width:  |  Height:  |  Size: 828 B

View file

@ -72,9 +72,72 @@
media="(device-width: 1024px) and (device-height: 1366px) and (-webkit-device-pixel-ratio: 2)" media="(device-width: 1024px) and (device-height: 1366px) and (-webkit-device-pixel-ratio: 2)"
rel="apple-touch-startup-image" rel="apple-touch-startup-image"
/> />
<!--CSS for noscript screen-->
<style>
noscript {
background: #242424;
color: white;
position: fixed;
top: 0;
left: 0;
width: 100vw;
min-height: 100vh;
display: flex;
align-items: center;
justify-content: center;
user-select: none;
}
noscript > div {
padding: 12px;
display: flex;
font-family: "Open Sans", sans-serif;
flex-direction: column;
justify-content: center;
text-align: center;
}
noscript > div > h1 {
margin: 8px 0;
text-transform: uppercase;
font-size: 20px;
font-weight: 700;
}
noscript > div > p {
margin: 4px 0;
font-size: 14px;
}
noscript > div > a {
align-self: center;
margin-top: 20px;
padding: 8px 10px;
font-size: 14px;
width: 80px;
font-weight: 600;
background: #ed5151;
border-radius: 4px;
text-decoration: none;
color: white;
transition: background-color 0.2s;
}
noscript > div > a:hover {
background-color: #cf4848;
}
noscript > div > a:active {
background-color: #b64141;
}
</style>
</head> </head>
<body onContextMenu="return false" ontouchstart=""> <body onContextMenu="return false" ontouchstart="">
<div id="app"></div> <div id="app"></div>
<script type="module" src="/src/main.tsx"></script> <script type="module" src="/src/main.tsx"></script>
<noscript>
<div>
<img src="disabled-js.svg" />
<h1>Well, this is really awkward...</h1>
<p>Seems like your JavaScript is disabled.</p>
<p>You'll need to enable JavaScript to run this app.</p>
<a href="https://app.revolt.chat" target="_blank">Reload</a>
</div>
</noscript>
</body> </body>
</html> </html>

View file

@ -24,8 +24,9 @@ const PreloaderBase = styled.div`
width: 100%; width: 100%;
height: 100%; height: 100%;
display: grid; display: flex;
place-items: center; align-items: center;
justify-content: center;
.spinner { .spinner {
width: 58px; width: 58px;

View file

@ -46,7 +46,13 @@ $fontSize: 40px;
@while ($count > 0) { @while ($count > 0) {
$left: random(100); $left: random(100);
$deltaLeft: random(2 * $windNoise * 10) / 10 - $windNoise + $windSpeed; $deltaLeft: random(2 * $windNoise * 10) / 10 - $windNoise + $windSpeed;
/*$deltaLeft: math.div(random(2 * $windNoise * 10), 10) -
$windNoise +
$windSpeed;*/
$scale: 1 + (random(2 * $sizeNoise * 10) / 10 - $sizeNoise) / 100; $scale: 1 + (random(2 * $sizeNoise * 10) / 10 - $sizeNoise) / 100;
/*$scale: 1 +
(math.div(random(2 * $sizeNoise * 10), 10) - $sizeNoise) /
100;*/
.snowflake:nth-child(#{$count}) { .snowflake:nth-child(#{$count}) {
animation: animation-snowflake-#{$count} linear infinite; animation: animation-snowflake-#{$count} linear infinite;

View file

@ -1,126 +1,330 @@
// Pure CSS hand wave - by https://jarv.is/notes/css-waving-hand-emoji/
@keyframes wave-animation {
0% {
transform: rotate(0deg);
}
10% {
transform: rotate(14deg);
} /* The following five values can be played with to make the waving more or less extreme */
20% {
transform: rotate(-8deg);
}
30% {
transform: rotate(14deg);
}
40% {
transform: rotate(-4deg);
}
50% {
transform: rotate(10deg);
}
60% {
transform: rotate(0deg);
} /* Reset for the last half to pause */
100% {
transform: rotate(0deg);
}
}
/*@keyframes shrink {
0% {
background-size: 140% 140%;
}
10% {
background-size: 150% 150%;
}
100% {
background-size: 100% 100%;
}
}*/
.login { .login {
width: 100%; width: 100%;
height: 100%; height: 100%;
padding: 40px 35px;
display: flex; display: flex;
flex-direction: row; user-select: none;
background: url("/src/pages/login/background.jpg");
background-position: center;
background-repeat: no-repeat;
background-size: cover;
/*animation: shrink 5s normal forwards;*/
svg { .nav {
margin: auto; display: flex;
align-items: center;
.logo {
flex-grow: 1;
> img {
height: 24px;
}
} }
> div {
flex: 1;
} }
.content { .content {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
justify-content: space-between; justify-content: space-between;
flex-grow: 1;
}
.attribution { select {
color: var(--tertiary-background); max-width: 180px;
font-size: 12px; padding: 4px;
line-height: 12px; height: fit-content;
margin: 8px; background-color: rgba(36, 36, 36, 0.75);
border: 2px solid rgba(128, 128, 128, 0.15);
backdrop-filter: blur(20px);
font-size: 13px;
}
.middle {
display: flex; display: flex;
flex-direction: row; gap: 50px;
justify-content: space-between;
}
.modal { .loginQR {
display: flex; background-color: rgba(36, 36, 36, 0.75);
flex-direction: row; border: 2px solid rgba(128, 128, 128, 0.15);
border-radius: 8px;
justify-content: center; width: 330px;
} }
} }
.bg { .form {
background-size: cover !important; background-color: rgba(36, 36, 36, 0.75);
} border: 2px solid rgba(128, 128, 128, 0.15);
} backdrop-filter: blur(20px);
max-width: 360px;
max-height: 600px;
padding: 30px 25px;
border-radius: 8px;
margin-inline-start: 50px;
margin-top: 20px;
margin-bottom: 20px;
box-shadow: 0 2px 10px 0 rgb(0 0 0 / 20%);
.form { .captcha {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
font-size: 14px; gap: 10px;
font-size: 13px;
img { .title {
width: 260px; font-size: 20px;
margin: auto; font-weight: 600;
margin-bottom: 10px;
}
.checkbox {
display: flex;
align-items: center;
justify-content: center;
} }
a { a {
margin-top: 4px; cursor: pointer;
color: var(--accent);
}
}
.formModal {
display: flex;
flex-direction: column;
gap: 10px;
> span {
font-size: 13px;
word-break: keep-all;
a {
color: var(--accent);
white-space: nowrap;
}
}
.welcome {
font-size: 20px;
font-weight: 600;
margin-bottom: 10px;
.title {
display: flex;
align-items: center;
gap: 4px;
img {
animation-name: wave-animation;
animation-duration: 2.5s;
animation-iteration-count: 1;
transform-origin: 70% 70%;
height: 28px;
}
}
}
.subtitle {
display: flex;
align-items: center;
gap: 6px;
font-weight: 400;
font-size: 14px;
> div {
display: none;
margin-top: 1px;
font-size: 11px;
color: var(--secondary-foreground);
}
} }
form { form {
margin: 1em 0;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
gap: 10px;
> div {
margin: 0;
margin-bottom: -4px;
font-size: 12px;
color: var(--secondary-foreground);
}
input {
background: var(--secondary-background);
/*border: 2px solid rgba(128, 128, 128, 0.15);*/
}
button { button {
margin-top: 24px; padding: 8px;
background: var(--secondary-background);
margin-bottom: 15px;
}
}
} }
} }
.create {
text-align: center;
color: var(--tertiary-foreground);
a { a {
margin: 0 4px; color: white;
&:hover {
text-decoration: underline;
}
}
.bottom {
display: flex;
align-items: center;
justify-content: space-between;
font-size: 14px;
.links {
display: flex;
align-items: center;
gap: 15px;
.socials {
display: flex;
gap: 10px;
a {
transition: opacity 0.2s ease-in-out;
&:hover {
opacity: 0.7;
}
&:active {
opacity: 0.5;
}
}
}
.bullet {
height: 5px;
width: 5px;
background: grey;
border-radius: 50%;
}
.revolt {
display: flex;
gap: 10px;
a {
color: white !important;
}
}
} }
} }
} }
.success { .success {
display: flex; display: flex;
align-items: center;
flex-direction: column; flex-direction: column;
gap: 10px;
.note { .title {
color: var(--tertiary-foreground); font-size: 20px;
font-weight: 600;
} }
.mailProvider { .subtitle {
padding: 24px 0;
}
* {
margin: 0;
}
h1 {
font-weight: 400; font-weight: 400;
font-size: 14px;
margin-bottom: 10px;
} }
h2 { button {
font-weight: 300; width: 100%;
background: var(--secondary-background);
margin-bottom: 8px;
} }
}
.footer {
margin-top: 12px;
text-align: center;
color: var(--tertiary6);
a { a {
color: var(--tertiary-background) !important; font-size: 13px;
cursor: pointer; color: var(--accent);
margin: 0 2px;
&:hover {
color: var(--tertiary-foreground) !important;
}
} }
} }
@media only screen and (max-width: 768px) { @media only screen and (max-width: 768px) {
.bg { .login {
padding: 30px 20px;
background-image: unset;
background-color: var(--primary-background);
.content {
.nav {
.logo {
img {
height: 24px;
}
}
}
.bottom {
flex-direction: column;
.links {
flex-direction: column;
gap: 10px;
}
.bullet,
.attribution {
display: none; display: none;
} }
}
}
.form {
border: unset;
margin-inline-start: 0;
padding: 0;
max-width: unset;
box-shadow: unset;
}
.loginQR {
display: none;
}
}
} }

View file

@ -1,18 +1,17 @@
import { Twitter, Github, Mastodon } from "@styled-icons/boxicons-logos";
import { observer } from "mobx-react-lite"; import { observer } from "mobx-react-lite";
import { Helmet } from "react-helmet"; import { Helmet } from "react-helmet";
import { Route, Switch } from "react-router-dom"; import { Route, Switch } from "react-router-dom";
import { LIBRARY_VERSION } from "revolt.js";
import styles from "./Login.module.scss"; import styles from "./Login.module.scss";
import { Text } from "preact-i18n"; import { Text } from "preact-i18n";
import { useApplicationState } from "../../mobx/State"; import { useApplicationState } from "../../mobx/State";
import wideSVG from "../../../public/assets/wide.svg";
import LocaleSelector from "../../components/common/LocaleSelector"; import LocaleSelector from "../../components/common/LocaleSelector";
import background from "./background.jpg";
import { Titlebar } from "../../components/native/Titlebar"; import { Titlebar } from "../../components/native/Titlebar";
import { APP_VERSION } from "../../version";
import { FormCreate } from "./forms/FormCreate"; import { FormCreate } from "./forms/FormCreate";
import { FormLogin } from "./forms/FormLogin"; import { FormLogin } from "./forms/FormLogin";
import { FormReset, FormSendReset } from "./forms/FormReset"; import { FormReset, FormSendReset } from "./forms/FormReset";
@ -36,17 +35,20 @@ export default observer(() => {
/> />
</Helmet> </Helmet>
<div className={styles.content}> <div className={styles.content}>
<div className={styles.attribution}> <div className={styles.nav}>
<span> <a className={styles.logo}>
{/*TOFIX: Hide logo if on Desktop Native*/}
<img src={wideSVG} draggable={false} />
</a>
<LocaleSelector />
</div>
{/*<div className={styles.middle}>*/}
<div className={styles.form}>
{/*<div style={styles.version}>
API: <code>{configuration?.revolt ?? "???"}</code>{" "} API: <code>{configuration?.revolt ?? "???"}</code>{" "}
&middot; revolt.js: <code>{LIBRARY_VERSION}</code>{" "} &middot; revolt.js: <code>{LIBRARY_VERSION}</code>{" "}
&middot; App: <code>{APP_VERSION}</code> &middot; App: <code>{APP_VERSION}</code>
</span> </div>*/}
<span>
<LocaleSelector />
</span>
</div>
<div className={styles.modal}>
<Switch> <Switch>
<Route path="/login/create"> <Route path="/login/create">
<FormCreate /> <FormCreate />
@ -68,17 +70,58 @@ export default observer(() => {
</Route> </Route>
</Switch> </Switch>
</div> </div>
<div className={styles.attribution}> {/*<div className={styles.loginQR}></div>*/}
<span> {/*</div>*/}
<Text id="general.image_by" /> &lrm;@lorenzoherrera <div className={styles.bottom}>
&rlm;· unsplash.com <div className={styles.links}>
</span> <div className={styles.socials}>
<a
href="https://github.com/revoltchat"
target="_blank">
<Github size={24} />
</a>
<a
href="https://twitter.com/revoltchat"
target="_blank">
<Twitter size={24} />
</a>
<a
href="https://mastodon.social/@revoltchat"
target="_blank">
<Mastodon size={24} />
</a>
</div>
<div className={styles.bullet} />
<div className={styles.revolt}>
<a
href="https://revolt.chat/about"
target="_blank"
rel="noreferrer">
<Text id="general.about" />
</a>
<a
href="https://revolt.chat/terms"
target="_blank"
rel="noreferrer">
<Text id="general.tos" />
</a>
<a
href="https://revolt.chat/privacy"
target="_blank"
rel="noreferrer">
<Text id="general.privacy" />
</a>
</div>
</div>
<a
className={styles.attribution}
href="https://unsplash.com/@fakurian"
target="_blank">
<Text id="general.image_by" /> &lrm;@fakurian &rlm;·
unsplash.com
</a>
</div> </div>
</div> </div>
<div
className={styles.bg}
style={{ background: `url('${background}')` }}
/>
</div> </div>
</> </>
); );

Binary file not shown.

After

Width:  |  Height:  |  Size: 484 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 484 KiB

After

Width:  |  Height:  |  Size: 69 KiB

View file

@ -27,16 +27,18 @@ export const CaptchaBlock = observer((props: CaptchaProps) => {
return <Preloader type="spinner" />; return <Preloader type="spinner" />;
return ( return (
<div> <div className={styles.captcha}>
<div className={styles.title}>Are you human?</div>
<div className={styles.checkbox}>
<HCaptcha <HCaptcha
theme="dark"
sitekey={configuration.features.captcha.key} sitekey={configuration.features.captcha.key}
onVerify={(token) => props.onSuccess(token)} onVerify={(token) => props.onSuccess(token)}
/> />
<div className={styles.footer}> </div>
<a onClick={props.onCancel}> <a onClick={props.onCancel}>
<Text id="login.cancel" /> <Text id="login.cancel" />
</a> </a>
</div> </div>
</div>
); );
}); });

View file

@ -15,10 +15,10 @@ import wideSVG from "../../../../public/assets/wide.svg";
import Button from "../../../components/ui/Button"; import Button from "../../../components/ui/Button";
import Overline from "../../../components/ui/Overline"; import Overline from "../../../components/ui/Overline";
import Preloader from "../../../components/ui/Preloader"; import Preloader from "../../../components/ui/Preloader";
import WaveSVG from "../../settings/assets/wave.svg";
import FormField from "../FormField"; import FormField from "../FormField";
import { CaptchaBlock, CaptchaProps } from "./CaptchaBlock"; import { CaptchaBlock, CaptchaProps } from "./CaptchaBlock";
import { Legal } from "./Legal";
import { MailProvider } from "./MailProvider"; import { MailProvider } from "./MailProvider";
interface Props { interface Props {
@ -112,30 +112,28 @@ export function Form({ page, callback }: Props) {
<div className={styles.success}> <div className={styles.success}>
{configuration?.features.email ? ( {configuration?.features.email ? (
<> <>
<Envelope size={72} /> <div>
<h2> <div className={styles.title}>
<Text id="login.check_mail" /> <Text id="login.check_mail" />
</h2> </div>
<p className={styles.note}> <div className={styles.subtitle}>
<Text id="login.email_delay" /> <Text id="login.email_delay" />
</p> </div>
</div>
<MailProvider email={success} /> <MailProvider email={success} />
</> </>
) : ( ) : (
<> <>
<CheckCircle size={72} /> <div className={styles.title}>
<h1>
<Text id="login.successful_registration" /> <Text id="login.successful_registration" />
</h1> </div>
</> </>
)} )}
<span className={styles.footer}>
<Link to="/login"> <Link to="/login">
<a> <a>
<Text id="login.remembered" /> <Text id="login.remembered" />
</a> </a>
</Link> </Link>
</span>
</div> </div>
); );
} }
@ -144,8 +142,18 @@ export function Form({ page, callback }: Props) {
if (loading) return <Preloader type="spinner" />; if (loading) return <Preloader type="spinner" />;
return ( return (
<div className={styles.form}> <div className={styles.formModal}>
<img src={wideSVG} /> <div className={styles.welcome}>
<div className={styles.title}>
<img src={WaveSVG} draggable={false} />
<Text id="login.welcome" />
</div>
<div className={styles.subtitle}>
<Text id="login.subtitle" />
<div>(app.revolt.chat)</div>
</div>
</div>
{/* Preact / React typing incompatabilities */} {/* Preact / React typing incompatabilities */}
<form <form
onSubmit={ onSubmit={
@ -203,13 +211,13 @@ export function Form({ page, callback }: Props) {
{page === "create" && ( {page === "create" && (
<> <>
<span className={styles.create}> <span className={styles.create}>
<Text id="login.existing" /> <Text id="login.existing" />{" "}
<Link to="/login"> <Link to="/login">
<Text id="login.title" /> <Text id="login.title" />
</Link> </Link>
</span> </span>
<span className={styles.create}> <span className={styles.create}>
<Text id="login.missing_verification" /> <Text id="login.missing_verification" />{" "}
<Link to="/login/resend"> <Link to="/login/resend">
<Text id="login.resend" /> <Text id="login.resend" />
</Link> </Link>
@ -219,13 +227,13 @@ export function Form({ page, callback }: Props) {
{page === "login" && ( {page === "login" && (
<> <>
<span className={styles.create}> <span className={styles.create}>
<Text id="login.new" /> <Text id="login.new" />{" "}
<Link to="/login/create"> <Link to="/login/create">
<Text id="login.create" /> <Text id="login.create" />
</Link> </Link>
</span> </span>
<span className={styles.create}> <span className={styles.create}>
<Text id="login.forgot" /> <Text id="login.forgot" />{" "}
<Link to="/login/reset"> <Link to="/login/reset">
<Text id="login.reset" /> <Text id="login.reset" />
</Link> </Link>
@ -243,7 +251,6 @@ export function Form({ page, callback }: Props) {
</span> </span>
</> </>
)} )}
<Legal />
</div> </div>
); );
} }

View file

@ -1,29 +0,0 @@
import styles from "../Login.module.scss";
import { Text } from "preact-i18n";
export function Legal() {
return (
<span className={styles.footer}>
<a
href="https://revolt.chat/about"
target="_blank"
rel="noreferrer">
<Text id="general.about" />
</a>
&middot;
<a
href="https://revolt.chat/terms"
target="_blank"
rel="noreferrer">
<Text id="general.tos" />
</a>
&middot;
<a
href="https://revolt.chat/privacy"
target="_blank"
rel="noreferrer">
<Text id="general.privacy" />
</a>
</span>
);
}

View file

@ -0,0 +1,32 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg width="100%" height="100%" viewBox="0 0 32 32" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xml:space="preserve" xmlns:serif="http://www.serif.com/" style="fill-rule:evenodd;clip-rule:evenodd;stroke-linejoin:round;stroke-miterlimit:2;">
<metadata>
<rdf:RDF xmlns:cc="http://web.resource.org/cc/"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:dc = "http://purl.org/dc/elements/1.1/"
>
<rdf:Description rdf:about="">
<dc:title>Mutant Standard emoji 2020.04</dc:title>
</rdf:Description>
<cc:work rdf:about="">
<cc:license rdf:resource="http://creativecommons.org/licenses/by-nc-sa/4.0/"/>
<cc:attributionName>Dzuk</cc:attributionName>
<cc:attributionURL>http://mutant.tech/</cc:attributionURL>
</cc:work>
</rdf:RDF>
</metadata>
<rect id="wave--hmn-" serif:id="wave [hmn]" x="0" y="0" width="32" height="32" style="fill:none;"/>
<g id="outline">
<path d="M17.788,2.366c0.095,-0.129 0.202,-0.249 0.318,-0.359c0.225,-0.215 0.488,-0.391 0.772,-0.518c0.328,-0.147 0.681,-0.224 1.04,-0.238c0.047,-0.001 0.094,-0.001 0.14,0c0.501,0.014 0.99,0.157 1.414,0.426c0.158,0.1 0.304,0.217 0.439,0.346c0.706,0.693 1.417,1.382 2.098,2.1c0.265,0.287 0.47,0.623 0.595,0.994c0.115,0.339 0.163,0.7 0.14,1.058c-0.006,0.097 -0.017,0.195 -0.034,0.291l3.753,11.257c0.07,0.219 0.135,0.439 0.188,0.663c0.139,0.581 0.211,1.176 0.215,1.773c0.006,0.679 -0.077,1.358 -0.244,2.016c-0.212,0.835 -0.562,1.636 -1.031,2.359c-0.488,0.753 -1.106,1.407 -1.798,1.974c-1.357,1.112 -2.996,1.863 -4.723,2.164c-1.161,0.203 -2.356,0.203 -3.516,0c-1.149,-0.2 -2.261,-0.599 -3.276,-1.172c-0.183,-0.104 -0.361,-0.212 -0.537,-0.327c-0.03,0.444 -0.167,0.88 -0.405,1.262c-0.139,0.224 -0.31,0.428 -0.508,0.604c-0.213,0.19 -0.456,0.346 -0.718,0.462c-0.302,0.133 -0.627,0.211 -0.956,0.229c-0.315,0.018 -0.632,-0.019 -0.934,-0.108c-0.097,0.133 -0.205,0.257 -0.326,0.371c-0.225,0.215 -0.488,0.391 -0.772,0.518c-0.313,0.139 -0.651,0.22 -0.994,0.236c-0.357,0.017 -0.718,-0.037 -1.055,-0.158c-0.369,-0.132 -0.701,-0.343 -0.984,-0.612c-0.706,-0.693 -1.417,-1.382 -2.098,-2.1c-0.244,-0.264 -0.437,-0.569 -0.564,-0.906c-0.288,-0.764 -0.218,-1.635 0.189,-2.343c0.133,-0.229 0.298,-0.439 0.49,-0.621c0.082,-0.078 0.169,-0.151 0.26,-0.218c-0.065,-0.217 -0.103,-0.442 -0.113,-0.668c-0.012,-0.264 0.015,-0.529 0.078,-0.785c0.193,-0.774 0.726,-1.439 1.439,-1.796c0.24,-0.12 0.494,-0.201 0.755,-0.247c-0.386,-0.39 -0.771,-0.782 -1.154,-1.175c-0.312,-0.337 -0.556,-0.723 -0.708,-1.157c-0.12,-0.343 -0.181,-0.705 -0.181,-1.068c0,-0.363 0.061,-0.725 0.181,-1.067c0.176,-0.504 0.48,-0.957 0.87,-1.316c-0.117,-0.191 -0.215,-0.394 -0.29,-0.609c-0.12,-0.343 -0.181,-0.705 -0.181,-1.068c0,-0.31 0.045,-0.62 0.133,-0.917c0.247,-0.836 0.838,-1.549 1.609,-1.95c-0.005,-0.485 0.099,-0.97 0.308,-1.413c0.09,-0.19 0.198,-0.372 0.324,-0.541c0.076,-0.104 0.16,-0.199 0.246,-0.294c0.005,-0.004 0.014,-0.014 0.011,-0.011l-0.011,0.011c-0.001,0.002 -0.002,0.003 -0.002,0.001c0.005,-0.007 0.011,-0.013 0.017,-0.019c0.036,-0.036 0.073,-0.072 0.11,-0.107c0.095,-0.092 0.197,-0.177 0.303,-0.256c0.382,-0.282 0.824,-0.478 1.29,-0.571c0.156,-0.032 0.314,-0.049 0.473,-0.059c0.064,-0.002 0.129,-0.003 0.194,-0.003c0.327,-0.627 0.859,-1.142 1.505,-1.441c0.285,-0.132 0.588,-0.222 0.898,-0.267c0.136,-0.019 0.172,-0.019 0.308,-0.029c0.154,-0.004 0.154,-0.004 0.309,0c0.207,0.015 0.41,0.039 0.613,0.088c0.192,0.047 0.381,0.112 0.561,0.194c-0.004,-0.049 -0.007,-0.099 -0.009,-0.149c-0.03,-0.827 0.324,-1.64 0.95,-2.181c0.202,-0.174 0.43,-0.319 0.673,-0.429c0.333,-0.149 0.69,-0.226 1.054,-0.239c0.057,-0.001 0.057,-0.001 0.114,-0.001c0.191,0.005 0.38,0.026 0.567,0.068c0.06,0.014 0.12,0.03 0.178,0.048Z"/>
</g>
<g id="emoji">
<path d="M21.05,13.409c-0.306,-0.921 -0.235,-1.927 0.2,-2.796c0.435,-0.87 1.197,-1.531 2.12,-1.838c0.001,-0.001 0.001,-0.001 0.001,-0.001c0,0 1.903,5.707 3.191,9.573c0.71,2.13 0.156,4.478 -1.432,6.066c0,0.001 -0.001,0.001 -0.002,0.002c-1.542,1.543 -3.635,2.409 -5.816,2.409c-2.182,0 -4.274,-0.866 -5.817,-2.409l-6.652,-6.652c-0.48,-0.481 -0.48,-1.259 0,-1.74c0,0 0,0 0,0c0.481,-0.48 1.259,-0.48 1.74,0l4.349,4.35l0.58,-0.58l-6.089,-6.09c-0.48,-0.48 -0.48,-1.259 0,-1.739c0,0 0,0 0,-0.001c0.481,-0.48 1.259,-0.48 1.74,0l5.509,5.51l0.58,-0.58l-6.089,-6.089c-0.231,-0.231 -0.361,-0.544 -0.361,-0.87c0,-0.326 0.13,-0.639 0.361,-0.87c0,0 0,0 0,0c0.231,-0.231 0.544,-0.361 0.87,-0.361c0.326,0 0.639,0.13 0.869,0.361l5.51,5.509l0.58,-0.58l-4.93,-4.929c-0.48,-0.481 -0.48,-1.259 0,-1.74c0,0 0.001,0 0.001,0c0.48,-0.48 1.259,-0.48 1.739,0l5.458,5.458l1.421,2.218l0.951,0.153l-0.582,-1.744Z" style="fill:#FFC20B;"/>
<path d="M19.26,12.782l2.372,2.371l0.652,1.957c-0.289,0.082 -0.59,0.161 -0.881,0.252c-0.058,0.02 -0.114,0.041 -0.171,0.064c-0.221,0.095 -0.429,0.218 -0.614,0.373c-0.512,0.43 -0.824,1.07 -0.847,1.739c-0.009,0.263 0.028,0.522 0.102,0.775c0.228,0.717 0.475,1.428 0.713,2.142c0.033,0.112 0.048,0.224 0.031,0.341c-0.043,0.31 -0.282,0.566 -0.589,0.63c-0.075,0.016 -0.152,0.02 -0.228,0.013c-0.076,-0.008 -0.151,-0.027 -0.222,-0.058c-0.123,-0.053 -0.231,-0.139 -0.31,-0.248c-0.035,-0.047 -0.06,-0.097 -0.085,-0.15c-0.265,-0.704 -0.478,-1.428 -0.716,-2.142c-0.12,-0.377 -0.191,-0.764 -0.197,-1.159c-0.017,-1.024 0.383,-2.032 1.097,-2.766c0.298,-0.306 0.643,-0.553 1.021,-0.751l-1.128,-3.383Z" style="fill:#CE8D15;"/>
<path d="M6.03,25.251c0.182,0.01 0.348,0.079 0.483,0.202c0.695,0.672 1.401,1.336 2.051,2.052c0.068,0.081 0.121,0.172 0.153,0.274c0.028,0.093 0.039,0.191 0.03,0.288c-0.008,0.088 -0.032,0.176 -0.07,0.256c-0.032,0.066 -0.073,0.127 -0.122,0.181c-0.193,0.213 -0.501,0.298 -0.776,0.213c-0.11,-0.034 -0.207,-0.093 -0.292,-0.17c-0.695,-0.672 -1.401,-1.336 -2.051,-2.052c-0.068,-0.081 -0.121,-0.172 -0.153,-0.274c-0.021,-0.069 -0.032,-0.142 -0.033,-0.215c-0.002,-0.28 0.157,-0.543 0.405,-0.672c0.102,-0.053 0.213,-0.079 0.327,-0.084c0.024,0 0.024,0 0.048,0.001Zm1.011,-3c0.175,0.014 0.331,0.079 0.464,0.194c1.379,1.313 2.729,2.658 4.048,4.033c0.083,0.095 0.145,0.204 0.175,0.328c0.084,0.341 -0.088,0.704 -0.405,0.855c-0.082,0.04 -0.171,0.064 -0.262,0.071c-0.091,0.008 -0.183,-0.002 -0.27,-0.027c-0.111,-0.032 -0.209,-0.09 -0.296,-0.165c-1.379,-1.314 -2.729,-2.659 -4.048,-4.033c-0.076,-0.087 -0.134,-0.184 -0.166,-0.295c-0.096,-0.325 0.044,-0.683 0.335,-0.856c0.09,-0.054 0.187,-0.085 0.289,-0.1c0.046,-0.005 0.09,-0.006 0.136,-0.005Zm9.981,-18.001c0.184,0.009 0.349,0.077 0.487,0.199c1.034,0.994 2.048,2.008 3.042,3.042c0.08,0.09 0.14,0.194 0.172,0.31c0.072,0.263 -0.007,0.551 -0.203,0.74c-0.058,0.055 -0.124,0.101 -0.196,0.135c-0.08,0.039 -0.168,0.063 -0.257,0.071c-0.099,0.009 -0.2,-0.002 -0.294,-0.032c-0.106,-0.034 -0.199,-0.091 -0.282,-0.164c-1.034,-0.994 -2.048,-2.008 -3.042,-3.042c-0.073,-0.083 -0.13,-0.176 -0.164,-0.282c-0.105,-0.33 0.038,-0.701 0.338,-0.875c0.104,-0.061 0.22,-0.093 0.34,-0.101c0.03,-0.001 0.029,-0.001 0.059,-0.001Zm3.008,-0.999c0.182,0.01 0.348,0.079 0.483,0.202c0.695,0.672 1.401,1.336 2.051,2.052c0.073,0.087 0.129,0.186 0.159,0.297c0.02,0.07 0.029,0.143 0.027,0.216c-0.007,0.288 -0.185,0.553 -0.449,0.669c-0.082,0.036 -0.17,0.057 -0.259,0.062c-0.097,0.005 -0.195,-0.008 -0.286,-0.04c-0.101,-0.035 -0.19,-0.091 -0.269,-0.162c-0.695,-0.672 -1.401,-1.336 -2.051,-2.052c-0.068,-0.081 -0.121,-0.172 -0.153,-0.274c-0.082,-0.267 -0.006,-0.565 0.195,-0.76c0.053,-0.051 0.112,-0.094 0.177,-0.127c0.102,-0.053 0.213,-0.079 0.327,-0.084c0.024,0 0.024,0 0.048,0.001Z" style="fill:#565656;"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 7.5 KiB

View file

@ -126,6 +126,7 @@ export const Overview = observer(({ server }: Props) => {
alignItems: "center", alignItems: "center",
}}> }}>
<span style={{ flexShrink: "0", flex: `25%` }}>{i18n}</span> <span style={{ flexShrink: "0", flex: `25%` }}>{i18n}</span>
<span>Sends a message when someone joins your server</span>
<ComboBox <ComboBox
value={ value={
systemMessages?.[ systemMessages?.[