Skip to content

Commit aea8973

Browse files
committed
WIP form submit animation #13
1 parent 3f02264 commit aea8973

File tree

4 files changed

+116
-25
lines changed

4 files changed

+116
-25
lines changed

components/SubscribeForm.js

Lines changed: 20 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,11 @@ import { iPadMaxW } from '../lib/styles'
1212
class SubscribeForm extends React.Component {
1313
static propTypes = {
1414
mutate: React.PropTypes.func.isRequired,
15+
onSubmit: React.PropTypes.func,
16+
}
17+
18+
static defaultProps = {
19+
onSubmit: Function.prototype,
1520
}
1621

1722
constructor(props) {
@@ -33,17 +38,23 @@ class SubscribeForm extends React.Component {
3338
}
3439

3540
onSubmit(event) {
41+
this.props.onSubmit()
3642
event.preventDefault()
3743
const email = this.formEmail.state.value
38-
this.props.mutate({ variables: { email } })
39-
.then(({ data }) => {
40-
this.formEmail.setState({ value: '' })
41-
this.setState({ error: '' })
42-
this.handleOpen()
43-
})
44-
.catch((error) => {
45-
this.setState({ error: error.graphQLErrors[0].data.reason })
46-
})
44+
if (email.length === 0) {
45+
return
46+
}
47+
48+
this.props
49+
.mutate({ variables: { email } })
50+
.then(({ data }) => {
51+
this.formEmail.setState({ value: '' })
52+
this.setState({ error: '' })
53+
this.handleOpen()
54+
})
55+
.catch((error) => {
56+
this.setState({ error: error.graphQLErrors[0].data.reason })
57+
})
4758
}
4859

4960
handleOpen = () => {

data/resolvers.js

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,13 +19,13 @@ export default {
1919
let error
2020

2121
if (subscriberExists) {
22-
error = 'A subscriber with this email already exists'
22+
error = 'Your email has already been submitted'
2323
} else if (args.email.length === 0) {
24-
error = 'The email provided should not be empty'
24+
error = 'Empty email address'
2525
} else {
2626
const isValid = /^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,4}$/.test(args.email)
2727
if (!isValid) {
28-
error = 'Provide a valid email'
28+
error = 'Invalid email address'
2929
}
3030
}
3131

lib/analytics/autotrack.js

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,21 @@
11
// From:
22
// https://github.com/philipwalton/analyticsjs-boilerplate/blob/777ef6f2695c510a9e8d75ff0b426ee0a87ed18a/src/analytics/autotrack.js
3+
//
4+
// ISC License (ISC)
5+
//
6+
// Copyright (c) 2017, Philip Walton <[email protected]>
7+
//
8+
// Permission to use, copy, modify, and/or distribute this software for any
9+
// purpose with or without fee is hereby granted, provided that the above
10+
// copyright notice and this permission notice appear in all copies.
11+
//
12+
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
13+
// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
14+
// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
15+
// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
16+
// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
17+
// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
18+
// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
319

420
/* eslint-disable */
521

pages/index.js

Lines changed: 77 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import React, { Component } from 'react'
1+
import React, { Component, PropTypes } from 'react'
22
import ReactDOM from 'react-dom'
33
import MuiThemeProvider from 'material-ui/styles/MuiThemeProvider'
44
import Paper from 'material-ui/Paper'
@@ -20,13 +20,25 @@ import Email from '../components/email'
2020
import SubscribeForm from '../components/SubscribeForm'
2121
import BookLI from '../components/book-li'
2222
import LogoLI from '../components/logo-li'
23-
import Ripple from '../components/ripple'
23+
import RippleComponent from '../components/ripple'
2424
import Emoji from '../components/emoji'
2525

2626
import muiTheme from '../lib/muitheme'
2727
import { white, color, grey, iPadMaxW } from '../lib/styles'
2828
import withData from '../lib/withData'
2929

30+
const DEVELOPING_ANIMATIONS = false
31+
const showAnimations = (process.env.NODE_ENV !== 'production' && DEVELOPING_ANIMATIONS)
32+
33+
let Ripple = RippleComponent
34+
const Noop = ({ children }) => <div>{children}</div>
35+
Noop.propTypes = {
36+
children: PropTypes.element.isRequired,
37+
}
38+
if (!showAnimations) {
39+
Ripple = Noop
40+
}
41+
3042
// fixes "Warning: Unknown prop `onTouchTap` on <label> tag."
3143
if (typeof window !== 'undefined') injectTapEventPlugin()
3244

@@ -59,6 +71,14 @@ const bookTopics = [
5971
]
6072

6173
class Index extends Component {
74+
constructor(props) {
75+
super(props)
76+
77+
this.state = {
78+
subscribed: false,
79+
}
80+
}
81+
6282
componentDidMount() {
6383
const header = ReactDOM.findDOMNode(this.header)
6484
const introPara = ReactDOM.findDOMNode(this.introPara)
@@ -135,7 +155,11 @@ class Index extends Component {
135155
delay: 2,
136156
})
137157

138-
animation.play()
158+
if (showAnimations) {
159+
animation.play()
160+
} else {
161+
animation.time(animation.endTime())
162+
}
139163
}
140164

141165
render() {
@@ -233,6 +257,7 @@ class Index extends Component {
233257
flexDirection: 'column',
234258
justifyContent: 'center',
235259
alignItems: 'center',
260+
perspective: 1400,
236261
}}
237262
>
238263
<p
@@ -380,28 +405,67 @@ class Index extends Component {
380405
<Paper
381406
className="form-container"
382407
style={{
383-
display: 'flex',
384-
flexDirection: 'column',
385-
alignItems: 'center',
386-
justifyContent: 'center',
408+
position: 'relative',
387409
opacity: 0,
388410
paddingTop: 10,
389411
paddingBottom: 10,
390412
marginBottom: 20,
391413
willChange: 'opacity, transform',
414+
transition: this.state.subscribed ? 'transform 1s ease-in-out' : null,
415+
transform: this.state.subscribed ? 'rotateY( 180deg )' : null,
392416
}}
393417
zDepth={2}
394418
ref={(comingSoon) => { this.comingSoon = comingSoon }}
395419
>
396-
<h2
420+
<div className="card-face">
421+
<h2
422+
style={{
423+
margin: 0,
424+
textAlign: 'center',
425+
fontSize: '1.7em',
426+
}}
427+
>
428+
Coming soon
429+
</h2>
430+
<SubscribeForm
431+
onSubmit={() => this.setState({ subscribed: true })}
432+
/>
433+
</div>
434+
<div
435+
className="card-face"
397436
style={{
398-
margin: 0,
399-
fontSize: '1.7em',
437+
position: 'absolute',
438+
top: 0,
439+
transform: 'rotateY( 180deg )',
440+
backgroundColor: 'red',
400441
}}
401442
>
402-
Coming soon
403-
</h2>
404-
<SubscribeForm />
443+
<div
444+
style={{
445+
display: 'flex',
446+
alignItems: 'center',
447+
}}
448+
>
449+
<Emoji
450+
name="pray"
451+
/>
452+
{'Thank you'}
453+
<Emoji
454+
name="relaxed"
455+
/>
456+
</div>
457+
</div>
458+
<style jsx>{`
459+
.card-face {
460+
display: flex;
461+
flex-direction: column;
462+
align-items: center;
463+
justify-content: center;
464+
width: 100%;
465+
height: 100%;
466+
backface-visibility: hidden;
467+
}
468+
`}</style>
405469
</Paper>
406470
<div
407471
style={{

0 commit comments

Comments
 (0)