mirror of
https://github.com/kremalicious/portfolio.git
synced 2025-02-14 21:10:41 +01:00
animation tweaks
This commit is contained in:
parent
67ac38cdd6
commit
28a0675f16
@ -6,5 +6,5 @@ if (typeof window !== 'undefined' && !window.IntersectionObserver) {
|
||||
import('intersection-observer')
|
||||
}
|
||||
|
||||
// Page Transitions
|
||||
// Page Transitions & Layout
|
||||
export const wrapPageElement = wrapPageElementWithTransition
|
||||
|
@ -1,4 +1,4 @@
|
||||
import wrapPageElementWithTransition from './src/helpers/wrapPageElement'
|
||||
|
||||
// Page Transitions
|
||||
// Page Transitions & Layout
|
||||
export const wrapPageElement = wrapPageElementWithTransition
|
||||
|
@ -1,28 +1,46 @@
|
||||
import React, { Fragment } from 'react'
|
||||
import React, { PureComponent, Fragment } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import posed, { PoseGroup } from 'react-pose'
|
||||
import Head from './molecules/Head'
|
||||
import Header from './organisms/Header'
|
||||
import Footer from './organisms/Footer'
|
||||
import styles from './Layout.module.scss'
|
||||
|
||||
const Layout = ({ children, location }) => {
|
||||
const isHomepage = location.pathname === '/'
|
||||
const timeout = 150
|
||||
|
||||
return (
|
||||
<Fragment>
|
||||
<Head />
|
||||
<Header isHomepage={isHomepage} />
|
||||
export default class Layout extends PureComponent {
|
||||
static propTypes = {
|
||||
children: PropTypes.any.isRequired,
|
||||
location: PropTypes.object.isRequired
|
||||
}
|
||||
|
||||
<main className={styles.screen}>{children}</main>
|
||||
render() {
|
||||
const { children, location } = this.props
|
||||
const isHomepage = location.pathname === '/'
|
||||
|
||||
<Footer />
|
||||
</Fragment>
|
||||
)
|
||||
const RoutesContainer = posed.div({
|
||||
enter: {
|
||||
opacity: 1,
|
||||
delay: timeout,
|
||||
delayChildren: timeout
|
||||
},
|
||||
exit: {
|
||||
opacity: 0
|
||||
},
|
||||
initialPose: 'exit'
|
||||
})
|
||||
|
||||
return (
|
||||
<Fragment>
|
||||
<Head />
|
||||
<Header isHomepage={isHomepage} />
|
||||
<PoseGroup animateOnMount={true}>
|
||||
<RoutesContainer key={location.pathname}>
|
||||
<main className={styles.screen}>{children}</main>
|
||||
</RoutesContainer>
|
||||
</PoseGroup>
|
||||
<Footer />
|
||||
</Fragment>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
Layout.propTypes = {
|
||||
children: PropTypes.any.isRequired,
|
||||
location: PropTypes.object.isRequired
|
||||
}
|
||||
|
||||
export default Layout
|
||||
|
@ -1,27 +0,0 @@
|
||||
import React, { PureComponent } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import posed, { PoseGroup } from 'react-pose'
|
||||
|
||||
const timeout = 200
|
||||
|
||||
export default class Transition extends PureComponent {
|
||||
static propTypes = {
|
||||
children: PropTypes.node.isRequired,
|
||||
location: PropTypes.object.isRequired
|
||||
}
|
||||
|
||||
render() {
|
||||
const { children, location } = this.props
|
||||
|
||||
const RoutesContainer = posed.div({
|
||||
enter: { opacity: 1, delay: timeout, delayChildren: timeout },
|
||||
exit: { opacity: 0, delay: 0 }
|
||||
})
|
||||
|
||||
return (
|
||||
<PoseGroup animateOnMount={true}>
|
||||
<RoutesContainer key={location.pathname}>{children}</RoutesContainer>
|
||||
</PoseGroup>
|
||||
)
|
||||
}
|
||||
}
|
@ -1,6 +1,7 @@
|
||||
import React, { PureComponent } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import { StaticQuery, graphql } from 'gatsby'
|
||||
import posed, { PoseGroup } from 'react-pose'
|
||||
|
||||
import Logo from '../svg/Logo'
|
||||
import styles from './LogoUnit.module.scss'
|
||||
@ -14,6 +15,19 @@ const query = graphql`
|
||||
}
|
||||
`
|
||||
|
||||
const Animation = posed.div({
|
||||
enter: {
|
||||
opacity: 1,
|
||||
y: 0,
|
||||
transition: { type: 'spring' }
|
||||
},
|
||||
exit: {
|
||||
opacity: 0,
|
||||
y: '2rem',
|
||||
transition: { type: 'spring' }
|
||||
}
|
||||
})
|
||||
|
||||
class LogoUnit extends PureComponent {
|
||||
state = { minimal: false }
|
||||
|
||||
@ -44,16 +58,20 @@ class LogoUnit extends PureComponent {
|
||||
const { minimal } = this.state
|
||||
|
||||
return (
|
||||
<div className={minimal ? styles.minimal : styles.logounit}>
|
||||
<Logo className={styles.logounit__logo} />
|
||||
<h1 className={styles.logounit__title}>
|
||||
{meta.title.toLowerCase()}
|
||||
</h1>
|
||||
<p className={styles.logounit__description}>
|
||||
<span>{'{ '}</span> {meta.tagline.toLowerCase()}{' '}
|
||||
<span>{' }'}</span>
|
||||
</p>
|
||||
</div>
|
||||
<PoseGroup animateOnMount={true}>
|
||||
<Animation>
|
||||
<div className={minimal ? styles.minimal : styles.logounit}>
|
||||
<Logo className={styles.logounit__logo} />
|
||||
<h1 className={styles.logounit__title}>
|
||||
{meta.title.toLowerCase()}
|
||||
</h1>
|
||||
<p className={styles.logounit__description}>
|
||||
<span>{'{ '}</span> {meta.tagline.toLowerCase()}{' '}
|
||||
<span>{' }'}</span>
|
||||
</p>
|
||||
</div>
|
||||
</Animation>
|
||||
</PoseGroup>
|
||||
)
|
||||
}}
|
||||
/>
|
||||
|
@ -25,13 +25,11 @@
|
||||
margin-right: $spacer / 4;
|
||||
color: $brand-main;
|
||||
line-height: $line-height;
|
||||
transition: color .2s ease-out;
|
||||
}
|
||||
|
||||
.logounit__description {
|
||||
font-size: $font-size-h4;
|
||||
color: $brand-grey;
|
||||
transition: color .2s ease-out;
|
||||
|
||||
:global(.dark) & {
|
||||
color: $brand-grey-light;
|
||||
|
@ -1,8 +1,8 @@
|
||||
import React, { Fragment, PureComponent } from 'react'
|
||||
import React, { PureComponent } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import { StaticQuery, graphql } from 'gatsby'
|
||||
import posed, { PoseGroup } from 'react-pose'
|
||||
|
||||
// import { MoveIn } from '../atoms/Animations'
|
||||
import styles from './Availability.module.scss'
|
||||
|
||||
const query = graphql`
|
||||
@ -17,6 +17,19 @@ const query = graphql`
|
||||
}
|
||||
`
|
||||
|
||||
const Animation = posed.aside({
|
||||
enter: {
|
||||
opacity: 1,
|
||||
y: 0,
|
||||
transition: { type: 'spring' }
|
||||
},
|
||||
exit: {
|
||||
opacity: 0,
|
||||
y: '2rem',
|
||||
transition: { type: 'spring' }
|
||||
}
|
||||
})
|
||||
|
||||
export default class Availability extends PureComponent {
|
||||
static propTypes = { hide: PropTypes.bool }
|
||||
|
||||
@ -29,9 +42,9 @@ export default class Availability extends PureComponent {
|
||||
const { status, available, unavailable } = availability
|
||||
|
||||
return (
|
||||
<Fragment>
|
||||
{!this.props.hide && (
|
||||
<aside
|
||||
!this.props.hide && (
|
||||
<PoseGroup animateOnMount={true}>
|
||||
<Animation
|
||||
className={
|
||||
status
|
||||
? `${styles.availability} ${styles.available}`
|
||||
@ -43,9 +56,9 @@ export default class Availability extends PureComponent {
|
||||
__html: status ? available : unavailable
|
||||
}}
|
||||
/>
|
||||
</aside>
|
||||
)}
|
||||
</Fragment>
|
||||
</Animation>
|
||||
</PoseGroup>
|
||||
)
|
||||
)
|
||||
}}
|
||||
/>
|
||||
|
@ -1,7 +1,7 @@
|
||||
import React, { PureComponent } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import { StaticQuery, graphql } from 'gatsby'
|
||||
import posed from 'react-pose'
|
||||
import posed, { PoseGroup } from 'react-pose'
|
||||
|
||||
import Email from '../svg/Email'
|
||||
import Blog from '../svg/Blog'
|
||||
@ -43,18 +43,16 @@ const NetworkIcon = props => {
|
||||
}
|
||||
}
|
||||
|
||||
const AnimatedContainer = posed.div({
|
||||
const Animation = posed.aside({
|
||||
enter: {
|
||||
opacity: 1,
|
||||
y: 0,
|
||||
transition: {
|
||||
ease: 'easeInOut'
|
||||
}
|
||||
transition: { type: 'spring' }
|
||||
},
|
||||
exit: {
|
||||
y: '-100%',
|
||||
transition: {
|
||||
ease: 'easeInOut'
|
||||
}
|
||||
opacity: 0,
|
||||
y: '-2rem',
|
||||
transition: { type: 'spring' }
|
||||
}
|
||||
})
|
||||
|
||||
@ -93,16 +91,16 @@ export default class Network extends PureComponent {
|
||||
|
||||
return (
|
||||
!this.props.hide && (
|
||||
<AnimatedContainer>
|
||||
<aside className={this.state.classes}>
|
||||
<PoseGroup animateOnMount={true}>
|
||||
<Animation className={this.state.classes}>
|
||||
{Object.keys(meta.social).map((key, i) => (
|
||||
<a className={styles.link} href={meta.social[key]} key={i}>
|
||||
<NetworkIcon title={key} className={icons.icon} />
|
||||
<span className={styles.title}>{key}</span>
|
||||
</a>
|
||||
))}
|
||||
</aside>
|
||||
</AnimatedContainer>
|
||||
</Animation>
|
||||
</PoseGroup>
|
||||
)
|
||||
)
|
||||
}}
|
||||
|
@ -1,10 +1,24 @@
|
||||
import React, { PureComponent, Fragment } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import Helmet from 'react-helmet'
|
||||
import posed, { PoseGroup } from 'react-pose'
|
||||
import Day from '../svg/Day'
|
||||
import Night from '../svg/Night'
|
||||
import styles from './ThemeSwitch.module.scss'
|
||||
|
||||
const Animation = posed.aside({
|
||||
enter: {
|
||||
opacity: 1,
|
||||
y: 0,
|
||||
transition: { type: 'spring' }
|
||||
},
|
||||
exit: {
|
||||
opacity: 0,
|
||||
y: '-2rem',
|
||||
transition: { type: 'spring' }
|
||||
}
|
||||
})
|
||||
|
||||
const ThemeToggle = ({ dark }) => (
|
||||
<span id="toggle" className={styles.checkboxContainer} aria-live="assertive">
|
||||
<Day className={dark ? null : 'active'} />
|
||||
@ -60,20 +74,22 @@ export default class ThemeSwitch extends PureComponent {
|
||||
<Helmet>
|
||||
<body className={this.isDark() ? 'dark' : null} />
|
||||
</Helmet>
|
||||
<aside className={styles.themeSwitch}>
|
||||
<label className={styles.checkbox}>
|
||||
<span className={styles.label}>Toggle Night Mode</span>
|
||||
<input
|
||||
onChange={this.handleChange}
|
||||
type="checkbox"
|
||||
name="toggle"
|
||||
value="toggle"
|
||||
aria-describedby="toggle"
|
||||
checked={this.isDark()}
|
||||
/>
|
||||
<ThemeToggle dark={this.isDark()} />
|
||||
</label>
|
||||
</aside>
|
||||
<PoseGroup animateOnMount={true}>
|
||||
<Animation className={styles.themeSwitch}>
|
||||
<label className={styles.checkbox}>
|
||||
<span className={styles.label}>Toggle Night Mode</span>
|
||||
<input
|
||||
onChange={this.handleChange}
|
||||
type="checkbox"
|
||||
name="toggle"
|
||||
value="toggle"
|
||||
aria-describedby="toggle"
|
||||
checked={this.isDark()}
|
||||
/>
|
||||
<ThemeToggle dark={this.isDark()} />
|
||||
</label>
|
||||
</Animation>
|
||||
</PoseGroup>
|
||||
</Fragment>
|
||||
)
|
||||
}
|
||||
|
@ -1,8 +1,8 @@
|
||||
import React from 'react'
|
||||
import Transition from '../components/Transition'
|
||||
import Layout from '../components/Layout'
|
||||
|
||||
const wrapPageElement = ({ element, props }) => (
|
||||
<Transition {...props}>{element}</Transition>
|
||||
<Layout {...props}>{element}</Layout>
|
||||
)
|
||||
|
||||
export default wrapPageElement
|
||||
|
@ -2,7 +2,6 @@ import React, { Component } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import { Link } from 'gatsby'
|
||||
import giphyAPI from 'giphy-js-sdk-core'
|
||||
import Layout from '../components/Layout'
|
||||
import Content from '../components/atoms/Content'
|
||||
import Button from '../components/atoms/Button'
|
||||
import './404.scss'
|
||||
@ -42,24 +41,22 @@ export default class NotFound extends Component {
|
||||
|
||||
render() {
|
||||
return (
|
||||
<Layout location={this.props.location}>
|
||||
<Content className="content content--404">
|
||||
<h1>Shenanigans, page not found.</h1>
|
||||
<p>
|
||||
You might want to check the url, or{' '}
|
||||
<Link to={'/'}>go back to the homepage</Link>. Or just check out
|
||||
some cat fail gifs, entirely your choice.
|
||||
</p>
|
||||
<Content className="content content--404">
|
||||
<h1>Shenanigans, page not found.</h1>
|
||||
<p>
|
||||
You might want to check the url, or{' '}
|
||||
<Link to={'/'}>go back to the homepage</Link>. Or just check out some
|
||||
cat fail gifs, entirely your choice.
|
||||
</p>
|
||||
|
||||
<video className="gif" src={this.state.gif} autoPlay loop />
|
||||
<video className="gif" src={this.state.gif} autoPlay loop />
|
||||
|
||||
<div>
|
||||
<Button onClick={this.handleClick}>
|
||||
Show me another cat fail gif
|
||||
</Button>
|
||||
</div>
|
||||
</Content>
|
||||
</Layout>
|
||||
<div>
|
||||
<Button onClick={this.handleClick}>
|
||||
Show me another cat fail gif
|
||||
</Button>
|
||||
</div>
|
||||
</Content>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -1,33 +1,30 @@
|
||||
import React from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import { Link, graphql } from 'gatsby'
|
||||
import Layout from '../components/Layout'
|
||||
import ProjectImage from '../components/atoms/ProjectImage'
|
||||
import FullWidth from '../components/atoms/FullWidth'
|
||||
import styles from './index.module.scss'
|
||||
|
||||
const Home = ({ data, location }) => {
|
||||
const Home = ({ data }) => {
|
||||
const projects = data.allProjectsYaml.edges
|
||||
|
||||
return (
|
||||
<Layout location={location}>
|
||||
<FullWidth>
|
||||
<div className={styles.projects}>
|
||||
{projects.map(({ node }) => {
|
||||
const { slug, title, img } = node
|
||||
<FullWidth>
|
||||
<div className={styles.projects}>
|
||||
{projects.map(({ node }) => {
|
||||
const { slug, title, img } = node
|
||||
|
||||
return (
|
||||
<article className={styles.project} key={slug}>
|
||||
<Link to={slug}>
|
||||
<h1 className={styles.title}>{title}</h1>
|
||||
<ProjectImage fluid={img.childImageSharp.fluid} alt={title} />
|
||||
</Link>
|
||||
</article>
|
||||
)
|
||||
})}
|
||||
</div>
|
||||
</FullWidth>
|
||||
</Layout>
|
||||
return (
|
||||
<article className={styles.project} key={slug}>
|
||||
<Link to={slug}>
|
||||
<h1 className={styles.title}>{title}</h1>
|
||||
<ProjectImage fluid={img.childImageSharp.fluid} alt={title} />
|
||||
</Link>
|
||||
</article>
|
||||
)
|
||||
})}
|
||||
</div>
|
||||
</FullWidth>
|
||||
)
|
||||
}
|
||||
|
||||
|
@ -1,9 +1,8 @@
|
||||
import React from 'react'
|
||||
import React, { Fragment } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import Helmet from 'react-helmet'
|
||||
import ReactMarkdown from 'react-markdown'
|
||||
import { graphql } from 'gatsby'
|
||||
import Layout from '../components/Layout'
|
||||
import Content from '../components/atoms/Content'
|
||||
import FullWidth from '../components/atoms/FullWidth'
|
||||
import ProjectImage from '../components/atoms/ProjectImage'
|
||||
@ -31,7 +30,7 @@ const ProjectImages = ({ projectImages, title }) => (
|
||||
</FullWidth>
|
||||
)
|
||||
|
||||
const Project = ({ data, location }) => {
|
||||
const Project = ({ data }) => {
|
||||
const project = data.projectsYaml
|
||||
const projectImages = data.projectImages.edges
|
||||
const { title, links, techstack } = project
|
||||
@ -39,7 +38,7 @@ const Project = ({ data, location }) => {
|
||||
const descriptionWithLineBreaks = description.split('\n').join('\n\n')
|
||||
|
||||
return (
|
||||
<Layout location={location}>
|
||||
<Fragment>
|
||||
<Helmet title={title} />
|
||||
|
||||
<SEO project={project} />
|
||||
@ -57,7 +56,7 @@ const Project = ({ data, location }) => {
|
||||
</article>
|
||||
|
||||
<ProjectNav slug={project.slug} />
|
||||
</Layout>
|
||||
</Fragment>
|
||||
)
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user