Changeset View
Changeset View
Standalone View
Standalone View
web/cashtab/src/components/Common/ScanQRCode.js
import React, { useState } from 'react'; | import React, { useState } from 'react'; | ||||
import { Alert, Modal } from 'antd'; | import { Alert, Modal } from 'antd'; | ||||
import { QrcodeOutlined } from '@ant-design/icons'; | import { QrcodeOutlined } from '@ant-design/icons'; | ||||
import styled from 'styled-components'; | import styled from 'styled-components'; | ||||
import { BrowserQRCodeReader } from '@zxing/library'; | import { BrowserQRCodeReader } from '@zxing/library'; | ||||
import { currency } from '@components/Common/Ticker.js'; | import { currency } from '@components/Common/Ticker.js'; | ||||
import { Event } from '@utils/GoogleAnalytics'; | import { Event } from '@utils/GoogleAnalytics'; | ||||
import BigNumber from 'bignumber.js'; | |||||
const StyledScanQRCode = styled.span` | const StyledScanQRCode = styled.span` | ||||
display: block; | display: block; | ||||
`; | `; | ||||
const StyledModal = styled(Modal)` | const StyledModal = styled(Modal)` | ||||
width: 400px !important; | width: 400px !important; | ||||
height: 400px !important; | height: 400px !important; | ||||
Show All 35 Lines | export const ScanQRCode = ({ | ||||
const parseContent = content => { | const parseContent = content => { | ||||
let type = 'unknown'; | let type = 'unknown'; | ||||
let values = {}; | let values = {}; | ||||
// If what scanner reads from QR code begins with 'bitcoincash:' or 'simpleledger:' or their successor prefixes | // If what scanner reads from QR code begins with 'bitcoincash:' or 'simpleledger:' or their successor prefixes | ||||
if ( | if ( | ||||
content.split(currency.prefix).length > 1 || | content.split(currency.prefix).length > 1 || | ||||
content.split(currency.tokenPrefix).length > 1 | content.split(currency.tokenPrefix).length > 1 || | ||||
content.split('ecash:').length > 1 | |||||
Fabien: This is hacky. If you wrap this inside a factility such as `isCurrency()` or `isToken()` then… | |||||
) { | ) { | ||||
type = 'address'; | type = 'address'; | ||||
values = { address: content }; | |||||
// Check for params | |||||
// eg mercurymessenger.io | |||||
// ecash:qqd3qn4zazjhygk5a2vzw2gvqgqwempr4gtfza25mc?amount=500000 | |||||
const paramCheck = content.split('?'); | |||||
let cleanAddress = paramCheck[0]; | |||||
let queryString; | |||||
let amount = null; | |||||
if (paramCheck.length > 1) { | |||||
queryString = paramCheck[1]; | |||||
const addrParams = new URLSearchParams(queryString); | |||||
if (addrParams.has('amount')) { | |||||
// Amount in satoshis | |||||
try { | |||||
amount = new BigNumber( | |||||
parseInt(addrParams.get('amount')), | |||||
) | |||||
.div(1e8) | |||||
.toString(); | |||||
} catch (err) { | |||||
amount = null; | |||||
} | |||||
} | |||||
} | |||||
FabienUnsubmitted Not Done Inline ActionsThe same thing with this block, I don't see why it should only be a QR code thing. Fabien: The same thing with this block, I don't see why it should only be a QR code thing. | |||||
// NB for now, backend will only accept legacy prefixes | |||||
// So, convert `ecash:` to `bitcoincash:` | |||||
if (cleanAddress.split('ecash:').length > 1) { | |||||
cleanAddress = `bitcoincash:` + cleanAddress.split('ecash:')[1]; | |||||
FabienUnsubmitted Not Done Inline ActionsIs the checksum re-computed ? Fabien: Is the checksum re-computed ? | |||||
} | |||||
values = { address: cleanAddress, amount: amount }; | |||||
// Event("Category", "Action", "Label") | // Event("Category", "Action", "Label") | ||||
// Track number of successful QR code scans | // Track number of successful QR code scans | ||||
// BCH or slp? | // BCH or slp? | ||||
let eventLabel = currency.ticker; | let eventLabel = currency.ticker; | ||||
const isToken = content.split(currency.tokenPrefix).length > 1; | const isToken = content.split(currency.tokenPrefix).length > 1; | ||||
if (isToken) { | if (isToken) { | ||||
eventLabel = currency.tokenTicker; | eventLabel = currency.tokenTicker; | ||||
} | } | ||||
Show All 24 Lines | const scanForQrCode = async () => { | ||||
'test-area-qr-code-webcam', | 'test-area-qr-code-webcam', | ||||
); | ); | ||||
const result = parseContent(content.text); | const result = parseContent(content.text); | ||||
// stop scanning and fill form if it's an address | // stop scanning and fill form if it's an address | ||||
if (result.type === 'address') { | if (result.type === 'address') { | ||||
// Hide the scanner | // Hide the scanner | ||||
setVisible(false); | setVisible(false); | ||||
onScan(result.values.address); | onScan(result.values); | ||||
return teardownCodeReader(codeReader); | return teardownCodeReader(codeReader); | ||||
} | } | ||||
} catch (err) { | } catch (err) { | ||||
console.log(`Error in QR scanner:`); | console.log(`Error in QR scanner:`); | ||||
console.log(err); | console.log(err); | ||||
console.log(JSON.stringify(err.message)); | console.log(JSON.stringify(err.message)); | ||||
//setMobileErrorMsg(JSON.stringify(err.message)); | //setMobileErrorMsg(JSON.stringify(err.message)); | ||||
setError(err); | setError(err); | ||||
▲ Show 20 Lines • Show All 58 Lines • Show Last 20 Lines |
This is hacky. If you wrap this inside a factility such as isCurrency() or isToken() then you can have a single place to add new prefixes, and have it to work everywhere the same.
For now this is causing different behavior when pasting the address or using the QR code scanner.