diff --git a/landing/footer.css b/landing/footer.css
index dcd11b198..6613e4e63 100644
--- a/landing/footer.css
+++ b/landing/footer.css
@@ -1,92 +1,94 @@
/* ===== CSS FOOTER GRID LAYOUT ===== */
div.footer_grid {
max-width: 1920px;
margin-left: auto;
margin-right: auto;
display: grid;
column-gap: 6em;
padding-left: 60px;
padding-right: 60px;
padding-top: 20px;
padding-bottom: 40px;
transition-property: max-width;
transition: 300ms;
grid-template-columns: 1fr 1fr;
grid-template-areas: 'sitemap subscribe_updates';
}
div.footer_legal {
max-width: 1080px;
transition-property: max-width;
transition: 300ms;
}
div.sitemap {
grid-area: sitemap;
}
div.sitemap a {
display: block;
padding-bottom: 4px;
width: max-content;
}
div.inactive_tab a,
div.inactive_tab svg {
color: #8a8f98;
transition: 300ms;
}
div.inactive_tab:hover a,
div.inactive_tab:hover svg {
color: white;
transition: 300ms;
}
.active_tab a {
color: white;
transition: 300ms;
}
div.footer_logo a {
font-size: 24px;
font-weight: 500;
color: white;
padding-bottom: 8px;
}
div.footer_logo a:hover {
color: #7e57c2;
}
div.subscribe_updates {
grid-area: subscribe_updates;
align-self: center;
}
/* ===== VISUAL EFFECTS ===== */
div.footer_blur {
background-color: rgba(255, 255, 255, 0.125);
backdrop-filter: none;
+ position: sticky;
+ top: 100vh;
-webkit-backdrop-filter: blur(2px);
}
/* ===== SMALLEST BREAKPOINT ===== */
@media (max-width: 1099px) {
div.footer_grid {
padding-left: 3%;
padding-right: 3%;
grid-template-columns: minmax(auto, 540px);
justify-content: center;
grid-template-areas:
'subscribe_updates'
'sitemap';
}
div.footer_container {
padding-top: 5%;
}
div.sitemap {
padding-top: 60px;
grid-area: sitemap;
}
}
diff --git a/landing/header.react.js b/landing/header.react.js
index cd41ddb32..404e7c36b 100644
--- a/landing/header.react.js
+++ b/landing/header.react.js
@@ -1,82 +1,82 @@
// @flow
import { faTwitter, faGithub } from '@fortawesome/free-brands-svg-icons';
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import * as React from 'react';
import { Link } from 'react-router-dom';
import headerStyles from './header.css';
import type { LandingPageName } from './landing.react';
type HeaderProps = {
+isLegalPage: boolean,
+activePageName: LandingPageName,
};
function Header(props: HeaderProps): React.Node {
const { isLegalPage, activePageName } = props;
const headerStyle = isLegalPage
? `${headerStyles.header_grid} ${headerStyles.header_legal}`
: headerStyles.header_grid;
const onRequestAccess = React.useCallback(async (e: Event) => {
e.preventDefault();
window?.scrollTo(0, document.body?.scrollHeight);
document.getElementById('subscription-form')?.focus();
}, []);
return (
- <>
+
);
}
export default Header;
diff --git a/landing/landing.css b/landing/landing.css
index 29982b5e0..ca72bced2 100644
--- a/landing/landing.css
+++ b/landing/landing.css
@@ -1,494 +1,500 @@
/* ===== GENERAL PAGE STYLES ===== */
html {
background: radial-gradient(ellipse at bottom, #1f252e, #111827);
background-attachment: fixed;
font-family: 'IBM Plex Sans', sans-serif;
color: white;
word-break: break-word;
}
/* Override browser default to achieve edge-to-edge footer translucency effect */
body {
background-image: radial-gradient(
circle at top left,
#2d008888 0%,
#ffffff00 50%
);
margin: 0;
padding: 0;
}
+html,
+body,
+:global(div#react-root) {
+ height: 100%;
+}
+
a {
transition: 0.2s;
text-decoration: none;
}
.mono {
font-family: 'iA Writer Duo S', monospace;
}
.no_bottom_margin {
margin-bottom: 0;
}
@media screen and (-webkit-min-device-pixel-ratio: 0) and (min-resolution: 0.001dpcm) {
img {
image-rendering: -webkit-optimize-contrast !important;
}
}
@media not all and (min-resolution: 0.001dpcm) {
@supports (-webkit-appearance: none) and (stroke-color: transparent) {
img {
image-rendering: unset !important;
}
}
}
/* ===== TEXT STYLES ===== */
h1 {
font-size: 58px;
font-family: 'IBM Plex Sans', sans-serif;
}
h2 {
font-size: 50px;
font-family: 'IBM Plex Sans', sans-serif;
}
p,
li {
font-size: 24px;
line-height: 1.6em;
}
.app_landing_subheading {
font-weight: bold;
padding-inline: 4px;
}
span.app_landing_subheading {
background-color: #7e57c2;
}
p.app_landing_subheading {
font-family: 'iA Writer Duo S', monospace;
color: #7e57c2;
font-size: 32px;
padding-inline: 0px;
}
span.purple_accent {
color: #7e57c2;
}
/* ===== COMMON CSS GRID LAYOUT ===== */
div.body_grid,
div.app_landing_grid {
max-width: 1920px;
margin-left: auto;
margin-right: auto;
display: grid;
column-gap: 6em;
padding-left: 60px;
padding-right: 60px;
padding-top: 20px;
padding-bottom: 40px;
transition-property: max-width;
transition: 300ms;
}
/* ===== CSS BODY GRID LAYOUT ===== */
div.body_grid {
grid-template-columns: 1fr 1fr;
grid-template-areas:
'hero_copy hero_image'
'server_image server_copy'
'keyserver_company keyserver_company'
'keyserver_copy read_the_docs';
}
div.hero_copy {
grid-area: hero_copy;
align-self: center;
}
div.hero_image {
grid-area: hero_image;
object-fit: scale-down;
align-self: center;
}
div.server_image {
grid-area: server_image;
object-fit: scale-down;
align-self: center;
}
div.server_copy {
grid-area: server_copy;
align-self: center;
}
div.keyserver_company {
grid-area: keyserver_company;
text-align: center;
padding-top: 80px;
}
div.read_the_docs {
grid-area: read_the_docs;
align-self: center;
padding-bottom: 40px;
}
/* ===== APP LANDING GRID ===== */
div.app_landing_grid {
grid-template-columns: 2fr 3fr;
grid-template-areas: 'app_preview app_copy';
padding-top: 6vh;
padding-bottom: 8vh;
}
div.app_preview {
grid-area: app_preview;
justify-self: right;
}
div.app_preview img {
min-height: 560px;
max-height: 70vh;
max-width: 30vw;
object-fit: scale-down;
position: sticky;
top: 18vh;
left: 0;
}
div.app_copy {
grid-area: app_copy;
align-self: center;
justify-self: left;
}
.app_copy_wrapper {
height: 70vh;
display: flex;
flex-direction: column;
justify-content: center;
}
h1.cycling_header {
font-family: 'iA Writer Duo S', monospace;
font-size: 50px;
margin: 0;
white-space: pre-wrap;
}
/* ===== TILE GRID STYLING ===== */
div.tile_grid {
display: grid;
margin-right: 16%;
grid-template-columns: 1fr;
grid-template-rows: 1fr 1fr 1fr 1fr 1fr 1fr;
row-gap: 36vh;
margin-top: 32vh;
margin-bottom: 36vh;
grid-template-areas:
'tile_one'
'tile_two'
'tile_three'
'tile_four'
'tile_five'
'tile_six';
}
div.tile_grid > div {
display: flex;
padding: 36px;
border-radius: 8px;
background-color: #ebedee;
justify-content: center;
flex-direction: column;
transition: 300ms;
background-color: rgba(0, 0, 0, 0.35);
backdrop-filter: none;
-webkit-backdrop-filter: blur(2px);
transition: 300ms;
}
.active_card {
box-shadow: 0px 20px 50px rgba(126, 87, 194, 0.5);
}
div.tile_title_row {
display: flex;
flex-direction: row;
align-items: center;
align-content: center;
justify-content: flex-start;
margin-left: 20px;
margin-right: 20px;
padding-bottom: 20px;
}
div.tile_title_row > p.tile_title {
font-family: 'iA Writer Duo S', monospace;
font-weight: bold;
font-size: 36px;
transition: 300ms;
}
div.tile_grid > div p {
font-size: 22px;
color: white;
text-align: left;
margin-top: 0px;
margin-bottom: 0px;
margin-left: 20px;
margin-right: 20px;
transition: 300ms;
}
div.tile_one {
grid-area: tile_one;
}
div.tile_two {
grid-area: tile_two;
}
div.tile_three {
grid-area: tile_three;
}
div.tile_four {
grid-area: tile_four;
}
div.tile_five {
grid-area: tile_five;
}
div.tile_six {
grid-area: tile_six;
}
/* ===== LEGAL PAGE STYLING ===== */
div.legal_container {
max-width: 1080px;
margin-left: auto;
margin-right: auto;
padding-left: 60px;
padding-right: 60px;
}
div.legal_container h1 {
font-size: 42px;
}
div.legal_container h2 {
font-size: 38px;
}
div.legal_container p,
li {
font-size: 20px;
}
div.legal_container a {
color: #7e57c2;
}
div.legal_container a:hover {
color: #8c69c9;
}
/* ===== LAYOUT HACKS ===== */
div.body_grid > div + .starting_section {
padding-top: 80px;
}
.section {
padding-top: 80px;
}
/* ===== MEDIUM-LARGE BREAKPOINT ===== */
@media (max-width: 1699px) {
div.tile_title_row > p.tile_title {
font-size: 30px;
}
h1.cycling_header {
font-size: 44px;
}
}
/* ===== MEDIUM BREAKPOINT ===== */
@media (max-width: 1499px) {
div.body_grid {
padding-left: 60px;
padding-right: 60px;
}
h1 {
font-size: 42px;
}
h2 {
font-size: 38px;
}
p,
li {
font-size: 18px;
}
/* ===== LEGAL PAGE STYLING ===== */
div.legal_container h1 {
font-size: 28px;
}
div.legal_container h2 {
font-size: 24px;
}
div.legal_container p,
li {
font-size: 16px;
}
/* ===== APP LANDING GRID STYLING ===== */
div.tile_grid > div p {
font-size: 16px;
}
div.tile_title_row > p.tile_title {
font-size: 24px;
}
h1.cycling_header {
font-size: 38px;
}
}
/* ===== MEDIUM-SMALL BREAKPOINT ===== */
@media (max-width: 1299px) {
div.tile_title_row > p.tile_title {
font-size: 22px;
}
h1.cycling_header {
font-size: 30px;
}
}
/* ===== SMALLEST BREAKPOINT ===== */
@media (max-width: 1099px) {
/* ===== TEXT STYLES ===== */
h1 {
font-size: 28px;
}
h2 {
font-size: 24px;
}
p,
li {
font-size: 16px;
}
/* ===== COMMON CSS GRID LAYOUT ===== */
div.body_grid,
div.app_landing_grid {
padding-left: 3%;
padding-right: 3%;
grid-template-columns: minmax(auto, 540px);
justify-content: center;
padding-top: 0vh;
padding-bottom: 2vh;
}
/* ===== CSS BODY GRID LAYOUT ===== */
div.body_grid {
grid-template-areas:
'hero_image'
'hero_copy'
'server_image'
'server_copy'
'keyserver_company'
'keyserver_copy'
'read_the_docs';
}
div.keyserver_company {
text-align: left;
padding-top: 60px;
}
.keyserver_company > h1 {
font-size: 24px;
}
div.keyserver_copy {
padding-bottom: 0;
}
div.read_the_docs {
padding-top: 20px;
padding-bottom: 0;
}
/* ===== APP LANDING GRID LAYOUT ===== */
div.app_landing_grid {
grid-template-areas:
'app_preview'
'app_copy';
}
div.app_preview {
grid-area: app_preview;
align-self: center;
justify-self: center;
}
div.app_preview img {
max-height: 92vh;
max-width: 96vw;
}
.app_copy_wrapper {
height: 30vh;
}
div.app_copy {
grid-area: app_copy;
align-self: center;
justify-self: center;
}
h1.cycling_header {
font-family: 'iA Writer Duo S', monospace;
margin-top: 4vh;
font-size: 22px;
text-align: center;
}
.app_landing_subheading {
margin-bottom: 6vh;
text-align: center;
}
p.app_landing_subheading {
font-size: 18px;
}
div.tile_grid {
row-gap: 4vh;
padding-left: 3%;
padding-right: 3%;
grid-template-columns: minmax(auto, 540px);
justify-content: center;
}
div.app_copy div.tile_grid {
margin: 0;
}
div.tile_grid {
padding-bottom: 4vh;
}
div.tile_title_row > p.tile_title {
font-size: 20px;
}
.active_card {
box-shadow: none;
}
/* ===== LAYOUT HACKS ===== */
.section {
padding-top: 20px;
}
/* ===== LEGAL PAGE STYLING ===== */
div.legal_container {
max-width: 540px;
padding-left: 3%;
padding-right: 3%;
}
}
diff --git a/landing/landing.react.js b/landing/landing.react.js
index 9b0fbf69f..74df19f04 100644
--- a/landing/landing.react.js
+++ b/landing/landing.react.js
@@ -1,58 +1,58 @@
// @flow
import * as React from 'react';
import { useRouteMatch } from 'react-router-dom';
import AppLanding from './app-landing.react';
import Footer from './footer.react';
import Header from './header.react';
import Keyservers from './keyservers.react';
import Privacy from './privacy.react';
import Support from './support.react';
import Terms from './terms.react';
import useScrollToTopOnNavigate from './use-scroll-to-top-on-navigate.react';
export type LandingPageName =
| 'app'
| 'keyservers'
| 'privacy'
| 'terms'
| 'support';
type ActivePage = { name: LandingPageName, node: React.Node };
function Landing(): React.Node {
useScrollToTopOnNavigate();
const onPrivacy = useRouteMatch({ path: '/privacy' });
const onTerms = useRouteMatch({ path: '/terms' });
const onSupport = useRouteMatch({ path: '/support' });
const onKeyservers = useRouteMatch({ path: '/keyservers' });
const isLegalPage: boolean = React.useMemo(
() => !!(onPrivacy || onTerms || onSupport),
[onPrivacy, onSupport, onTerms],
);
const activePage: ActivePage = React.useMemo(() => {
if (onPrivacy) {
return { name: 'privacy', node: };
} else if (onTerms) {
return { name: 'terms', node: };
} else if (onSupport) {
return { name: 'support', node: };
} else if (onKeyservers) {
return { name: 'keyservers', node: };
} else {
return { name: 'app', node: };
}
}, [onKeyservers, onPrivacy, onSupport, onTerms]);
return (
-
+ <>
{activePage.node}
-
+ >
);
}
export default Landing;