Brand colours and icons on login screen
Diff
chartered-frontend/package.json | 4 ++++
chartered-frontend/yarn.lock | 33 +++++++++++++++++++++++++++++++++
chartered-frontend/src/pages/Login.tsx | 35 +++++++++++++++++++++++++++++++++++
3 files changed, 70 insertions(+), 2 deletions(-)
@@ -23,6 +23,10 @@
"typescript": "^4.4.2"
},
"dependencies": {
"@fortawesome/fontawesome-svg-core": "^1.2.36",
"@fortawesome/free-brands-svg-icons": "^5.15.4",
"@fortawesome/free-solid-svg-icons": "^5.15.4",
"@fortawesome/react-fontawesome": "^0.1.15",
"@types/node": "^16.10.1",
"bootstrap": "^5.1.1",
"lodash": "^4.17.21",
@@ -901,6 +901,39 @@
"@babel/helper-validator-identifier" "^7.14.9"
to-fast-properties "^2.0.0"
"@fortawesome/fontawesome-common-types@^0.2.36":
version "0.2.36"
resolved "https://registry.yarnpkg.com/@fortawesome/fontawesome-common-types/-/fontawesome-common-types-0.2.36.tgz#b44e52db3b6b20523e0c57ef8c42d315532cb903"
integrity sha512-a/7BiSgobHAgBWeN7N0w+lAhInrGxksn13uK7231n2m8EDPE3BMCl9NZLTGrj9ZXfCmC6LM0QLqXidIizVQ6yg==
"@fortawesome/fontawesome-svg-core@^1.2.36":
version "1.2.36"
resolved "https://registry.yarnpkg.com/@fortawesome/fontawesome-svg-core/-/fontawesome-svg-core-1.2.36.tgz#4f2ea6f778298e0c47c6524ce2e7fd58eb6930e3"
integrity sha512-YUcsLQKYb6DmaJjIHdDWpBIGCcyE/W+p/LMGvjQem55Mm2XWVAP5kWTMKWLv9lwpCVjpLxPyOMOyUocP1GxrtA==
dependencies:
"@fortawesome/fontawesome-common-types" "^0.2.36"
"@fortawesome/free-brands-svg-icons@^5.15.4":
version "5.15.4"
resolved "https://registry.yarnpkg.com/@fortawesome/free-brands-svg-icons/-/free-brands-svg-icons-5.15.4.tgz#ec8a44dd383bcdd58aa7d1c96f38251e6fec9733"
integrity sha512-f1witbwycL9cTENJegcmcZRYyawAFbm8+c6IirLmwbbpqz46wyjbQYLuxOc7weXFXfB7QR8/Vd2u5R3q6JYD9g==
dependencies:
"@fortawesome/fontawesome-common-types" "^0.2.36"
"@fortawesome/free-solid-svg-icons@^5.15.4":
version "5.15.4"
resolved "https://registry.yarnpkg.com/@fortawesome/free-solid-svg-icons/-/free-solid-svg-icons-5.15.4.tgz#2a68f3fc3ddda12e52645654142b9e4e8fbb6cc5"
integrity sha512-JLmQfz6tdtwxoihXLg6lT78BorrFyCf59SAwBM6qV/0zXyVeDygJVb3fk+j5Qat+Yvcxp1buLTY5iDh1ZSAQ8w==
dependencies:
"@fortawesome/fontawesome-common-types" "^0.2.36"
"@fortawesome/react-fontawesome@^0.1.15":
version "0.1.15"
resolved "https://registry.yarnpkg.com/@fortawesome/react-fontawesome/-/react-fontawesome-0.1.15.tgz#1450b838f905981d721bf07e14e3b52c0e9a91ed"
integrity sha512-/HFHdcoLESxxMkqZAcZ6RXDJ69pVApwdwRos/B2kiMWxDSAX2dFK8Er2/+rG+RsrzWB/dsAyjefLmemgmfE18g==
dependencies:
prop-types "^15.7.2"
"@hypnosphi/create-react-context@^0.3.1":
version "0.3.1"
resolved "https://registry.yarnpkg.com/@hypnosphi/create-react-context/-/create-react-context-0.3.1.tgz#f8bfebdc7665f5d426cba3753e0e9c7d3154d7c6"
@@ -1,9 +1,18 @@
import React = require("react");
import { useState, useEffect, useRef } from "react";
import { useLocation } from "react-router-dom";
import { useAuth } from "../useAuth";
import { useUnauthenticatedRequest } from "../util";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { IconName } from "@fortawesome/fontawesome-svg-core";
import {
faGithub,
faGitlab,
faGoogle,
IconDefinition,
} from "@fortawesome/free-brands-svg-icons";
import { faSignInAlt } from "@fortawesome/free-solid-svg-icons";
interface OAuthProviders {
providers: string[];
@@ -84,7 +93,7 @@
className="btn-close"
aria-label="Close"
onClick={() => setError("")}
></button>
/>
</div>
<form onSubmit={handleSubmit}>
@@ -126,6 +135,7 @@
disabled={!!loading}
showSpinner={loading === "password"}
text={`Login`}
icon={faSignInAlt}
onClick={handleSubmit}
/>
</form>
@@ -141,7 +151,11 @@
variant="dark"
disabled={!!loading}
showSpinner={loading === v}
text={`Login with ${v}`}
text={`Login with ${
v.charAt(0).toUpperCase() + v.slice(1)
}`}
icon={getIconForProvider(v)[0]}
background={getIconForProvider(v)[1]}
onClick={(evt) => {
evt.preventDefault();
handleOAuthLogin(v);
@@ -157,6 +171,17 @@
</div>
</div>
);
}
const BRANDS = {
default: [faSignInAlt, ""],
github: [faGithub, "#4078c0"],
gitlab: [faGitlab, "#6E49cb"],
google: [faGoogle, "#4285f4"],
};
function getIconForProvider(provider: string): [IconDefinition, string] {
return BRANDS[provider] || BRANDS["default"];
}
function ButtonOrSpinner({
@@ -165,6 +190,8 @@
disabled,
showSpinner,
text,
icon,
background,
onClick,
}: {
type: "button" | "submit";
@@ -172,6 +199,8 @@
disabled: boolean;
showSpinner: boolean;
text: string;
icon?: IconDefinition;
background?: string;
onClick: (evt) => any;
}) {
if (showSpinner) {
@@ -192,7 +221,9 @@
disabled={disabled}
onClick={onClick}
className={`btn btn-lg mt-2 btn-${variant} w-100`}
style={{ background, borderColor: background }}
>
{icon ? <FontAwesomeIcon icon={icon} className="me-2" /> : <></>}
{text}
</button>
);