- implement screenshots
- implement OG tags
93
src/components/landing/Screenshots.js
Normal file
@ -0,0 +1,93 @@
|
|||||||
|
import React from 'react';
|
||||||
|
import { useStaticQuery, graphql } from 'gatsby';
|
||||||
|
import GatsbyImage from 'gatsby-image';
|
||||||
|
import styles from './Screenshots.module.css';
|
||||||
|
|
||||||
|
const Screenshots = () => {
|
||||||
|
const screenshots = useStaticQuery(graphql`
|
||||||
|
query {
|
||||||
|
screen1: file(relativePath: { eq: "screenshots/screen-1.png" }) {
|
||||||
|
childImageSharp {
|
||||||
|
fluid(maxWidth: 800) {
|
||||||
|
...GatsbyImageSharpFluid
|
||||||
|
}
|
||||||
|
fixed(width: 360) {
|
||||||
|
...GatsbyImageSharpFixed
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
screen2: file(relativePath: { eq: "screenshots/screen-2.png" }) {
|
||||||
|
childImageSharp {
|
||||||
|
fluid(maxWidth: 800) {
|
||||||
|
...GatsbyImageSharpFluid
|
||||||
|
}
|
||||||
|
fixed(width: 360) {
|
||||||
|
...GatsbyImageSharpFixed
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
screen3: file(relativePath: { eq: "screenshots/screen-3.png" }) {
|
||||||
|
childImageSharp {
|
||||||
|
fluid(maxWidth: 800) {
|
||||||
|
...GatsbyImageSharpFluid
|
||||||
|
}
|
||||||
|
fixed(width: 360) {
|
||||||
|
...GatsbyImageSharpFixed
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
screen4: file(relativePath: { eq: "screenshots/screen-4.png" }) {
|
||||||
|
childImageSharp {
|
||||||
|
fluid(maxWidth: 800) {
|
||||||
|
...GatsbyImageSharpFluid
|
||||||
|
}
|
||||||
|
fixed(width: 360) {
|
||||||
|
...GatsbyImageSharpFixed
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
screen5: file(relativePath: { eq: "screenshots/screen-5.png" }) {
|
||||||
|
childImageSharp {
|
||||||
|
fluid(maxWidth: 800) {
|
||||||
|
...GatsbyImageSharpFluid
|
||||||
|
}
|
||||||
|
fixed(width: 360) {
|
||||||
|
...GatsbyImageSharpFixed
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
screen6: file(relativePath: { eq: "screenshots/screen-6.png" }) {
|
||||||
|
childImageSharp {
|
||||||
|
fluid(maxWidth: 800) {
|
||||||
|
...GatsbyImageSharpFluid
|
||||||
|
}
|
||||||
|
fixed(width: 360) {
|
||||||
|
...GatsbyImageSharpFixed
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="mt-24 mb-4">
|
||||||
|
<h4 className="text-xl uppercase font-bold mb-8">Screenshots</h4>
|
||||||
|
|
||||||
|
<div className="flex w-full overflow-x-scroll">
|
||||||
|
{Object.keys(screenshots).map((x) => (
|
||||||
|
<a
|
||||||
|
target="_blank"
|
||||||
|
rel="noreferrer"
|
||||||
|
className={styles.screenshot}
|
||||||
|
key={screenshots[x].childImageSharp.fluid.src}
|
||||||
|
href={screenshots[x].childImageSharp.fluid.src}
|
||||||
|
>
|
||||||
|
<GatsbyImage fixed={screenshots[x].childImageSharp.fixed} />
|
||||||
|
</a>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default Screenshots;
|
||||||
13
src/components/landing/Screenshots.module.css
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
.screenshot {
|
||||||
|
@apply shadow-xl rounded border-2 border-primary-100 ml-10;
|
||||||
|
@apply transition-opacity duration-200 ease-in-out;
|
||||||
|
}
|
||||||
|
|
||||||
|
.screenshot:hover {
|
||||||
|
@apply opacity-50;
|
||||||
|
@apply transition-opacity duration-200 ease-in-out;
|
||||||
|
}
|
||||||
|
|
||||||
|
.screenshot:first-child {
|
||||||
|
@apply ml-0;
|
||||||
|
}
|
||||||
@ -1,5 +1,6 @@
|
|||||||
import React, { memo, useEffect } from 'react';
|
import React, { memo, useEffect } from 'react';
|
||||||
import { Slide, toast } from 'react-toastify';
|
import { Slide, toast } from 'react-toastify';
|
||||||
|
import { Helmet } from 'react-helmet';
|
||||||
import ModalRegistrar from '../../modals/ModalRegistrar';
|
import ModalRegistrar from '../../modals/ModalRegistrar';
|
||||||
|
|
||||||
const Wrapper = ({ children }) => {
|
const Wrapper = ({ children }) => {
|
||||||
@ -16,6 +17,22 @@ const Wrapper = ({ children }) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
|
<Helmet>
|
||||||
|
<title>Reactive Resume</title>
|
||||||
|
<meta
|
||||||
|
name="description"
|
||||||
|
content="A free and open source resume builder that’s built to make the mundane tasks of creating, updating and sharing your resume as easy as 1, 2, 3."
|
||||||
|
/>
|
||||||
|
<link rel="canonical" href="https://rxresu.me" />
|
||||||
|
<meta property="og:url" content="https://rxresu.me" />
|
||||||
|
<meta property="og:type" content="website" />
|
||||||
|
<meta
|
||||||
|
property="og:description"
|
||||||
|
content="A free and open source resume builder that’s built to make the mundane tasks of creating, updating and sharing your resume as easy as 1, 2, 3."
|
||||||
|
/>
|
||||||
|
<meta property="og:image" content="http://rxresu.me/images/share.png" />
|
||||||
|
</Helmet>
|
||||||
|
|
||||||
{children}
|
{children}
|
||||||
|
|
||||||
<ModalRegistrar />
|
<ModalRegistrar />
|
||||||
|
|||||||
@ -47,6 +47,8 @@ const FrequentlyAskedQuestions = () => {
|
|||||||
Your name and your email address is stored along with your user
|
Your name and your email address is stored along with your user
|
||||||
information, if you signed in with Google, and of course, all the
|
information, if you signed in with Google, and of course, all the
|
||||||
information you input in your resume is also stored in the database.
|
information you input in your resume is also stored in the database.
|
||||||
|
You won't even get any marketing emails, feature updates,
|
||||||
|
newsletters, notification emails, nothing.
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@ -83,8 +85,26 @@ const FrequentlyAskedQuestions = () => {
|
|||||||
<strong>Absolutely no catch to this freebie.</strong> This project
|
<strong>Absolutely no catch to this freebie.</strong> This project
|
||||||
is just my way of giving back to the community that I've
|
is just my way of giving back to the community that I've
|
||||||
learned so much from. If you'd like to show your appreciation
|
learned so much from. If you'd like to show your appreciation
|
||||||
however, you can follow me on my social media and let me know, or
|
however, you can follow me on my social media and let me know how
|
||||||
donate to the app to help pay the cloud bills.
|
much it helped you, or donate to help pay the cloud bills, or if you
|
||||||
|
are a fellow developer, you can head to GitHub and contribute to the
|
||||||
|
code and raising a PR.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<hr />
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<h4 className="text-xl font-medium mb-4">
|
||||||
|
Is there a mobile app for Reactive Resume?
|
||||||
|
</h4>
|
||||||
|
<p className="leading-loose">
|
||||||
|
<strong>Not yet. But soon, maybe?</strong> One of the main
|
||||||
|
motivations for me to shift to a centralized database approach was
|
||||||
|
that I could one day build a mobile app as well that could let users
|
||||||
|
jump from editing on their desktops to editing on their phones. It
|
||||||
|
requires a lot of time, so I would not expect it any time soon, but
|
||||||
|
it's definitely in the pipeline.
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@ -1,9 +1,10 @@
|
|||||||
|
import { Link } from '@reach/router';
|
||||||
import React, { memo } from 'react';
|
import React, { memo } from 'react';
|
||||||
import { Helmet } from 'react-helmet';
|
import { Helmet } from 'react-helmet';
|
||||||
import { Link } from '@reach/router';
|
|
||||||
import { useTranslation } from 'react-i18next';
|
import { useTranslation } from 'react-i18next';
|
||||||
import Hero from '../components/landing/Hero';
|
import Hero from '../components/landing/Hero';
|
||||||
import Wrapper from '../components/shared/Wrapper';
|
import Wrapper from '../components/shared/Wrapper';
|
||||||
|
import Screenshots from '../components/landing/Screenshots';
|
||||||
|
|
||||||
const Home = () => {
|
const Home = () => {
|
||||||
const { t } = useTranslation();
|
const { t } = useTranslation();
|
||||||
@ -18,6 +19,17 @@ const Home = () => {
|
|||||||
<div className="container mt-24">
|
<div className="container mt-24">
|
||||||
<Hero />
|
<Hero />
|
||||||
|
|
||||||
|
<p className="leading-loose text-xl mt-16">
|
||||||
|
Reactive Resume is a free and open source resume builder that’s built
|
||||||
|
to make the mundane tasks of creating, updating and sharing your
|
||||||
|
resume as easy as 1, 2, 3. With this app, you can create multiple
|
||||||
|
resumes, share them with recruiters through a unique link and print as
|
||||||
|
PDF, all for free, no advertisements, without losing the integrity and
|
||||||
|
privacy of your data.
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<Screenshots />
|
||||||
|
|
||||||
<div className="pt-8">
|
<div className="pt-8">
|
||||||
<Feature title="Create a resume that’s worthy of who you are.">
|
<Feature title="Create a resume that’s worthy of who you are.">
|
||||||
Keep up with the latest trends in resume design without having to
|
Keep up with the latest trends in resume design without having to
|
||||||
|
|||||||
BIN
static/images/screenshots/screen-1.png
Normal file
|
After Width: | Height: | Size: 159 KiB |
BIN
static/images/screenshots/screen-2.png
Normal file
|
After Width: | Height: | Size: 72 KiB |
BIN
static/images/screenshots/screen-3.png
Normal file
|
After Width: | Height: | Size: 61 KiB |
BIN
static/images/screenshots/screen-4.png
Normal file
|
After Width: | Height: | Size: 94 KiB |
BIN
static/images/screenshots/screen-5.png
Normal file
|
After Width: | Height: | Size: 34 KiB |
BIN
static/images/screenshots/screen-6.png
Normal file
|
After Width: | Height: | Size: 43 KiB |
BIN
static/images/share.png
Normal file
|
After Width: | Height: | Size: 490 KiB |