@@ -22,7 +22,7 @@ import Cubes from './Cubes';
2222import Frameworks from '../Frameworks' ;
2323
2424import getScrollPos from '../../../utils/scroll' ;
25-
25+ import { useMatchMedia , useInterval } from '../../../hooks' ;
2626import media from '../../../utils/media' ;
2727
2828const Container = styled ( Centered ) `
@@ -66,77 +66,65 @@ const Message = styled.h2`
6666
6767const TEMPLATES = [ parcel , react , vue , angular , gatsby , nuxt , next ] ;
6868
69- export default class Animation extends React . PureComponent {
70- state = {
71- templates : TEMPLATES . filter ( tem => tem . showOnHomePage && tem . showCube ) ,
72- templateIndex : 0 ,
73- templateSelected : false ,
74- canvas : null ,
75- } ;
76-
77- componentDidMount ( ) {
78- this . startTimer ( ) ;
79- }
80-
81- componentWillUnmount ( ) {
82- clearTimeout ( this . timeout ) ;
83- }
84-
85- startTimer = ( ) => {
86- this . timeout = setTimeout ( ( ) => {
87- if ( ! this . state . templateSelected ) {
88- if ( ! window . scrolling && getScrollPos ( ) . y < window . innerHeight ) {
89- this . setState ( state => ( {
90- templateIndex : ( state . templateIndex + 1 ) % state . templates . length ,
91- } ) ) ;
92- }
93-
94- this . startTimer ( ) ;
69+ const Animation = ( ) => {
70+ const templates = TEMPLATES . filter ( tem => tem . showOnHomePage && tem . showCube ) ;
71+ const reduceAnimation = useMatchMedia ( '(prefers-reduced-motion: reduce)' ) ;
72+ const [ templateIndex , setTemplateIndex ] = React . useState ( 0 ) ;
73+ const [ templateSelected , setTemplateSelected ] = React . useState ( false ) ;
74+ const canvas = React . useRef ( ) ;
75+
76+ const changeTemplate = React . useCallback ( ( ) => {
77+ if ( ! templateSelected ) {
78+ // @ts -ignore
79+ if ( ! window . scrolling && getScrollPos ( ) . y < window . innerHeight ) {
80+ setTemplateIndex ( index => ( index + 1 ) % templates . length ) ;
9581 }
96- } , 6000 ) ;
97- } ;
82+ }
83+ } , [ templateSelected , templates . length ] ) ;
9884
99- setCanvas = canvas => {
100- this . setState ( { canvas } ) ;
85+ const setCanvas = canvasToSet => {
86+ canvas . current = canvasToSet ;
10187 } ;
10288
103- selectTemplate = template => {
104- this . setState ( state => ( {
105- templateIndex : state . templates . indexOf ( template ) ,
106- templateSelected : true ,
107- } ) ) ;
89+ const selectTemplate = template => {
90+ setTemplateIndex ( templates . indexOf ( template ) ) ;
91+ setTemplateSelected ( true ) ;
10892 } ;
10993
110- render ( ) {
111- const template = this . state . templates [ this . state . templateIndex ] ;
112- return (
113- < Relative >
114- < Fullscreen >
115- < Background
116- templateIndex = { this . state . templateIndex }
117- template = { template }
118- setCanvas = { this . setCanvas }
119- />
120- < Container horizontal >
121- < HomeTitle template = { template } />
94+ useInterval ( changeTemplate , 6000 ) ;
95+ const template = templates [ templateIndex ] ;
96+
97+ return (
98+ < Relative >
99+ < Fullscreen >
100+ < Background
101+ templateIndex = { templateIndex }
102+ template = { template }
103+ setCanvas = { setCanvas }
104+ />
105+ < Container horizontal >
106+ < HomeTitle template = { template } />
107+ { ! reduceAnimation && (
122108 < Media query = "(min-width: 1280px)" >
123109 < Cubes
124- canvas = { this . state . canvas }
125- templates = { this . state . templates }
110+ canvas = { canvas . current }
111+ templates = { templates }
126112 template = { template }
127- setTemplate = { this . selectTemplate }
113+ setTemplate = { selectTemplate }
128114 />
129115 </ Media >
130- </ Container >
131- </ Fullscreen >
132- < Centered horizontal >
133- < Message >
134- CodeSandbox is an online editor that helps you create web
135- applications, from prototype to deployment.
136- </ Message >
137- </ Centered >
138- < Frameworks templates = { TEMPLATES . filter ( tem => tem . showOnHomePage ) } />
139- </ Relative >
140- ) ;
141- }
142- }
116+ ) }
117+ </ Container >
118+ </ Fullscreen >
119+ < Centered horizontal >
120+ < Message >
121+ CodeSandbox is an online editor that helps you create web
122+ applications, from prototype to deployment.
123+ </ Message >
124+ </ Centered >
125+ < Frameworks templates = { TEMPLATES . filter ( tem => tem . showOnHomePage ) } />
126+ </ Relative >
127+ ) ;
128+ } ;
129+
130+ export default React . memo ( Animation ) ;
0 commit comments