1import { UnavailabilityError } from 'expo-errors';
2import mapValues from 'lodash.mapvalues';
3import PropTypes from 'prop-types';
4import React from 'react';
5import { Platform, ViewPropTypes } from 'react-native';
6import ExpoBarCodeScannerModule from './ExpoBarCodeScannerModule';
7import ExpoBarCodeScannerView from './ExpoBarCodeScannerView';
8const { BarCodeType, Type } = ExpoBarCodeScannerModule;
9const EVENT_THROTTLE_MS = 500;
10export class BarCodeScanner extends React.Component {
11    constructor() {
12        super(...arguments);
13        this.lastEvents = {};
14        this.lastEventsTimes = {};
15        // coordinates of cornerPoints and boundingBox are represented in DP (Display-Indepent Points) unit
16        // React Native is using the same unit
17        this.onObjectDetected = (callback) => ({ nativeEvent, }) => {
18            const { type } = nativeEvent;
19            if (this.lastEvents[type] &&
20                this.lastEventsTimes[type] &&
21                JSON.stringify(nativeEvent) === this.lastEvents[type] &&
22                Date.now() - this.lastEventsTimes[type] < EVENT_THROTTLE_MS) {
23                return;
24            }
25            if (callback) {
26                callback(nativeEvent);
27                this.lastEventsTimes[type] = new Date();
28                this.lastEvents[type] = JSON.stringify(nativeEvent);
29            }
30        };
31    }
32    static async scanFromURLAsync(url, barCodeTypes = Object.values(BarCodeType)) {
33        if (!ExpoBarCodeScannerModule.scanFromURLAsync) {
34            throw new UnavailabilityError('expo-barcode-scanner', 'scanFromURLAsync');
35        }
36        if (Array.isArray(barCodeTypes) && !barCodeTypes.length) {
37            throw new Error('No barCodeTypes specified; provide at least one barCodeType for scanner');
38        }
39        if (Platform.OS === 'ios') {
40            if (Array.isArray(barCodeTypes) && !barCodeTypes.includes(BarCodeType.qr)) {
41                // Only QR type is supported on iOS, fail if one tries to use other types
42                throw new Error('Only QR type is supported by scanFromURLAsync() on iOS');
43            }
44            // on iOS use only supported QR type
45            return await ExpoBarCodeScannerModule.scanFromURLAsync(url, [BarCodeType.qr]);
46        }
47        // On other platforms, if barCodeTypes is not provided, use all available types
48        return await ExpoBarCodeScannerModule.scanFromURLAsync(url, barCodeTypes);
49    }
50    render() {
51        const nativeProps = this.convertNativeProps(this.props);
52        const { onBarCodeScanned } = this.props;
53        return (<ExpoBarCodeScannerView {...nativeProps} onBarCodeScanned={this.onObjectDetected(onBarCodeScanned)}/>);
54    }
55    convertNativeProps(props) {
56        const newProps = mapValues(props, this.convertProp);
57        return newProps;
58    }
59    convertProp(value, key) {
60        if (typeof value === 'string' && BarCodeScanner.ConversionTables[key]) {
61            return BarCodeScanner.ConversionTables[key][value];
62        }
63        return value;
64    }
65}
66BarCodeScanner.Constants = {
67    BarCodeType,
68    Type,
69};
70BarCodeScanner.ConversionTables = {
71    type: Type,
72};
73BarCodeScanner.propTypes = {
74    ...ViewPropTypes,
75    onBarCodeScanned: PropTypes.func,
76    barCodeTypes: PropTypes.array,
77    type: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
78};
79BarCodeScanner.defaultProps = {
80    type: Type.back,
81    barCodeTypes: Object.values(BarCodeType),
82};
83export const { Constants } = BarCodeScanner;
84//# sourceMappingURL=BarCodeScanner.js.map