diff options
author | Hsuan Lee <hsuan@cobinhood.com> | 2019-01-19 18:42:04 +0800 |
---|---|---|
committer | Hsuan Lee <hsuan@cobinhood.com> | 2019-01-19 18:42:04 +0800 |
commit | 7ae38906926dc09bc10670c361af0d2bf0050426 (patch) | |
tree | 5fb10ae366b987db09e4ddb4bc3ba0f75404ad08 /packages/website/ts/pages/instant | |
parent | b5fd3c72a08aaa6957917d74c333387a16edf66b (diff) | |
download | dexon-sol-tools-7ae38906926dc09bc10670c361af0d2bf0050426.tar.gz dexon-sol-tools-7ae38906926dc09bc10670c361af0d2bf0050426.tar.zst dexon-sol-tools-7ae38906926dc09bc10670c361af0d2bf0050426.zip |
Update dependency packages
Diffstat (limited to 'packages/website/ts/pages/instant')
-rw-r--r-- | packages/website/ts/pages/instant/code_demo.tsx | 183 | ||||
-rw-r--r-- | packages/website/ts/pages/instant/config_generator.tsx | 329 | ||||
-rw-r--r-- | packages/website/ts/pages/instant/config_generator_address_input.tsx | 84 | ||||
-rw-r--r-- | packages/website/ts/pages/instant/configurator.tsx | 104 | ||||
-rw-r--r-- | packages/website/ts/pages/instant/fee_percentage_slider.tsx | 80 | ||||
-rw-r--r-- | packages/website/ts/pages/instant/rc-slider.css | 295 | ||||
-rw-r--r-- | packages/website/ts/pages/instant/select.tsx | 74 |
7 files changed, 0 insertions, 1149 deletions
diff --git a/packages/website/ts/pages/instant/code_demo.tsx b/packages/website/ts/pages/instant/code_demo.tsx deleted file mode 100644 index c59f148b8..000000000 --- a/packages/website/ts/pages/instant/code_demo.tsx +++ /dev/null @@ -1,183 +0,0 @@ -import * as React from 'react'; -import * as CopyToClipboard from 'react-copy-to-clipboard'; -import SyntaxHighlighter from 'react-syntax-highlighter'; - -import { Button } from 'ts/components/button'; -import { Container } from 'ts/components/ui/container'; -import { styled } from 'ts/style/theme'; -import { zIndex } from 'ts/style/z_index'; - -const CustomPre = styled.pre` - margin: 0px; - line-height: 24px; - overflow: scroll; - width: 100%; - height: 100%; - max-height: 800px; - border-radius: 4px; - code { - background-color: inherit !important; - border-radius: 0px; - font-family: 'Roboto Mono', sans-serif; - border: none; - } - code:first-of-type { - background-color: #060d0d !important; - color: #999; - min-height: 100%; - text-align: center; - margin-right: 15px; - line-height: 25px; - padding: 10px 7px !important; - } - code:last-of-type { - position: relative; - top: 10px; - top: 0; - padding-top: 11px; - display: inline-block; - line-height: 25px; - } -`; - -const customStyle = { - 'hljs-comment': { - color: '#7e7887', - }, - 'hljs-quote': { - color: '#7e7887', - }, - 'hljs-variable': { - color: '#be4678', - }, - 'hljs-template-variable': { - color: '#be4678', - }, - 'hljs-attribute': { - color: '#be4678', - }, - 'hljs-regexp': { - color: '#be4678', - }, - 'hljs-link': { - color: '#be4678', - }, - 'hljs-tag': { - color: '#61f5ff', - }, - 'hljs-name': { - color: '#61f5ff', - }, - 'hljs-selector-id': { - color: '#be4678', - }, - 'hljs-selector-class': { - color: '#be4678', - }, - 'hljs-number': { - color: '#c994ff', - }, - 'hljs-meta': { - color: '#61f5ff', - }, - 'hljs-built_in': { - color: '#aa573c', - }, - 'hljs-builtin-name': { - color: '#aa573c', - }, - 'hljs-literal': { - color: '#aa573c', - }, - 'hljs-type': { - color: '#aa573c', - }, - 'hljs-params': { - color: '#aa573c', - }, - 'hljs-string': { - color: '#bcff88', - }, - 'hljs-symbol': { - color: '#2a9292', - }, - 'hljs-bullet': { - color: '#2a9292', - }, - 'hljs-title': { - color: '#576ddb', - }, - 'hljs-section': { - color: '#576ddb', - }, - 'hljs-keyword': { - color: '#955ae7', - }, - 'hljs-selector-tag': { - color: '#955ae7', - }, - 'hljs-deletion': { - color: '#19171c', - display: 'inline-block', - width: '100%', - backgroundColor: '#be4678', - }, - 'hljs-addition': { - color: '#19171c', - display: 'inline-block', - width: '100%', - backgroundColor: '#2a9292', - }, - hljs: { - display: 'block', - overflowX: 'hidden', - background: '#1B2625', - color: 'white', - fontSize: '12px', - }, - 'hljs-emphasis': { - fontStyle: 'italic', - }, - 'hljs-strong': { - fontWeight: 'bold', - }, -}; - -export interface CodeDemoProps { - children: string; -} - -export interface CodeDemoState { - didCopyCode: boolean; -} - -export class CodeDemo extends React.Component<CodeDemoProps, CodeDemoState> { - public state: CodeDemoState = { - didCopyCode: false, - }; - public render(): React.ReactNode { - const copyButtonText = this.state.didCopyCode ? 'Copied!' : 'Copy'; - return ( - <Container position="relative" height="100%"> - <Container position="absolute" top="10px" right="10px" zIndex={zIndex.overlay - 1}> - <CopyToClipboard text={this.props.children} onCopy={this._handleCopyClick}> - <StyledButton>{copyButtonText}</StyledButton> - </CopyToClipboard> - </Container> - <SyntaxHighlighter language="html" style={customStyle} showLineNumbers={true} PreTag={CustomPre}> - {this.props.children} - </SyntaxHighlighter> - </Container> - ); - } - private readonly _handleCopyClick = () => { - this.setState({ didCopyCode: true }); - }; -} - -const StyledButton = styled(Button)` - border-radius: 4px; - font-size: 15px; - font-weight: 400; - padding: 9px 21px 7px; -`; diff --git a/packages/website/ts/pages/instant/config_generator.tsx b/packages/website/ts/pages/instant/config_generator.tsx deleted file mode 100644 index 29fce85db..000000000 --- a/packages/website/ts/pages/instant/config_generator.tsx +++ /dev/null @@ -1,329 +0,0 @@ -import { StandardRelayerAPIOrderProvider } from '@0x/asset-buyer'; -import { getContractAddressesForNetworkOrThrow } from '@0x/contract-addresses'; -import { assetDataUtils } from '@0x/order-utils'; -import { ObjectMap } from '@0x/types'; -import * as _ from 'lodash'; -import * as React from 'react'; -import styled from 'styled-components'; - -import { CheckMark } from 'ts/components/ui/check_mark'; -import { Container } from 'ts/components/ui/container'; -import { MultiSelect } from 'ts/components/ui/multi_select'; -import { Spinner } from 'ts/components/ui/spinner'; -import { Text } from 'ts/components/ui/text'; -import { ConfigGeneratorAddressInput } from 'ts/pages/instant/config_generator_address_input'; -import { FeePercentageSlider } from 'ts/pages/instant/fee_percentage_slider'; -import { colors } from 'ts/style/colors'; -import { WebsitePaths } from 'ts/types'; -import { constants } from 'ts/utils/constants'; - -// New components -import { Heading } from 'ts/components/text'; -import { Select, SelectItemConfig } from 'ts/pages/instant/select'; - -import { assetMetaDataMap } from '../../../../instant/src/data/asset_meta_data_map'; -import { ERC20AssetMetaData, ZeroExInstantBaseConfig } from '../../../../instant/src/types'; - -export interface ConfigGeneratorProps { - value: ZeroExInstantBaseConfig; - onConfigChange: (config: ZeroExInstantBaseConfig) => void; -} - -export interface ConfigGeneratorState { - isLoadingAvailableTokens: boolean; - // Address to token info - availableTokens?: ObjectMap<ERC20AssetMetaData>; -} - -const SRA_ENDPOINTS = ['https://api.radarrelay.com/0x/v2/', 'https://sra.bamboorelay.com/0x/v2/']; - -export class ConfigGenerator extends React.Component<ConfigGeneratorProps, ConfigGeneratorState> { - public state: ConfigGeneratorState = { - isLoadingAvailableTokens: true, - }; - public componentDidMount(): void { - // tslint:disable-next-line:no-floating-promises - this._setAvailableAssetsFromOrderProvider(); - } - public componentDidUpdate(prevProps: ConfigGeneratorProps): void { - if (prevProps.value.orderSource !== this.props.value.orderSource) { - // tslint:disable-next-line:no-floating-promises - this._setAvailableAssetsFromOrderProvider(); - const newConfig: ZeroExInstantBaseConfig = { - ...this.props.value, - availableAssetDatas: undefined, - }; - this.props.onConfigChange(newConfig); - } - } - public render(): React.ReactNode { - const { value } = this.props; - if (!_.isString(value.orderSource)) { - throw new Error('ConfigGenerator component only supports string values as an orderSource.'); - } - return ( - <Container minWidth="350px"> - <ConfigGeneratorSection title="Liquidity Source"> - <Select - shouldIncludeEmpty={false} - id="" - value={value.orderSource} - items={this._generateItems()} - onChange={this._handleSRASelection.bind(this)} - /> - </ConfigGeneratorSection> - <ConfigGeneratorSection {...this._getTokenSelectorProps()}> - {this._renderTokenMultiSelectOrSpinner()} - </ConfigGeneratorSection> - <ConfigGeneratorSection title="Transaction fee ETH address" marginBottom="10px" isOptional={true}> - <ConfigGeneratorAddressInput - value={value.affiliateInfo ? value.affiliateInfo.feeRecipient : ''} - onChange={this._handleAffiliateAddressChange} - /> - </ConfigGeneratorSection> - <ConfigGeneratorSection - title="Fee percentage" - actionText="Learn more" - onActionTextClick={this._handleAffiliatePercentageLearnMoreClick} - > - <FeePercentageSlider - value={value.affiliateInfo.feePercentage} - onChange={this._handleAffiliatePercentageChange} - isDisabled={ - _.isUndefined(value.affiliateInfo) || - _.isUndefined(value.affiliateInfo.feeRecipient) || - _.isEmpty(value.affiliateInfo.feeRecipient) - } - /> - </ConfigGeneratorSection> - </Container> - ); - } - private readonly _getTokenSelectorProps = (): ConfigGeneratorSectionProps => { - if (_.isEmpty(this.state.availableTokens)) { - return { - title: 'What tokens can users buy?', - }; - } - if (_.isUndefined(this.props.value.availableAssetDatas)) { - return { - title: 'What tokens can users buy?', - actionText: 'Unselect All', - onActionTextClick: this._handleUnselectAllClick, - }; - } - return { - title: 'What tokens can users buy?', - actionText: 'Select All', - onActionTextClick: this._handleSelectAllClick, - }; - }; - private readonly _generateItems = (): SelectItemConfig[] => { - return _.map(SRA_ENDPOINTS, endpoint => ({ - label: endpoint, - value: endpoint, - onClick: this._handleSRASelection.bind(this, endpoint), - })); - }; - private readonly _handleAffiliatePercentageLearnMoreClick = (): void => { - window.open(`${WebsitePaths.Wiki}#Learn-About-Affiliate-Fees`, '_blank'); - }; - private readonly _handleSRASelection = (event: React.ChangeEvent<HTMLSelectElement>) => { - const sraEndpoint = event.target.value; - const newConfig: ZeroExInstantBaseConfig = { - ...this.props.value, - orderSource: sraEndpoint, - }; - this.props.onConfigChange(newConfig); - }; - private readonly _handleAffiliateAddressChange = (address: string, isValid: boolean) => { - const oldConfig: ZeroExInstantBaseConfig = this.props.value; - const newConfig: ZeroExInstantBaseConfig = { - ...oldConfig, - affiliateInfo: { - feeRecipient: address, - feePercentage: oldConfig.affiliateInfo.feePercentage, - }, - }; - this.props.onConfigChange(newConfig); - }; - private readonly _handleAffiliatePercentageChange = (value: number) => { - const oldConfig: ZeroExInstantBaseConfig = this.props.value; - const newConfig: ZeroExInstantBaseConfig = { - ...oldConfig, - affiliateInfo: { - feeRecipient: oldConfig.affiliateInfo.feeRecipient, - feePercentage: value, - }, - }; - this.props.onConfigChange(newConfig); - }; - private readonly _handleSelectAllClick = () => { - const newConfig: ZeroExInstantBaseConfig = { - ...this.props.value, - availableAssetDatas: undefined, - }; - this.props.onConfigChange(newConfig); - }; - private readonly _handleUnselectAllClick = () => { - const newConfig: ZeroExInstantBaseConfig = { - ...this.props.value, - availableAssetDatas: [], - }; - this.props.onConfigChange(newConfig); - }; - private readonly _handleTokenClick = (assetData: string) => { - const { value } = this.props; - let newAvailableAssetDatas: string[] = []; - const allKnownAssetDatas = _.keys(this.state.availableTokens); - const availableAssetDatas = value.availableAssetDatas; - if (_.isUndefined(availableAssetDatas)) { - // It being undefined means it's all tokens. - newAvailableAssetDatas = _.pull(allKnownAssetDatas, assetData); - } else if (!_.includes(availableAssetDatas, assetData)) { - // Add it - newAvailableAssetDatas = [...availableAssetDatas, assetData]; - if (newAvailableAssetDatas.length === allKnownAssetDatas.length) { - // If all tokens are manually selected, just show none. - newAvailableAssetDatas = undefined; - } - } else { - // Remove it - newAvailableAssetDatas = _.pull(availableAssetDatas, assetData); - } - const newConfig: ZeroExInstantBaseConfig = { - ...this.props.value, - availableAssetDatas: newAvailableAssetDatas, - }; - this.props.onConfigChange(newConfig); - }; - private readonly _setAvailableAssetsFromOrderProvider = async (): Promise<void> => { - const { value } = this.props; - if (!_.isUndefined(value.orderSource) && _.isString(value.orderSource)) { - this.setState({ isLoadingAvailableTokens: true }); - const networkId = constants.NETWORK_ID_MAINNET; - const sraOrderProvider = new StandardRelayerAPIOrderProvider(value.orderSource, networkId); - const etherTokenAddress = getContractAddressesForNetworkOrThrow(networkId).etherToken; - const etherTokenAssetData = assetDataUtils.encodeERC20AssetData(etherTokenAddress); - const assetDatas = await sraOrderProvider.getAvailableMakerAssetDatasAsync(etherTokenAssetData); - const availableTokens = _.reduce( - assetDatas, - (acc, assetData) => { - const metaDataIfExists = assetMetaDataMap[assetData] as ERC20AssetMetaData; - if (metaDataIfExists) { - acc[assetData] = metaDataIfExists; - } - return acc; - }, - {} as ObjectMap<ERC20AssetMetaData>, - ); - this.setState({ availableTokens, isLoadingAvailableTokens: false }); - } - }; - private readonly _renderTokenMultiSelectOrSpinner = (): React.ReactNode => { - const { value } = this.props; - const { availableTokens, isLoadingAvailableTokens } = this.state; - const multiSelectHeight = '200px'; - if (isLoadingAvailableTokens) { - return ( - <Container - className="flex flex-column items-center justify-center" - height={multiSelectHeight} - backgroundColor={colors.white} - borderRadius="4px" - width="100%" - > - <Container position="relative" left="12px" marginBottom="20px"> - <Spinner /> - </Container> - <Text fontSize="16px">Loading...</Text> - </Container> - ); - } - const availableAssetDatas = _.keys(availableTokens); - if (availableAssetDatas.length === 0) { - return ( - <Container - className="flex flex-column items-center justify-center" - height={multiSelectHeight} - backgroundColor={colors.white} - borderRadius="4px" - width="100%" - > - <Text fontSize="16px">No tokens available. Try another endpoint?</Text> - </Container> - ); - } - const items = _.map(_.keys(availableTokens), assetData => { - const metaData = availableTokens[assetData]; - return { - value: assetData, - renderItemContent: (isSelected: boolean) => ( - <Container className="flex items-center"> - <Container marginRight="10px"> - <CheckMark isChecked={isSelected} color={colors.brandLight} /> - </Container> - <CheckboxText isSelected={isSelected}> - {metaData.symbol.toUpperCase()} — {metaData.name} - </CheckboxText> - </Container> - ), - onClick: this._handleTokenClick.bind(this, assetData), - }; - }); - return <MultiSelect items={items} selectedValues={value.availableAssetDatas} height={multiSelectHeight} />; - }; -} - -export interface ConfigGeneratorSectionProps { - title: string; - actionText?: string; - onActionTextClick?: () => void; - isOptional?: boolean; - marginBottom?: string; -} - -export const ConfigGeneratorSection: React.StatelessComponent<ConfigGeneratorSectionProps> = ({ - title, - actionText, - onActionTextClick, - isOptional, - marginBottom, - children, -}) => ( - <Container marginBottom={marginBottom}> - <Container marginBottom="10px" className="flex justify-between items-center"> - <Heading size="small" marginBottom="0" isFlex={true}> - <span>{title}</span> - {isOptional && <OptionalText> Optional</OptionalText>} - </Heading> - {actionText && <OptionalAction onClick={onActionTextClick}>{actionText}</OptionalAction>} - </Container> - {children} - </Container> -); - -ConfigGeneratorSection.defaultProps = { - marginBottom: '30px', -}; - -const OptionalText = styled.span` - display: inline; - font-size: 14px; - color: #999999; - flex-shrink: 0; -`; - -interface CheckboxTextProps { - isSelected?: boolean; -} - -const CheckboxText = styled.span<CheckboxTextProps>` - font-size: 14px; - line-height: 18px; - color: ${props => (props.isSelected ? colors.brandDark : '#666666')}; -`; - -const OptionalAction = styled(OptionalText)` - cursor: pointer; -`; diff --git a/packages/website/ts/pages/instant/config_generator_address_input.tsx b/packages/website/ts/pages/instant/config_generator_address_input.tsx deleted file mode 100644 index 890e39da6..000000000 --- a/packages/website/ts/pages/instant/config_generator_address_input.tsx +++ /dev/null @@ -1,84 +0,0 @@ -import { addressUtils } from '@0x/utils'; -import * as _ from 'lodash'; -import * as React from 'react'; -import styled from 'styled-components'; - -import { colors } from 'ts/style/colors'; - -import { Container } from 'ts/components/ui/container'; - -import { Paragraph } from 'ts/components/text'; - -export interface ConfigGeneratorAddressInputProps { - value?: string; - onChange?: (address: string, isValid: boolean) => void; -} - -export interface ConfigGeneratorAddressInputState { - errMsg: string; -} - -export interface InputProps { - className?: string; - value?: string; - width?: string; - fontSize?: string; - fontColor?: string; - padding?: string; - placeholderColor?: string; - placeholder?: string; - backgroundColor?: string; - onChange?: (event: React.ChangeEvent<HTMLInputElement>) => void; -} - -export class ConfigGeneratorAddressInput extends React.Component< - ConfigGeneratorAddressInputProps, - ConfigGeneratorAddressInputState -> { - public state = { - errMsg: '', - }; - public render(): React.ReactNode { - const { errMsg } = this.state; - const hasError = !_.isEmpty(errMsg); - return ( - <Container height="80px"> - <Input value={this.props.value} onChange={this._handleChange} placeholder="0xe99...aa8da4" /> - <Container marginTop="5px" isHidden={!hasError} height="25px"> - <Paragraph size="small" isNoMargin={true}> - {errMsg} - </Paragraph> - </Container> - </Container> - ); - } - - private readonly _handleChange = (event: React.ChangeEvent<HTMLInputElement>): void => { - const address = event.target.value; - const isValidAddress = addressUtils.isAddress(address.toLowerCase()) || address === ''; - const errMsg = isValidAddress ? '' : 'Please enter a valid Ethereum address'; - this.setState({ - errMsg, - }); - this.props.onChange(address, isValidAddress); - }; -} - -const PlainInput: React.StatelessComponent<InputProps> = ({ value, className, placeholder, onChange }) => ( - <input className={className} value={value} onChange={onChange} placeholder={placeholder} /> -); - -export const Input = styled(PlainInput)` - background-color: ${colors.white}; - color: ${colors.textDarkSecondary}; - font-size: 1rem; - width: 100%; - padding: 16px 20px 18px; - border-radius: 4px; - border: 1px solid transparent; - outline: none; - &::placeholder { - color: #333333; - opacity: 0.5; - } -`; diff --git a/packages/website/ts/pages/instant/configurator.tsx b/packages/website/ts/pages/instant/configurator.tsx deleted file mode 100644 index a63e1752e..000000000 --- a/packages/website/ts/pages/instant/configurator.tsx +++ /dev/null @@ -1,104 +0,0 @@ -import * as _ from 'lodash'; -import * as React from 'react'; -import styled from 'styled-components'; - -import { CodeDemo } from 'ts/pages/instant/code_demo'; -import { ConfigGenerator } from 'ts/pages/instant/config_generator'; - -import { Link } from 'ts/components/link'; -import { Column, FlexWrap } from 'ts/components/newLayout'; -import { Heading } from 'ts/components/text'; -import { WebsitePaths } from 'ts/types'; - -import { ZeroExInstantBaseConfig } from '../../../../instant/src/types'; - -export interface ConfiguratorState { - instantConfig: ZeroExInstantBaseConfig; -} - -export class Configurator extends React.Component { - public state: ConfiguratorState = { - instantConfig: { - orderSource: 'https://api.radarrelay.com/0x/v2/', - availableAssetDatas: undefined, - affiliateInfo: { - feeRecipient: '', - feePercentage: 0, - }, - }, - }; - public render(): React.ReactNode { - const codeToDisplay = this._generateCodeDemoCode(); - return ( - <FlexWrap isFlex={true}> - <Column width="442px" padding="0 70px 0 0"> - <ConfigGenerator value={this.state.instantConfig} onConfigChange={this._handleConfigChange} /> - </Column> - <Column width="100%"> - <HeadingWrapper> - <Heading size="small" marginBottom="15px"> - Code Snippet - </Heading> - <Link href={`${WebsitePaths.Wiki}#Get-Started-With-Instant`} isBlock={true} target="_blank"> - Explore the Docs - </Link> - </HeadingWrapper> - <CodeDemo key={codeToDisplay}>{codeToDisplay}</CodeDemo> - </Column> - </FlexWrap> - ); - } - private readonly _handleConfigChange = (config: ZeroExInstantBaseConfig) => { - this.setState({ - instantConfig: config, - }); - }; - private readonly _generateCodeDemoCode = (): string => { - const { instantConfig } = this.state; - return `<!DOCTYPE html> -<html> - <head> - <meta charset="utf-8" /> - <script src="https://instant.0x.org/instant.js"></script> - </head> - <body> - <script> - zeroExInstant.render({ - orderSource: '${instantConfig.orderSource}',${ - !_.isUndefined(instantConfig.affiliateInfo) && instantConfig.affiliateInfo.feeRecipient - ? `\n affiliateInfo: { - feeRecipient: '${instantConfig.affiliateInfo.feeRecipient.toLowerCase()}', - feePercentage: ${instantConfig.affiliateInfo.feePercentage} - },` - : '' - }${ - !_.isUndefined(instantConfig.availableAssetDatas) - ? `\n availableAssetDatas: ${this._renderAvailableAssetDatasString( - instantConfig.availableAssetDatas, - )}` - : '' - } - }, 'body'); - </script> - </body> - </html>`; - }; - private readonly _renderAvailableAssetDatasString = (availableAssetDatas: string[]): string => { - const stringAvailableAssetDatas = availableAssetDatas.map(assetData => `'${assetData}'`); - if (availableAssetDatas.length < 2) { - return `[${stringAvailableAssetDatas.join(', ')}]`; - } - return `[\n ${stringAvailableAssetDatas.join( - ', \n ', - )}\n ]`; - }; -} - -const HeadingWrapper = styled.div` - display: flex; - justify-content: space-between; - - a { - transform: translateY(-8px); - } -`; diff --git a/packages/website/ts/pages/instant/fee_percentage_slider.tsx b/packages/website/ts/pages/instant/fee_percentage_slider.tsx deleted file mode 100644 index c4d9f908f..000000000 --- a/packages/website/ts/pages/instant/fee_percentage_slider.tsx +++ /dev/null @@ -1,80 +0,0 @@ -import Slider from 'rc-slider'; -import * as React from 'react'; -import styled from 'styled-components'; -import 'ts/pages/instant/rc-slider.css'; - -import { colors } from 'ts/style/colors'; - -const SliderWithTooltip = (Slider as any).createSliderWithTooltip(Slider); -// tslint:disable-next-line:no-unused-expression - -export interface FeePercentageSliderProps { - value: number; - isDisabled?: boolean; - onChange: (value: number) => void; -} - -export class FeePercentageSlider extends React.Component<FeePercentageSliderProps> { - public render(): React.ReactNode { - return ( - <StyledSlider - min={0} - max={0.05} - step={0.0025} - value={this.props.value} - disabled={this.props.isDisabled} - onChange={this.props.onChange} - tipFormatter={this._feePercentageSliderFormatter} - tipProps={{ placement: 'bottom', overlayStyle: { backgroundColor: '#fff', borderRadius: '4px' } }} - trackStyle={{ - backgroundColor: colors.brandLight, - }} - railStyle={{ - backgroundColor: 'rgba(255, 255, 255, 0.2)', - }} - handleStyle={{ - border: 'none', - boxShadow: 'none', - }} - activeDotStyle={{ - boxShadow: 'none', - border: 'none', - }} - /> - ); - } - private readonly _feePercentageSliderFormatter = (value: number): React.ReactNode => { - return <Text>{`${(value * 100).toFixed(2)}%`}</Text>; - }; -} - -const StyledSlider = styled(SliderWithTooltip)` - .rc-slider-tooltip__inner { - box-shadow: none !important; - background-color: ${colors.white} !important; - border-radius: 4px !important; - padding: 3px 12px !important; - height: auto !important; - position: relative; - top: 7px; - &:after { - border: solid transparent; - content: ' '; - height: 0; - width: 0; - position: absolute; - pointer-events: none; - border-width: 6px; - bottom: 100%; - left: 100%; - border-bottom-color: ${colors.white}; - margin-left: -60%; - } - } -`; - -const Text = styled.span` - color: #000000; - font-size: 12px; - line-height: 18px; -`; diff --git a/packages/website/ts/pages/instant/rc-slider.css b/packages/website/ts/pages/instant/rc-slider.css deleted file mode 100644 index 63038324e..000000000 --- a/packages/website/ts/pages/instant/rc-slider.css +++ /dev/null @@ -1,295 +0,0 @@ -.rc-slider { - position: relative; - height: 14px; - padding: 5px 0; - width: 100%; - border-radius: 6px; - -ms-touch-action: none; - touch-action: none; - box-sizing: border-box; - -webkit-tap-highlight-color: rgba(0, 0, 0, 0); -} - -.rc-slider * { - box-sizing: border-box; - -webkit-tap-highlight-color: rgba(0, 0, 0, 0); -} - -.rc-slider-rail { - position: absolute; - width: 100%; - background-color: #e9e9e9; - height: 4px; - border-radius: 6px; -} - -.rc-slider-track { - position: absolute; - left: 0; - height: 4px; - border-radius: 6px; - background-color: #abe2fb; -} - -.rc-slider-handle { - position: absolute; - margin-left: -7px; - margin-top: -5px; - width: 14px; - height: 14px; - cursor: pointer; - cursor: -webkit-grab; - cursor: grab; - border-radius: 50%; - border: solid 2px #96dbfa; - background-color: #fff; - -ms-touch-action: pan-x; - touch-action: pan-x; -} - -.rc-slider-handle:focus { - border-color: #57c5f7; - box-shadow: 0 0 0 5px #96dbfa; - outline: none; -} - -.rc-slider-handle-click-focused:focus { - border-color: #96dbfa; - box-shadow: unset; -} - -.rc-slider-handle:hover { - border-color: #57c5f7; -} - -.rc-slider-handle:active { - border-color: #57c5f7; - box-shadow: 0 0 5px #57c5f7; - cursor: -webkit-grabbing; - cursor: grabbing; -} - -.rc-slider-mark { - position: absolute; - top: 18px; - left: 0; - width: 100%; - font-size: 12px; -} - -.rc-slider-mark-text { - position: absolute; - display: inline-block; - vertical-align: middle; - text-align: center; - cursor: pointer; - color: #999; -} - -.rc-slider-mark-text-active { - color: #666; -} - -.rc-slider-step { - position: absolute; - width: 100%; - height: 4px; - background: transparent; -} - -.rc-slider-dot { - position: absolute; - bottom: -2px; - margin-left: -4px; - width: 8px; - height: 8px; - border: 2px solid #e9e9e9; - background-color: #fff; - cursor: pointer; - border-radius: 50%; - vertical-align: middle; -} - -.rc-slider-dot-active { - border-color: #96dbfa; -} - -.rc-slider-disabled { - opacity: 0.2; -} - -.rc-slider-disabled .rc-slider-track { - background-color: #ccc; -} - -.rc-slider-disabled .rc-slider-handle, -.rc-slider-disabled .rc-slider-dot { - border-color: #ccc; - box-shadow: none; - background-color: #fff; - cursor: not-allowed; -} - -.rc-slider-disabled .rc-slider-mark-text, -.rc-slider-disabled .rc-slider-dot { - cursor: not-allowed !important; -} - -.rc-slider-vertical { - width: 14px; - height: 100%; - padding: 0 5px; -} - -.rc-slider-vertical .rc-slider-rail { - height: 100%; - width: 4px; -} - -.rc-slider-vertical .rc-slider-track { - left: 5px; - bottom: 0; - width: 4px; -} - -.rc-slider-vertical .rc-slider-handle { - margin-left: -5px; - margin-bottom: -7px; - -ms-touch-action: pan-y; - touch-action: pan-y; -} - -.rc-slider-vertical .rc-slider-mark { - top: 0; - left: 18px; - height: 100%; -} - -.rc-slider-vertical .rc-slider-step { - height: 100%; - width: 4px; -} - -.rc-slider-vertical .rc-slider-dot { - left: 2px; - margin-bottom: -4px; -} - -.rc-slider-vertical .rc-slider-dot:first-child { - margin-bottom: -4px; -} - -.rc-slider-vertical .rc-slider-dot:last-child { - margin-bottom: -4px; -} - -.rc-slider-tooltip-zoom-down-enter, -.rc-slider-tooltip-zoom-down-appear { - animation-duration: .3s; - animation-fill-mode: both; - display: block !important; - animation-play-state: paused; -} - -.rc-slider-tooltip-zoom-down-leave { - animation-duration: .3s; - animation-fill-mode: both; - display: block !important; - animation-play-state: paused; -} - -.rc-slider-tooltip-zoom-down-enter.rc-slider-tooltip-zoom-down-enter-active, -.rc-slider-tooltip-zoom-down-appear.rc-slider-tooltip-zoom-down-appear-active { - animation-name: rcSliderTooltipZoomDownIn; - animation-play-state: running; -} - -.rc-slider-tooltip-zoom-down-leave.rc-slider-tooltip-zoom-down-leave-active { - animation-name: rcSliderTooltipZoomDownOut; - animation-play-state: running; -} - -.rc-slider-tooltip-zoom-down-enter, -.rc-slider-tooltip-zoom-down-appear { - transform: scale(0, 0); - animation-timing-function: cubic-bezier(0.23, 1, 0.32, 1); -} - -.rc-slider-tooltip-zoom-down-leave { - animation-timing-function: cubic-bezier(0.755, 0.05, 0.855, 0.06); -} - -@keyframes rcSliderTooltipZoomDownIn { - 0% { - opacity: 0; - transform-origin: 50% 100%; - transform: scale(0, 0); - } - - 100% { - transform-origin: 50% 100%; - transform: scale(1, 1); - } -} - -@keyframes rcSliderTooltipZoomDownOut { - 0% { - transform-origin: 50% 100%; - transform: scale(1, 1); - } - - 100% { - opacity: 0; - transform-origin: 50% 100%; - transform: scale(0, 0); - } -} - -.rc-slider-tooltip { - position: absolute; - left: -9999px; - top: -9999px; - visibility: visible; - box-sizing: border-box; - -webkit-tap-highlight-color: rgba(0, 0, 0, 0); -} - -.rc-slider-tooltip * { - box-sizing: border-box; - -webkit-tap-highlight-color: rgba(0, 0, 0, 0); -} - -.rc-slider-tooltip-hidden { - display: none; -} - -.rc-slider-tooltip-placement-top { - padding: 4px 0 8px 0; -} - -.rc-slider-tooltip-inner { - padding: 4px 6px 4px; - min-width: 24px; - height: 24px; - font-size: 12px; - line-height: 1; - color: #000; - text-align: center; - text-decoration: none; -} - -.rc-slider-tooltip-arrow { - position: absolute; - width: 0; - height: 0; - border-color: transparent; - border-style: solid; -} - -.rc-slider-tooltip-placement-top .rc-slider-tooltip-arrow { - bottom: 4px; - left: 50%; - margin-left: -4px; - border-width: 4px 4px 0; - border-top-color: #6c6c6c; -} diff --git a/packages/website/ts/pages/instant/select.tsx b/packages/website/ts/pages/instant/select.tsx deleted file mode 100644 index d4146cfb0..000000000 --- a/packages/website/ts/pages/instant/select.tsx +++ /dev/null @@ -1,74 +0,0 @@ -import * as React from 'react'; -import styled from 'styled-components'; - -export interface SelectItemConfig { - label: string; - value?: string; - onClick?: () => void; -} - -interface SelectProps { - value?: string; - id: string; - items: SelectItemConfig[]; - emptyText?: string; - onChange?: (ev: React.ChangeEvent<HTMLSelectElement>) => void; - shouldIncludeEmpty: boolean; -} - -export const Select: React.FunctionComponent<SelectProps> = ({ - value, - id, - items, - shouldIncludeEmpty, - emptyText, - onChange, -}) => { - return ( - <Container> - <StyledSelect id={id} onChange={onChange}> - {shouldIncludeEmpty && <option value="">{emptyText}</option>} - {items.map((item, index) => ( - <option - key={`${id}-item-${index}`} - value={item.value} - selected={item.value === value} - onClick={item.onClick} - > - {item.label} - </option> - ))} - </StyledSelect> - <Caret width="12" height="7" fill="none" xmlns="http://www.w3.org/2000/svg"> - <path d="M11 1L6 6 1 1" stroke="#666" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" /> - </Caret> - </Container> - ); -}; - -Select.defaultProps = { - emptyText: 'Select...', - shouldIncludeEmpty: true, -}; - -const Container = styled.div` - background-color: #fff; - border-radius: 4px; - display: flex; - width: 100%; - position: relative; -`; - -const StyledSelect = styled.select` - appearance: none; - border: 0; - font-size: 1rem; - width: 100%; - padding: 20px 20px 20px 20px; -`; - -const Caret = styled.svg` - position: absolute; - right: 20px; - top: calc(50% - 4px); -`; |