Skip to content

Instantly share code, notes, and snippets.

@dailenspencer
Created May 14, 2018 23:28
Show Gist options
  • Save dailenspencer/e925895ea38737cd77343cc5c4d86e40 to your computer and use it in GitHub Desktop.
Save dailenspencer/e925895ea38737cd77343cc5c4d86e40 to your computer and use it in GitHub Desktop.
import React from 'react'
import {Route} from 'react-router-dom';
import TransitionGroup from 'react-transition-group/TransitionGroup';
import _ from 'lodash';
import HomePage from 'components/Pages/Home/home.page';
import ParallaxPage from 'components/Pages/Home/parallax.page';
import NavigationPage from 'components/Pages/Navigation/navigation.page';
import BlogListPage from 'components/Pages/Blog/blogList.page';
import BlogPostPage from 'components/Pages/Blog/blogPost.page';
import ProjectGridPage from 'components/Pages/ProjectGrid/projectGrid.page';
import ProjectContentPage from 'components/Pages/ProjectContent/projectContent.page';
import SubscribePage from 'components/Pages/Subscribe/subscribe.page';
import AboutPage from 'components/Pages/About/about.page';
//import ErrorPage from 'components/Pages/Error/error.page';
import NavigationButton from 'components/Widgets/NavigationButton';
import {Animator} from 'lib/Helpers/Animator.js';
import {determineIntroReactRouterAnimationType,determineExitReactRouterAnimationType} from 'lib/Helpers/AnimationDetector';
import {retrieveBlogData} from 'lib/Helpers/aws/index';
const $ = window.$;
const TweenMax = window.TweenMax;
const CustomEase = window.CustomEase;
const firstChild = props => {
const childrenArray = React.Children.toArray(props.children);
return childrenArray[0] || null;
};
export default class Main extends React.Component {
constructor(props){
super(props)
this.state = {
componentIsLoading: true
}
}
componentWillMount () {
}
handleClick () {
this.context.router.history.push('/navigation')
}
render() {
return (
<div id="Home">
<NavigationButton/>
<Route
exact
path="/"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <Navigation {...rest} />}
</TransitionGroup>
)}/>
<Route
exact
path="/parallax"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <Parallax {...rest} />}
</TransitionGroup>
)}/>
<Route
path="/home"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <Home {...rest} />}
</TransitionGroup>
)}/>
<Route
path="/navigation"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <Navigation {...rest} />}
</TransitionGroup>
)}/>
<Route
exact
path="/blog"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <BlogList {...rest} />}
</TransitionGroup>
)}/>
<Route
path="/blog/:id"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <BlogPost {...rest} blogID={match.params.id}/>}
</TransitionGroup>
)}/>
<Route
exact
path="/projects"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <ProjectGrid {...rest}/>}
</TransitionGroup>
)}/>
<Route
path="/projects/:id"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <ProjectContent {...rest} projectID={match.params.id} />}
</TransitionGroup>
)}/>
<Route
path="/subscribe"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <Subscribe {...rest} />}
</TransitionGroup>
)}/>
<Route
path="/about"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <About {...rest} />}
</TransitionGroup>
)}/>
<Route
path="/contact"
children={({ match, ...rest }) => (
<TransitionGroup component={firstChild}>
{match && <About {...rest} scrollTo={'.section-contact'}/>}
</TransitionGroup>
)}/>
</div>
);
}
}
Main.contextTypes = {
router: React.PropTypes.object.isRequired
};
const AnimatedWrapper = (WrappedComponent, ComponentSelector) => class AnimatedWrapper
extends React.Component {
constructor(props){
super(props)
this.state = {
windowWidth: $(window).width(),
windowHeight: $(window).height()
}
}
componentWillEnter(callback) {
this.introAnimationType = determineIntroReactRouterAnimationType(this.props.location.originPath, this.props.location.targetPath)
$(ComponentSelector).css({'z-index':'10'})
switch (this.introAnimationType) {
case 'slideInFromTop':
Animator.slideInFromTop.prepareForAnimation(ComponentSelector, this.state.windowHeight);
break;
case 'slideInFromBottom':
Animator.slideInFromBottom.prepareForAnimation(ComponentSelector, this.state.windowHeight);
break;
default:
if (this.props.history.action === 'POP' || this.props.location.pathname === '/navigation') {
Animator.slideInFromLeft.prepareForAnimation(ComponentSelector, this.state.windowWidth);
} else {
Animator.slideInFromRight.prepareForAnimation(ComponentSelector, this.state.windowWidth);
}
break;
}
callback();
}
componentDidEnter () {
$(ComponentSelector).addClass('transitioning');
switch (this.introAnimationType) {
case 'slideInFromTop':
Animator.slideInFromTop.performAnimation(ComponentSelector, this.state.windowHeight);
break;
case 'slideInFromBottom':
Animator.slideInFromBottom.performAnimation(ComponentSelector, this.state.windowHeight);
break;
default:
if (this.props.history.action === 'POP' || this.props.history.location.pathname === '/navigation') {
Animator.slideInFromLeft.performAnimation(ComponentSelector, this.state.windowWidth);
} else {
Animator.slideInFromRight.performAnimation(ComponentSelector, this.state.windowWidth);
}
break;
}
}
componentWillLeave(callback) {
var exitAnimation = determineExitReactRouterAnimationType(this.props.location.pathname,this.props.history.location.pathname)
switch (exitAnimation) {
case 'slideOutToTop':
TweenMax.to($(ComponentSelector), 1.05,
{
y: -this.state.windowHeight,
ease: CustomEase.create("custom", "M0,0,C0.173,0,0.242,0.036,0.322,0.13,0.401,0.223,0.449,0.367,0.502,0.506,0.546,0.622,0.62,0.824,0.726,0.916,0.799,0.98,0.869,1,1,1"),
onComplete: function () {
callback()
}
}
);
break
case 'slideOutToBottom':
TweenMax.to($(ComponentSelector), 1.05,
{
y: this.state.windowHeight,
ease: CustomEase.create("custom", "M0,0,C0.173,0,0.242,0.036,0.322,0.13,0.401,0.223,0.449,0.367,0.502,0.506,0.546,0.622,0.62,0.824,0.726,0.916,0.799,0.98,0.869,1,1,1"),
onComplete: function () {
callback()
}
}
);
break;
default:
if (this.props.history.action === 'POP' || this.props.history.location.pathname === '/navigation') {
TweenMax.to($(ComponentSelector), 1.05,
{
x: this.state.windowWidth,
ease: CustomEase.create("custom", "M0,0,C0.173,0,0.242,0.036,0.322,0.13,0.401,0.223,0.449,0.367,0.502,0.506,0.546,0.622,0.62,0.824,0.726,0.916,0.799,0.98,0.869,1,1,1"),
onComplete: function () {
callback()
}
}
);
} else {
TweenMax.to($(ComponentSelector), 1.05,
{
x: -this.state.windowWidth,
ease: CustomEase.create("custom", "M0,0,C0.173,0,0.242,0.036,0.322,0.13,0.401,0.223,0.449,0.367,0.502,0.506,0.546,0.622,0.62,0.824,0.726,0.916,0.799,0.98,0.869,1,1,1"),
onComplete: function () {
callback()
}
}
);
}
break;
}
}
render () {
return (
<div className='animated-page-wrapper'>
<WrappedComponent {...this.props} />
</div>
)
}
}
class HomeComponent extends React.Component {
render () {
return (
<div className="page-slider-slide page-active home">
<HomePage/>
</div>
)
}
}
const HomeComponentSelector = '.page-slider-slide.page-active.home'
const Home = AnimatedWrapper(HomeComponent, HomeComponentSelector, 'right');
class ParallaxComponent extends React.Component {
render () {
return (
<div className="page-slider-slide page-active parallax">
<ParallaxPage/>
</div>
)
}
}
const ParallaxComponentSelector = '.page-slider-slide.page-active.home'
const Parallax = AnimatedWrapper(ParallaxComponent, ParallaxComponentSelector, 'right');
class NavigationComponent extends React.Component {
render() {
return (
<div className="page-slider-slide page-active navigation">
<NavigationPage/>
</div>
)
}
}
const NavigationComponentSelector = '.page-slider-slide.page-active.navigation'
const Navigation = AnimatedWrapper(NavigationComponent, NavigationComponentSelector);
/*Blog Component*/
/*Page that holds the list of blog items*/
class BlogListComponent extends React.Component {
render() {
return (
<div className="page-slider-slide page-active blog-list">
<BlogListPage/>
</div>
)
}
}
const BlogListComponentSelector = '.page-slider-slide.page-active.blog-list'
const BlogList = AnimatedWrapper(BlogListComponent, BlogListComponentSelector);
/*Blog Content Component*/
/*Page that holds the actual contents of a blog item*/
class BlogPostComponent extends React.Component {
componentDidMount () {
//HACK: needed to add this so parallax.js will update/refresh at appropriate time when transitioning from bloglist page to blogpost page
var count = 0;
var initWindowResize = _.throttle(function(){
if (count > 5 && !$('.transitioning').length) { //disconnect observer when page is done transitining
$(window).trigger('resize').trigger('scroll')
observer.disconnect();
} else if (count > 2) { //for some reason, we cant trigger the resize/scroll event for two counts. If we do it before, parallax.js will get funky
if ($('.parallax-window') && $('.parallax-window').data('__parallax')){
$('.parallax-window').data('__parallax').o.aspectRatio = null;
$(window).trigger('resize').trigger('scroll')
}
}
count++;
}, 10)
var observer = new MutationObserver((mutations) => {
mutations.forEach((mutationRecord) => {
initWindowResize();
});
});
var target = document.getElementById('blog-post');
observer.observe(target, { attributes : true, attributeFilter : ['style'] });
}
render() {
return (
<div className="page-slider-slide page-active blog-post" id="blog-post">
<BlogPostPage {...this.props}/>
</div>
)
}
}
const BlogPostComponentSelector = '.page-slider-slide.page-active.blog-post'
const BlogPost = AnimatedWrapper(BlogPostComponent, BlogPostComponentSelector);
class ProjectGridComponent extends React.Component {
render() {
return (
<div className="page-slider-slide page-active projects">
<ProjectGridPage/>
</div>
)
}
}
const ProjectsGridComponentSelector = '.page-slider-slide.page-active.projects'
const ProjectGrid = AnimatedWrapper(ProjectGridComponent, ProjectsGridComponentSelector);
class ProjectContentComponent extends React.Component {
render() {
return (
<div className="page-slider-slide page-active project-content">
<ProjectContentPage {...this.props}/>
</div>
)
}
}
const ProjectContentComponentSelector = '.page-slider-slide.page-active.project-content'
const ProjectContent = AnimatedWrapper(ProjectContentComponent, ProjectContentComponentSelector);
class SubscribeComponent extends React.Component {
render () {
return (
<div className="page-slider-slide page-active subscribe">
<SubscribePage/>
</div>
)
}
}
const SubscribeComponentSelector = '.page-slider-slide.page-active.subscribe'
const Subscribe = AnimatedWrapper(SubscribeComponent, SubscribeComponentSelector);
class AboutComponent extends React.Component {
render() {
return (
<div className="page-slider-slide page-active about">
<AboutPage {...this.props}/>
</div>
)
}
}
const AboutComponentSelector = '.page-slider-slide.page-active.about';
const About = AnimatedWrapper(AboutComponent, AboutComponentSelector);
/*Commenting out until in use*/
// class ErrorComponent extends React.Component {
// render() {
// return (
// <div className="page-slider-slide page-active error">
// <ErrorPage/>
// </div>
// )
// }
// }
// const ErrorComponentSelector = '.page-slider-slide.page-active.error';
// const Error = AnimatedWrapper(ErrorComponent, ErrorComponentSelector);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment