Add QrCode & Copy to ShapeShift (#4322)
* Extract CopyIcon to ~/ui/Icons * Add copy & QrCode address * Default size 4 * Add bitcoin: link * use protocol links applicable to coin exchanged * Remove .only
This commit is contained in:
parent
e81787da34
commit
cb8fea3b5a
@ -18,6 +18,8 @@ import { observer } from 'mobx-react';
|
|||||||
import React, { Component, PropTypes } from 'react';
|
import React, { Component, PropTypes } from 'react';
|
||||||
import { FormattedMessage } from 'react-intl';
|
import { FormattedMessage } from 'react-intl';
|
||||||
|
|
||||||
|
import { CopyToClipboard, QrCode } from '~/ui';
|
||||||
|
|
||||||
import Value from '../Value';
|
import Value from '../Value';
|
||||||
import styles from '../shapeshift.css';
|
import styles from '../shapeshift.css';
|
||||||
|
|
||||||
@ -61,9 +63,7 @@ export default class AwaitingDepositStep extends Component {
|
|||||||
} }
|
} }
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<div className={ styles.hero }>
|
{ this.renderAddress(depositAddress, coinSymbol) }
|
||||||
{ depositAddress }
|
|
||||||
</div>
|
|
||||||
<div className={ styles.price }>
|
<div className={ styles.price }>
|
||||||
<div>
|
<div>
|
||||||
<FormattedMessage
|
<FormattedMessage
|
||||||
@ -79,4 +79,42 @@ export default class AwaitingDepositStep extends Component {
|
|||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
renderAddress (depositAddress, coinSymbol) {
|
||||||
|
const qrcode = (
|
||||||
|
<QrCode
|
||||||
|
className={ styles.qrcode }
|
||||||
|
value={ depositAddress }
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
let protocolLink = null;
|
||||||
|
|
||||||
|
// TODO: Expand for other coins where protocols are available
|
||||||
|
switch (coinSymbol) {
|
||||||
|
case 'BTC':
|
||||||
|
protocolLink = `bitcoin:${depositAddress}`;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className={ styles.addressInfo }>
|
||||||
|
{
|
||||||
|
protocolLink
|
||||||
|
? (
|
||||||
|
<a
|
||||||
|
href={ protocolLink }
|
||||||
|
target='_blank'
|
||||||
|
>
|
||||||
|
{ qrcode }
|
||||||
|
</a>
|
||||||
|
)
|
||||||
|
: qrcode
|
||||||
|
}
|
||||||
|
<div className={ styles.address }>
|
||||||
|
<CopyToClipboard data={ depositAddress } />
|
||||||
|
<span>{ depositAddress }</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -19,7 +19,10 @@ import React from 'react';
|
|||||||
|
|
||||||
import AwaitingDepositStep from './';
|
import AwaitingDepositStep from './';
|
||||||
|
|
||||||
|
const TEST_ADDRESS = '0x123456789123456789123456789123456789';
|
||||||
|
|
||||||
let component;
|
let component;
|
||||||
|
let instance;
|
||||||
|
|
||||||
function render () {
|
function render () {
|
||||||
component = shallow(
|
component = shallow(
|
||||||
@ -30,6 +33,7 @@ function render () {
|
|||||||
} }
|
} }
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
instance = component.instance();
|
||||||
|
|
||||||
return component;
|
return component;
|
||||||
}
|
}
|
||||||
@ -48,4 +52,61 @@ describe('modals/Shapeshift/AwaitingDepositStep', () => {
|
|||||||
render({ depositAddress: 'xyz' });
|
render({ depositAddress: 'xyz' });
|
||||||
expect(component.find('FormattedMessage').first().props().id).to.match(/awaitingDeposit/);
|
expect(component.find('FormattedMessage').first().props().id).to.match(/awaitingDeposit/);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('instance methods', () => {
|
||||||
|
describe('renderAddress', () => {
|
||||||
|
let address;
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
address = shallow(instance.renderAddress(TEST_ADDRESS));
|
||||||
|
});
|
||||||
|
|
||||||
|
it('renders the address', () => {
|
||||||
|
expect(address.text()).to.contain(TEST_ADDRESS);
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('CopyToClipboard', () => {
|
||||||
|
let copy;
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
copy = address.find('Connect(CopyToClipboard)');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('renders the copy', () => {
|
||||||
|
expect(copy.length).to.equal(1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('passes the address', () => {
|
||||||
|
expect(copy.props().data).to.equal(TEST_ADDRESS);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('QrCode', () => {
|
||||||
|
let qr;
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
qr = address.find('QrCode');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('renders the QrCode', () => {
|
||||||
|
expect(qr.length).to.equal(1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('passed the address', () => {
|
||||||
|
expect(qr.props().value).to.equal(TEST_ADDRESS);
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('protocol link', () => {
|
||||||
|
it('does not render a protocol link (unlinked type)', () => {
|
||||||
|
expect(address.find('a')).to.have.length(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('renders protocol link for BTC', () => {
|
||||||
|
address = shallow(instance.renderAddress(TEST_ADDRESS, 'BTC'));
|
||||||
|
expect(address.find('a').props().href).to.equal(`bitcoin:${TEST_ADDRESS}`);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
@ -14,9 +14,28 @@
|
|||||||
/* You should have received a copy of the GNU General Public License
|
/* You should have received a copy of the GNU General Public License
|
||||||
/* along with Parity. If not, see <http://www.gnu.org/licenses/>.
|
/* along with Parity. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
.body {
|
.body {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.addressInfo {
|
||||||
|
text-align: center;
|
||||||
|
|
||||||
|
.address {
|
||||||
|
background: rgba(255, 255, 255, 0.1);
|
||||||
|
margin: 0.75em 0;
|
||||||
|
padding: 1em;
|
||||||
|
|
||||||
|
span {
|
||||||
|
margin-left: 0.75em;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.qrcode {
|
||||||
|
margin: 0.75em 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
.shapeshift {
|
.shapeshift {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
bottom: 0.5em;
|
bottom: 0.5em;
|
||||||
|
@ -14,21 +14,21 @@
|
|||||||
// You should have received a copy of the GNU General Public License
|
// You should have received a copy of the GNU General Public License
|
||||||
// along with Parity. If not, see <http://www.gnu.org/licenses/>.
|
// along with Parity. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
import { IconButton } from 'material-ui';
|
||||||
import React, { Component, PropTypes } from 'react';
|
import React, { Component, PropTypes } from 'react';
|
||||||
|
import Clipboard from 'react-copy-to-clipboard';
|
||||||
import { connect } from 'react-redux';
|
import { connect } from 'react-redux';
|
||||||
import { bindActionCreators } from 'redux';
|
import { bindActionCreators } from 'redux';
|
||||||
|
|
||||||
import { IconButton } from 'material-ui';
|
|
||||||
import Clipboard from 'react-copy-to-clipboard';
|
|
||||||
import CopyIcon from 'material-ui/svg-icons/content/content-copy';
|
|
||||||
import Theme from '../Theme';
|
|
||||||
|
|
||||||
import { showSnackbar } from '~/redux/providers/snackbarActions';
|
import { showSnackbar } from '~/redux/providers/snackbarActions';
|
||||||
|
|
||||||
const { textColor, disabledTextColor } = Theme.flatButton;
|
import { CopyIcon } from '../Icons';
|
||||||
|
import Theme from '../Theme';
|
||||||
|
|
||||||
import styles from './copyToClipboard.css';
|
import styles from './copyToClipboard.css';
|
||||||
|
|
||||||
|
const { textColor, disabledTextColor } = Theme.flatButton;
|
||||||
|
|
||||||
class CopyToClipboard extends Component {
|
class CopyToClipboard extends Component {
|
||||||
static propTypes = {
|
static propTypes = {
|
||||||
showSnackbar: PropTypes.func.isRequired,
|
showSnackbar: PropTypes.func.isRequired,
|
||||||
|
@ -22,6 +22,7 @@ import CloseIcon from 'material-ui/svg-icons/navigation/close';
|
|||||||
import CompareIcon from 'material-ui/svg-icons/action/compare-arrows';
|
import CompareIcon from 'material-ui/svg-icons/action/compare-arrows';
|
||||||
import ComputerIcon from 'material-ui/svg-icons/hardware/desktop-mac';
|
import ComputerIcon from 'material-ui/svg-icons/hardware/desktop-mac';
|
||||||
import ContractIcon from 'material-ui/svg-icons/action/code';
|
import ContractIcon from 'material-ui/svg-icons/action/code';
|
||||||
|
import CopyIcon from 'material-ui/svg-icons/content/content-copy';
|
||||||
import DashboardIcon from 'material-ui/svg-icons/action/dashboard';
|
import DashboardIcon from 'material-ui/svg-icons/action/dashboard';
|
||||||
import DeleteIcon from 'material-ui/svg-icons/action/delete';
|
import DeleteIcon from 'material-ui/svg-icons/action/delete';
|
||||||
import DoneIcon from 'material-ui/svg-icons/action/done-all';
|
import DoneIcon from 'material-ui/svg-icons/action/done-all';
|
||||||
@ -50,6 +51,7 @@ export {
|
|||||||
CompareIcon,
|
CompareIcon,
|
||||||
ComputerIcon,
|
ComputerIcon,
|
||||||
ContractIcon,
|
ContractIcon,
|
||||||
|
CopyIcon,
|
||||||
DashboardIcon,
|
DashboardIcon,
|
||||||
DeleteIcon,
|
DeleteIcon,
|
||||||
DoneIcon,
|
DoneIcon,
|
||||||
|
@ -34,7 +34,7 @@ export default class QrCode extends Component {
|
|||||||
|
|
||||||
static defaultProps = {
|
static defaultProps = {
|
||||||
margin: 2,
|
margin: 2,
|
||||||
size: 5
|
size: 4
|
||||||
};
|
};
|
||||||
|
|
||||||
state = {
|
state = {
|
||||||
|
Loading…
Reference in New Issue
Block a user