Improved homepage 🙏

This commit is contained in:
Tom Moor 2018-07-11 20:23:36 -07:00
parent 95c4574549
commit 19a328ebeb
10 changed files with 209 additions and 104 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 52 KiB

After

Width:  |  Height:  |  Size: 253 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 124 KiB

After

Width:  |  Height:  |  Size: 400 KiB

View File

@ -6,12 +6,12 @@ import Grid from 'styled-components-grid';
import breakpoint from 'styled-components-breakpoint'; import breakpoint from 'styled-components-breakpoint';
import Notice from '../../shared/components/Notice'; import Notice from '../../shared/components/Notice';
import Hero from './components/Hero'; import Hero from './components/Hero';
import Centered from './components/Centered';
import SigninButtons from './components/SigninButtons'; import SigninButtons from './components/SigninButtons';
import { import SlackLogo from '../../shared/components/SlackLogo';
developers, import GithubLogo from '../../shared/components/GithubLogo';
githubUrl, import Flex from '../../shared/components/Flex';
slackAppStoreUrl, import { githubUrl, slackAppStoreUrl } from '../../shared/utils/routeHelpers';
} from '../../shared/utils/routeHelpers';
type Props = { type Props = {
notice?: 'google-hd' | 'auth-error' | 'hd-not-allowed', notice?: 'google-hd' | 'auth-error' | 'hd-not-allowed',
@ -55,77 +55,107 @@ function Home(props: Props) {
</Notice> </Notice>
)} )}
</Hero> </Hero>
<Features reverse={{ mobile: true, tablet: false, desktop: false }}> <Mask>
<Grid.Unit size={{ desktop: 1 / 3, tablet: 1 / 2 }}> <Features>
<Feature> <Centered>
<h2>Blazing Fast Wiki</h2> <Grid reverse={{ mobile: true, tablet: false, desktop: false }}>
<Grid.Unit size={{ tablet: 1 / 3 }}>
<Feature>
<h2>Improve Communication</h2>
<p>
Easily structure your teams information in one central,
structured location. No more hunting through folders or
scanning pages of search results and chat conversations.
</p>
</Feature>
<Feature>
<h2>Safe &amp; Secure</h2>
<p>
Outline provides a secure place for your teams
documentation on our hosted platform, stored in portable
Markdown format. Or, you can run your own copy it's open
source!
</p>
</Feature>
</Grid.Unit>
<Feature size={{ tablet: 2 / 3 }}>
<Screenshot
srcset="screenshot.png, screenshot@2x.png 2x"
src="/screenshot@2x.png"
alt="Outline Screenshot"
/>
</Feature>
</Grid>
</Centered>
</Features>
</Mask>
<Centered>
<Grid>
<Feature size={{ desktop: 1 / 3 }}>
<h2>Blazing Fast</h2>
<p> <p>
Outline is fast, really fast. Weve worked hard to ensure Outline is fast, really fast. Weve worked hard to ensure
millisecond response times, documents load instantly, search is millisecond response times documents load instantly, search is
speedy and navigating the UI is delightful. speedy and navigating the UI is delightful.
</p> </p>
</Feature> </Feature>
<Feature> <Feature size={{ desktop: 1 / 3 }} />
<h2># Markdown Support</h2> <Feature size={{ desktop: 1 / 3 }}>
<h2>Markdown Support</h2>
<p> <p>
Documents are stored in plain Markdown making editing, import Documents are stored in plain Markdown making editing, import
and export painless. Shortcuts are also built right into the and export painless. Shortcuts are also built right into the
editor so you can easily format using{' '} editor so you can easily format using **markdown syntax** if you
<strong>**markdown syntax**</strong> if you like. like.
</p> </p>
</Feature> </Feature>
</Grid.Unit> <Feature size={{ desktop: 1 / 3 }}>
<Feature size={{ desktop: 2 / 3, tablet: 1 / 2 }}> <h2>
<Screenshot <SlackLogo fill="#000" size={30} />&nbsp;Slack &amp; API
srcset="screenshot.png, screenshot@2x.png 2x" </h2>
src="/screenshot@2x.png" <p>
alt="Outline Screenshot" Get Slack notifications about changes and search Outline
/> directly within Slack using the{' '}
</Feature> <code>/outline &lt;keyword&gt;</code> command. Access your
</Features> information programatically through the modern API.
<Highlights id="features"> </p>
<Feature size={{ desktop: 1 / 3 }}> <p>
<h2>Slack Integration</h2> <a href={slackAppStoreUrl()}>Slack App</a>
<p> </p>
Get Slack notifications about newly updated documents. You can </Feature>
also search Outline directly within Slack using{' '} <Feature size={{ desktop: 1 / 3 }} />
<code>/outline &lt;keyword&gt;</code> command. <Feature size={{ desktop: 1 / 3 }}>
</p> <h2>
<p> <GithubLogo fill="#000" size={30} />&nbsp;Open Source
<a href={slackAppStoreUrl()}>Slack App</a> </h2>
</p> <p>
</Feature> Outline is open source, so the community can help improve it
<Feature size={{ desktop: 1 / 3 }}> too. You get new features, interface improvements, bug fixes,
<h2>Open Source</h2> and a transparent roadmap for free.
<p> </p>
Outline is open source, so the community can help improve it too. <p>
You get new features, interface improvements, bug fixes, and a <a href={githubUrl()}>GitHub</a>
transparent roadmap for free. </p>
</p> </Feature>
<p> </Grid>
<a href={githubUrl()}>GitHub</a> </Centered>
</p>
</Feature>
<Feature size={{ desktop: 1 / 3 }}>
<h2>Integrations &amp; API</h2>
<p>
All of Outlines functionality is available through the API.
Migrating Markdown documents or setting up automations is a breeze
with a few lines of code.
</p>
<p>
<a href={developers()}>Documentation</a>
</p>
</Feature>
</Highlights>
<Footer> <Footer>
<h2>Create an account</h2> <Centered>
<p> <Grid>
On the same page as us? Create a free account to give Outline a try. <Grid.Unit size={{ desktop: 1 / 3 }}>
</p> <h2>Create an account</h2>
<FooterCTA> <p>
<SigninButtons {...props} /> On the same page as us? Create a free account to give Outline
</FooterCTA> a try with your team.
</p>
</Grid.Unit>
<Grid.Unit size={{ desktop: 2 / 3 }}>
<Flex justify="center" align="center">
<SigninButtons {...props} />
</Flex>
</Grid.Unit>
</Grid>
</Centered>
</Footer> </Footer>
</Grid> </Grid>
</span> </span>
@ -139,25 +169,36 @@ const Screenshot = styled.img`
border-radius: 5px; border-radius: 5px;
${breakpoint('desktop')` ${breakpoint('desktop')`
width: 150%; margin-top: -120px;
margin-left: 120px;
width: 135%;
`}; `};
`; `;
const Highlights = styled(Grid)` const Mask = styled.div`
background: ${props => props.theme.primary}; width: 100%;
margin: 0 1em; overflow: hidden;
padding: 0 1em; padding: 8em 0;
`; `;
const Features = styled(Grid)` const Features = styled.div`
background: hsl(180, 58%, 85%);
padding: 0 2em; padding: 0 2em;
overflow: hidden; width: 100%;
`; `;
const Feature = styled(Grid.Unit)` const Feature = styled(Grid.Unit)`
padding: 3em 0; padding: 2em 0;
p {
font-weight: 500;
opacity: 0.8;
}
h2 { h2 {
display: flex;
font-size: 1.8em;
align-items: center;
margin-top: 0; margin-top: 0;
} }
@ -170,29 +211,33 @@ const Feature = styled(Grid.Unit)`
} }
${breakpoint('tablet')` ${breakpoint('tablet')`
padding: 4em 3em; padding: 4em 0;
`}; `};
`; `;
const Footer = styled.div` const Footer = styled.div`
text-align: center; background: hsl(127, 58%, 85%);
text-align: left;
width: 100%; width: 100%;
padding: 4em 2em; padding: 4em 2em;
h2 {
font-size: 1.8em;
margin-top: 0;
}
${breakpoint('tablet')` ${breakpoint('tablet')`
margin: 2em 0;
padding: 6em 4em; padding: 6em 4em;
`}; `};
`; `;
const FooterCTA = styled.p`
padding-top: 1em;
`;
const HeroText = styled.p` const HeroText = styled.p`
font-size: 18px; font-size: 22px;
color: #666;
font-weight: 500;
text-align: left;
max-width: 600px; max-width: 600px;
margin-left: auto;
margin-right: auto;
margin-bottom: 2em; margin-bottom: 2em;
`; `;

