feat(website): implement market maker form

This commit is contained in:
Brandon Millman 2019-01-06 20:45:46 -08:00
parent 99b6ca5b4f
commit 5e8da70eae
2 changed files with 184 additions and 63 deletions

View File

@ -13,10 +13,16 @@ import { Input, InputWidth } from 'ts/components/modals/input';
import { Heading, Paragraph } from 'ts/components/text';
import { GlobalStyle } from 'ts/constants/globalStyle';
export enum ModalContactType {
General = 'GENERAL',
MarketMaker = 'MARKET_MAKER',
}
interface Props {
theme?: GlobalStyle;
isOpen?: boolean;
onDismiss?: () => void;
modalContactType: ModalContactType;
}
interface FormProps {
@ -39,23 +45,30 @@ interface ErrorProps {
}
export class ModalContact extends React.Component<Props> {
public static defaultProps = {
modalContactType: ModalContactType.General,
};
public state = {
isSubmitting: false,
isSuccessful: false,
errors: {},
};
// shared fields
public nameRef: React.RefObject<HTMLInputElement> = React.createRef();
public emailRef: React.RefObject<HTMLInputElement> = React.createRef();
public companyProjectRef: React.RefObject<HTMLInputElement> = React.createRef();
public linkRef: React.RefObject<HTMLInputElement> = React.createRef();
public commentsRef: React.RefObject<HTMLInputElement> = React.createRef();
// general lead fields
public linkRef: React.RefObject<HTMLInputElement> = React.createRef();
// market maker lead fields
public countryRef: React.RefObject<HTMLInputElement> = React.createRef();
public fundSizeRef: React.RefObject<HTMLInputElement> = React.createRef();
public constructor(props: Props) {
super(props);
}
public render(): React.ReactNode {
const { isOpen, onDismiss } = this.props;
const { isSuccessful, errors } = this.state;
return (
<>
<DialogOverlay
@ -68,58 +81,7 @@ export class ModalContact extends React.Component<Props> {
<Heading color={colors.textDarkPrimary} size={34} asElement="h2">
Contact the 0x Core Team
</Heading>
<Paragraph isMuted={true} color={colors.textDarkPrimary}>
If you're considering building on 0x, we're happy to answer your questions. Fill out the
form so we can connect you with the right person to help you get started.
</Paragraph>
<InputRow>
<Input
name="name"
label="Your name"
type="text"
width={InputWidth.Half}
ref={this.nameRef}
required={true}
errors={errors}
/>
<Input
name="email"
label="Your email"
type="email"
ref={this.emailRef}
required={true}
errors={errors}
width={InputWidth.Half}
/>
</InputRow>
<InputRow>
<Input
name="companyOrProject"
label="Name of your project / company"
type="text"
ref={this.companyProjectRef}
required={true}
errors={errors}
/>
</InputRow>
<InputRow>
<Input
name="link"
label="Do you have any documentation or a website?"
type="text"
ref={this.linkRef}
errors={errors}
/>
</InputRow>
<InputRow>
<Input
name="comments"
label="Anything else?"
type="textarea"
ref={this.commentsRef}
errors={errors}
/>
</InputRow>
{this._renderFormContent(errors)}
<ButtonRow>
<Button
color="#5C5C5C"
@ -149,28 +111,182 @@ export class ModalContact extends React.Component<Props> {
</>
);
}
public _renderFormContent(errors: ErrorProps): React.ReactNode {
switch (this.props.modalContactType) {
case ModalContactType.MarketMaker:
return this._renderMarketMakerFormContent(errors);
case ModalContactType.General:
default:
return this._renderGeneralFormContent(errors);
}
}
private _renderMarketMakerFormContent(errors: ErrorProps): React.ReactNode {
return (
<>
<Paragraph isMuted={true} color={colors.textDarkPrimary}>
If youre considering market making on 0x, were happy to answer your questions. Fill out the form
so we can connect you with the right person to help you get started.
</Paragraph>
<InputRow>
<Input
name="name"
label="Your name"
type="text"
width={InputWidth.Half}
ref={this.nameRef}
required={true}
errors={errors}
/>
<Input
name="email"
label="Your email"
type="email"
ref={this.emailRef}
required={true}
errors={errors}
width={InputWidth.Half}
/>
</InputRow>
<InputRow>
<Input
name="country"
label="Country of Location"
type="text"
ref={this.countryRef}
required={true}
errors={errors}
/>
</InputRow>
<InputRow>
<Input
name="fundSize"
label="Fund Size"
type="text"
ref={this.fundSizeRef}
required={true}
errors={errors}
/>
</InputRow>
<InputRow>
<Input
name="companyOrProject"
label="Name of your project / company"
type="text"
ref={this.companyProjectRef}
required={false}
errors={errors}
/>
</InputRow>
<InputRow>
<Input
name="comments"
label="What is prompting you to reach out?"
type="textarea"
ref={this.commentsRef}
required={false}
errors={errors}
/>
</InputRow>
</>
);
}
private _renderGeneralFormContent(errors: ErrorProps): React.ReactNode {
return (
<>
<Paragraph isMuted={true} color={colors.textDarkPrimary}>
If you're considering building on 0x, we're happy to answer your questions. Fill out the form so we
can connect you with the right person to help you get started.
</Paragraph>
<InputRow>
<Input
name="name"
label="Your name"
type="text"
width={InputWidth.Half}
ref={this.nameRef}
required={true}
errors={errors}
/>
<Input
name="email"
label="Your email"
type="email"
ref={this.emailRef}
required={true}
errors={errors}
width={InputWidth.Half}
/>
</InputRow>
<InputRow>
<Input
name="companyOrProject"
label="Name of your project / company"
type="text"
ref={this.companyProjectRef}
required={true}
errors={errors}
/>
</InputRow>
<InputRow>
<Input
name="link"
label="Do you have any documentation or a website?"
type="text"
ref={this.linkRef}
errors={errors}
/>
</InputRow>
<InputRow>
<Input
name="comments"
label="Anything else?"
type="textarea"
ref={this.commentsRef}
errors={errors}
/>
</InputRow>
</>
);
}
private async _onSubmitAsync(e: Event): Promise<void> {
e.preventDefault();
const name = this.nameRef.current.value;
const email = this.emailRef.current.value;
const projectOrCompany = this.companyProjectRef.current.value;
const link = this.linkRef.current.value;
const comments = this.commentsRef.current.value;
let jsonBody;
if (this.props.modalContactType === ModalContactType.MarketMaker) {
jsonBody = {
name: this.nameRef.current.value,
email: this.emailRef.current.value,
country: this.countryRef.current.value,
fundSize: this.fundSizeRef.current.value,
projectOrCompany: this.companyProjectRef.current.value,
comments: this.commentsRef.current.value,
};
} else {
jsonBody = {
name: this.nameRef.current.value,
email: this.emailRef.current.value,
projectOrCompany: this.companyProjectRef.current.value,
link: this.linkRef.current.value,
comments: this.commentsRef.current.value,
};
}
this.setState({ ...this.state, errors: [], isSubmitting: true });
const endpoint =
this.props.modalContactType === ModalContactType.MarketMaker ? '/market_maker_leads' : '/leads';
try {
// Disabling no-unbound method b/c no reason for _.isEmpty to be bound
// tslint:disable:no-unbound-method
const response = await fetch('https://website-api.0xproject.com/leads', {
const response = await fetch(`https://website-api.0xproject.com${endpoint}`, {
method: 'post',
mode: 'cors',
credentials: 'same-origin',
headers: {
'content-type': 'application/json; charset=utf-8',
},
body: JSON.stringify(_.omitBy({ name, email, projectOrCompany, link, comments }, _.isEmpty)),
body: JSON.stringify(_.omitBy(jsonBody, _.isEmpty)),
});
if (!response.ok) {
@ -201,6 +317,7 @@ export class ModalContact extends React.Component<Props> {
);
}
}
// Handle errors: {"errors":[{"location":"body","param":"name","msg":"Invalid value"},{"location":"body","param":"email","msg":"Invalid value"}]}
const InputRow = styled.div`

View File

@ -5,7 +5,7 @@ import { Banner } from 'ts/components/banner';
import { Button } from 'ts/components/button';
import { Action, Definition } from 'ts/components/definition';
import { Hero } from 'ts/components/hero';
import { ModalContact } from 'ts/components/modals/modal_contact';
import { ModalContact, ModalContactType } from 'ts/components/modals/modal_contact';
import { Section } from 'ts/components/newLayout';
import { SiteWrap } from 'ts/components/siteWrap';
import { WebsitePaths } from 'ts/types';
@ -125,7 +125,11 @@ export class NextMarketMaker extends React.Component<NextMarketMakerProps> {
mainCta={{ text: 'Explore the Docs', href: `${WebsitePaths.Wiki}#Market-Making-on-0x` }}
secondaryCta={{ text: 'Get in Touch', onClick: this._onOpenContactModal.bind(this) }}
/>
<ModalContact isOpen={this.state.isContactModalOpen} onDismiss={this._onDismissContactModal} />
<ModalContact
isOpen={this.state.isContactModalOpen}
onDismiss={this._onDismissContactModal}
modalContactType={ModalContactType.MarketMaker}
/>
</SiteWrap>
);
}