diff --git a/www/package.json b/www/package.json index baa245e83b71f..ace5cd6c2dc53 100644 --- a/www/package.json +++ b/www/package.json @@ -5,6 +5,7 @@ "author": "Kyle Mathews ", "dependencies": { "@reach/skip-nav": "^0.1.1", + "axios": "^0.18.0", "bluebird": "^3.5.1", "dotenv": "^6.0.0", "email-validator": "^1.1.1", diff --git a/www/src/components/unbird.js b/www/src/components/unbird.js new file mode 100644 index 0000000000000..be82474480c45 --- /dev/null +++ b/www/src/components/unbird.js @@ -0,0 +1,223 @@ +import React from "react" +import PropTypes from "prop-types" +import axios from "axios" +import styled from "react-emotion" +import { rhythm, options } from "../utils/typography" +import presets, { colors } from "../utils/presets" +import EnvelopeFaIcon from "react-icons/lib/fa/envelope-o" +import CancelMdIcon from "react-icons/lib/md/close" +import SendIcon from "react-icons/lib/io/paper-airplane" + +const FeedbackComponent = styled(`section`)` + box-sizing: border-box; + position: relative; +` + +const FeedbackToggle = styled(`div`)` + width: 60px; + height: 60px; + bottom: 64px; + background-color: ${colors.gatsby}; + color: #fff; + border-radius: 100%; + box-shadow: 0 1px 6px rgba(0, 0, 0, 0.06), 0 2px 32px rgba(0, 0, 0, 0.16); + position: fixed; + right: 20px; + z-index: 99999; + cursor: pointer; + + :hover { + background-color: ${colors.gatsbyDark}; + } + + ${presets.Tablet} { + bottom: 30px; + right: 30px; + } +` + +const IconWrapper = styled(`div`)` + align-items: center; + display: flex; + height: 100%; + justify-content: center; + width: 100%; + + svg { + height: auto; + } +` + +const EnvelopeIcon = styled(EnvelopeFaIcon)` + font-size: ${rhythm(1)}; +` +const CancelIcon = styled(CancelMdIcon)` + font-size: ${rhythm(1.2)}; +` + +const StatusMessage = styled(`span`)` + position: absolute; + width: 100%; + background: ${colors.gray.dark}; + bottom: 60px; + color: #fff; + font-size: 16px; + padding: 0.4rem 0.8rem; + text-align: left; + left: 0; +` + +const FeedbackForm = styled(`div`)` + position: fixed; + right: 5%; + bottom: 134px; + width: 90%; + background-color: ${colors.gatsby}; + box-shadow: 0 0 40px 5px rgba(0, 0, 0, 0.2); + border-radius: ${presets.radiusLg}px; + font-family: ${options.systemFontFamily.join(`,`)}; + + ${presets.Tablet} { + width: 350px; + right: 30px; + bottom: 100px; + } +` + +const Label = styled(`label`)` + font-family: ${options.headerFontFamily.join(`,`)}; + font-weight: 600; + height: 240px; + color: #fff; + display: flex; + justify-content: center; + align-items: center; + padding: 40px; + font-size: 22px; + float: left; +` + +const Form = styled(`form`)` + margin: 0; +` + +const Input = styled(`input`)` + float: left; + height: 60px; + width: calc(100% - 60px); + font-size: 14px; + padding: 20px; + border: none; + resize: none; + border-right: 1px solid #ddd; + border-radius: 0; +` + +const Send = styled(`button`)` + float: left; + width: 60px; + height: 60px; + cursor: pointer; + border: none; + background: #fff; + padding: 0; + + svg { + width: 50%; + height: auto; + fill: ${colors.gatsby}; + } +` + +class Unbird extends React.Component { + state = { + visible: false, + feedbackInput: ``, + statusMessage: ``, + } + + static defaultProps = { + feedbackPrompt: `How can we improve your experience?`, + feedbackPlaceholder: `Send feedback...`, + } + + render() { + return ( + + + + {this.state.visible ? : } + + + + {this.state.visible && ( + +
+ + {this.state.statusMessage && ( + {this.state.statusMessage} + )} + + + + +
+
+ )} +
+ ) + } + + toggleFeedbackForm = () => { + this.setState({ + visible: !this.state.visible, + statusMessage: ``, + feedbackInput: ``, + }) + } + + handleFeedbackInput = e => { + this.setState({ feedbackInput: e.target.value }) + } + + setStatusMessage = msg => { + this.setState({ statusMessage: msg }) + } + + submitFeedback = async e => { + e.preventDefault() + + const { dataSetId, publicKey } = this.props + const Unbird = `https://app.unbird.com/widget/entry/${dataSetId}/${publicKey}` + + return axios + .post(Unbird, { + entry: this.state.feedbackInput, + }) + .then(_ => { + this.setStatusMessage(`Sent! Thanks :)`) + this.setState({ feedbackInput: `` }) + }) + .catch(_ => { + this.setStatusMessage(`Oops. Something went wrong...`) + }) + } +} + +Unbird.propTypes = { + dataSetId: PropTypes.string.isRequired, + publicKey: PropTypes.string.isRequired, + feedbackPrompt: PropTypes.string, + feedbackPlaceholder: PropTypes.string, +} + +export default Unbird diff --git a/www/src/utils/typography.js b/www/src/utils/typography.js index 500a970540fa5..3a81263e54b85 100644 --- a/www/src/utils/typography.js +++ b/www/src/utils/typography.js @@ -97,7 +97,7 @@ const _options = { paddingTop: `0.2em`, paddingBottom: `0.2em`, }, - "tt, code, kbd, .gatsby-code-title": { + "tt, code, kbd, label, .gatsby-code-title": { fontFamily: options.monospaceFontFamily.join(`,`), fontSize: `80%`, }, diff --git a/www/src/views/starter-library/index.js b/www/src/views/starter-library/index.js index 5217530824de1..72ebaff6f569a 100644 --- a/www/src/views/starter-library/index.js +++ b/www/src/views/starter-library/index.js @@ -1,6 +1,7 @@ import React, { Component } from "react" import Helmet from "react-helmet" import Layout from "../../components/layout" +import Unbird from "../../components/unbird" import RRSM from "../../utils/reach-router-state-manager" import queryString from "query-string" @@ -55,6 +56,11 @@ class StarterLibraryPage extends Component { )} defaultSearchState={{ v: [`2`] }} /> + ) }