View File

@ -0,0 +1,9 @@
// @flow
import styled from 'styled-components';
const Centered = styled.div`
margin: 0 auto;
max-width: 1000px;
`;
export default Centered;

View File

@ -1,16 +1,15 @@
// @flow // @flow
import styled from 'styled-components'; import styled from 'styled-components';
import Centered from './Centered';
const Hero = styled.div` const Hero = styled(Centered)`
width: 100%; width: 100%;
height: 70vh; min-height: 500px;
min-height: 400px; padding: 4em 0 0;
max-height: 600px;
padding: 6em 2em 0;
text-align: center;
h1 { h1 {
font-size: 2.5em; font-size: 3.5em;
line-height: 1em;
} }
`; `;

View File

@ -1,6 +1,7 @@
// @flow // @flow
import * as React from 'react'; import * as React from 'react';
import { Helmet } from 'react-helmet'; import { Helmet } from 'react-helmet';
import styled from 'styled-components';
import { TopNavigation, BottomNavigation } from './Navigation'; import { TopNavigation, BottomNavigation } from './Navigation';
import Analytics from '../../../shared/components/Analytics'; import Analytics from '../../../shared/components/Analytics';
import globalStyles from '../../../shared/styles/globals'; import globalStyles from '../../../shared/styles/globals';
@ -15,7 +16,7 @@ type Props = {
children?: React.Node, children?: React.Node,
}; };
export default function Layout({ children }: Props) { function Layout({ children }: Props) {
globalStyles(); globalStyles();
return ( return (
@ -63,11 +64,17 @@ export default function Layout({ children }: Props) {
{'{{HEAD}}'} {'{{HEAD}}'}
{'{{CSS}}'} {'{{CSS}}'}
</head> </head>
<body> <Body>
<TopNavigation /> <TopNavigation />
{children} {children}
<BottomNavigation /> <BottomNavigation />
</body> </Body>
</html> </html>
); );
} }
const Body = styled.body`
padding: 0 30px;
`;
export default Layout;

View File

@ -2,6 +2,7 @@
import * as React from 'react'; import * as React from 'react';
import styled from 'styled-components'; import styled from 'styled-components';
import breakpoint from 'styled-components-breakpoint'; import breakpoint from 'styled-components-breakpoint';
import Centered from './Centered';
import { import {
developers, developers,
changelog, changelog,
@ -102,9 +103,9 @@ const MenuItemDesktop = styled(MenuItem)`
`}; `};
`; `;
const Nav = styled.nav` const Nav = styled(Centered)`
display: flex; display: flex;
padding: 20px 30px; padding: 20px 0;
align-items: center; align-items: center;
justify-content: space-between; justify-content: space-between;
`; `;
@ -114,7 +115,7 @@ const BottomNav = styled.nav`
justify-content: center; justify-content: center;
align-items: center; align-items: center;
flex-direction: column; flex-direction: column;
margin-bottom: 40px; margin: 4em 0;
> div { > div {
display: flex; display: flex;
@ -124,6 +125,7 @@ const BottomNav = styled.nav`
${breakpoint('tablet')` ${breakpoint('tablet')`
flex-direction: row; flex-direction: row;
margin: 0 0 4em;
> div { > div {
margin: 0 0 0 40px; margin: 0 0 0 40px;

View File

@ -21,7 +21,7 @@ const SigninButtons = ({
return ( return (
<Wrapper> <Wrapper>
{slackSigninEnabled && ( {slackSigninEnabled && (
<Flex column> <Column column>
<Button href={signin('slack')}> <Button href={signin('slack')}>
<SlackLogo /> <SlackLogo />
<Spacer>Sign In with Slack</Spacer> <Spacer>Sign In with Slack</Spacer>
@ -29,11 +29,10 @@ const SigninButtons = ({
<LastLogin> <LastLogin>
{lastSignedIn === 'slack' && 'You signed in with Slack previously'} {lastSignedIn === 'slack' && 'You signed in with Slack previously'}
</LastLogin> </LastLogin>
</Flex> </Column>
)} )}
&nbsp;
{googleSigninEnabled && ( {googleSigninEnabled && (
<Flex column> <Column column>
<Button href={signin('google')}> <Button href={signin('google')}>
<GoogleLogo /> <GoogleLogo />
<Spacer>Sign In with Google</Spacer> <Spacer>Sign In with Google</Spacer>
@ -42,19 +41,28 @@ const SigninButtons = ({
{lastSignedIn === 'google' && {lastSignedIn === 'google' &&
'You signed in with Google previously'} 'You signed in with Google previously'}
</LastLogin> </LastLogin>
</Flex> </Column>
)} )}
</Wrapper> </Wrapper>
); );
}; };
const Column = styled(Flex)`
text-align: center;
&:first-child {
margin-right: 8px;
}
`;
const Wrapper = styled(Flex)` const Wrapper = styled(Flex)`
display: block; display: block;
justify-content: center; justify-content: center;
${breakpoint('tablet')` ${breakpoint('tablet')`
display: flex; display: flex;
`}; justify-content: flex-start;
`};
`; `;
const Spacer = styled.span` const Spacer = styled.span`
@ -73,8 +81,9 @@ const Button = styled.a`
`; `;
const LastLogin = styled.p` const LastLogin = styled.p`
font-size: 12px; font-size: 13px;
color: ${props => props.theme.slate}; font-weight: 500;
color: rgba(20, 23, 26, 0.5);
padding-top: 4px; padding-top: 4px;
`; `;

View File

@ -7,7 +7,11 @@ import webpackConfig from '../../webpack.config';
const PUBLIC_PATH = webpackConfig.output.publicPath; const PUBLIC_PATH = webpackConfig.output.publicPath;
const prefetchTags = [ const prefetchTags = [
<link rel="dns-prefetch" href={process.env.AWS_S3_UPLOAD_BUCKET_URL} />, <link
rel="dns-prefetch"
href={process.env.AWS_S3_UPLOAD_BUCKET_URL}
key="dns"
/>,
]; ];
try { try {

View File

@ -0,0 +1,30 @@
// @flow
import * as React from 'react';
type Props = {
size?: number,
fill?: string,
className?: string,
};
function GithubLogo({ size = 34, fill = '#FFF', className }: Props) {
return (
<svg
fill={fill}
width={size}
height={size}
viewBox="0 0 36 36"
xmlns="http://www.w3.org/2000/svg"
className={className}
>
<path
fillRule="evenodd"
clipRule="evenodd"
fill="#191717"
d="M18,1.4C9,1.4,1.7,8.7,1.7,17.7c0,7.2,4.7,13.3,11.1,15.5 c0.8,0.1,1.1-0.4,1.1-0.8c0-0.4,0-1.4,0-2.8c-4.5,1-5.5-2.2-5.5-2.2c-0.7-1.9-1.8-2.4-1.8-2.4c-1.5-1,0.1-1,0.1-1 c1.6,0.1,2.5,1.7,2.5,1.7c1.5,2.5,3.8,1.8,4.7,1.4c0.1-1.1,0.6-1.8,1-2.2c-3.6-0.4-7.4-1.8-7.4-8.1c0-1.8,0.6-3.2,1.7-4.4 c-0.2-0.4-0.7-2.1,0.2-4.3c0,0,1.4-0.4,4.5,1.7c1.3-0.4,2.7-0.5,4.1-0.5c1.4,0,2.8,0.2,4.1,0.5c3.1-2.1,4.5-1.7,4.5-1.7 c0.9,2.2,0.3,3.9,0.2,4.3c1,1.1,1.7,2.6,1.7,4.4c0,6.3-3.8,7.6-7.4,8c0.6,0.5,1.1,1.5,1.1,3c0,2.2,0,3.9,0,4.5 c0,0.4,0.3,0.9,1.1,0.8c6.5-2.2,11.1-8.3,11.1-15.5C34.3,8.7,27,1.4,18,1.4z"
/>
</svg>
);
}
export default GithubLogo;