├── .editorconfig
├── .gitignore
├── .npmignore
├── CONTRIBUTING.md
├── LICENSE
├── README.md
├── assets
├── example-background-image.png
├── example-code-styles.png
├── example-inner-eye-styles.png
├── example-linear-gradient.png
├── example-logo.png
├── example-outer-eye-styles.png
├── qr-code-1.png
├── qr-code-2.png
└── qr-code-3.png
├── index.js
├── lib
├── QRCode.js
├── QRCodeGenerator.js
└── styles
│ ├── codeStyles
│ ├── circle.js
│ ├── diamond.js
│ ├── dot.js
│ ├── index.js
│ ├── ninja.js
│ ├── sharp.js
│ └── square.js
│ ├── index.js
│ ├── innerEyeStyles
│ ├── circle.js
│ ├── diamond.js
│ ├── index.js
│ └── square.js
│ └── outerEyeStyles
│ ├── circle.js
│ ├── diamond.js
│ ├── index.js
│ └── square.js
├── package-lock.json
└── package.json
/.editorconfig:
--------------------------------------------------------------------------------
1 |
2 | # http://editorconfig.org
3 | root = true
4 |
5 | [*]
6 | indent_style = space
7 | indent_size = 2
8 | end_of_line = lf
9 | charset = utf-8
10 | trim_trailing_whitespace = true
11 | insert_final_newline = true
12 |
13 | [*.md]
14 | trim_trailing_whitespace = false
15 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 |
2 | # Logs
3 | *.log
4 |
5 | # Dependency directory
6 | node_modules
7 |
--------------------------------------------------------------------------------
/.npmignore:
--------------------------------------------------------------------------------
1 | *.log
2 | node_modules
3 | Example
4 | assets
5 | .DS_Store
6 | .editorconfig
7 | .travis.yml
8 |
--------------------------------------------------------------------------------
/CONTRIBUTING.md:
--------------------------------------------------------------------------------
1 | # Contributing
2 |
3 | Thank you for taking the time to try and make this project better!
4 |
5 | ## Reporting Bugs & Feature Requests
6 |
7 | If you have found an issue, create an issue on the repo- but make sure to:
8 | * Describe what does happen
9 | * Describe what should happen instead
10 | *i.e. In what way the functionality is different from desired.*
11 |
12 | If you would like to request a feature, then by all means and we will try to implement it if reasonable.
13 |
14 | If you would like to submit a feature request or report a bug, we encourage you to first look through the [issues](https://github.com/nating/react-native-custom-qr-codes/issues) and [pull requests](https://github.com/nating/react-native-custom-qr-codes/pulls) before filing a new issue.
15 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2017 Geoffrey Natin
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 |
2 | # react-native-custom-qr-codes-expo
3 |
4 |
A react-native-custom-qr-codes fork that plays ball nicely with Expo
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 | Customisable QR Codes for React Native.
17 |
18 |
19 | ## Installation
20 |
21 | `npm install react-native-custom-qr-codes-expo`
22 |
23 | If you are not using Expo, you will also have to manually link the [react-native-svg library](https://github.com/react-native-community/react-native-svg).
24 | Follow [the instructions here](https://github.com/react-native-community/react-native-svg#manual) to do this.
25 |
26 | ## Usage
27 |
28 |
29 | ```jsx
30 | import { QRCode } from 'react-native-custom-qr-codes-expo';
31 |
32 |
33 | ```
34 |
35 | ### Properties
36 |
37 | | Prop | Description | Default |
38 | |---|---|---|
39 | |**`content`**|The String to be encoded in the QR code. |`'No Content'`|
40 | |**`codeStyle`**|The style of the centre QR Code pieces. |`square`|
41 | |**`outerEyeStyle`**|The style of the outside of the QR Code's eyes. |`square`|
42 | |**`innerEyeStyle`**|The style of the inside of the QR Code's eyes. |`square`|
43 | |**`size`**|The width & height of the component. |`250`|
44 | |**`color`**|The color of the QR Code. |`black`|
45 | |**`backgroundColor`**|The background color of the component. |`white`|
46 | |**`padding`**|The padding between the edge of the component and the QR Code itself (In terms of QR code piece sizes). |`1`|
47 | |**`logo`**|The image to be put in the centre of the QR Code. **Must use a higher `ecl` for QR Code to work with a logo. (L->M->Q->H)** |none|
48 | |**`logoSize`**|The size of the logo in the QR Code. |none|
49 | |**`linearGradient`**|The two colors to be used for the linear gradient for the foreground. |none|
50 | |**`gradientDirection`**|The numbers that [define the orientation of the linear gradient](https://developer.mozilla.org/en-US/docs/Web/SVG/Tutorial/Gradients). |`[0,0,170,0]`|
51 | |**`backgroundImage`**|The image to be used as the filling of the QR Code pieces. **The Eyes can not be styled if a background image is used.**|none|
52 | |**`ecl`**|The [error correction level](http://www.qrcode.com/en/about/error_correction.html) of the QR Code. |`L`|
53 |
54 | ## Examples
55 |
56 | ### `codeStyle`
57 | ```jsx
58 |
59 |
60 |
61 |
62 |
63 | ```
64 |
65 |
66 | ### `outerEyeStyle`
67 | ```jsx
68 |
69 |
70 |
71 | ```
72 |
73 |
74 | ### `innerEyeStyle`
75 | ```jsx
76 |
77 |
78 |
79 | ```
80 |
81 |
82 | ### logo
83 | ```jsx
84 |
85 | ```
86 |
87 |
88 | ### linearGradient
89 | ```jsx
90 |
91 |
92 | ```
93 |
94 |
95 | ### backgroundImage
96 | ```jsx
97 |
98 | ```
99 |
100 |
101 | ## Contributing
102 |
103 | Take a look at [CONTRIBUTING.md](./CONTRIBUTING.md) 😁
104 |
105 | ## License
106 |
107 | [MIT License](http://opensource.org/licenses/mit-license.html). © Geoffrey Natin 2017
108 |
--------------------------------------------------------------------------------
/assets/example-background-image.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/example-background-image.png
--------------------------------------------------------------------------------
/assets/example-code-styles.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/example-code-styles.png
--------------------------------------------------------------------------------
/assets/example-inner-eye-styles.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/example-inner-eye-styles.png
--------------------------------------------------------------------------------
/assets/example-linear-gradient.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/example-linear-gradient.png
--------------------------------------------------------------------------------
/assets/example-logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/example-logo.png
--------------------------------------------------------------------------------
/assets/example-outer-eye-styles.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/example-outer-eye-styles.png
--------------------------------------------------------------------------------
/assets/qr-code-1.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/qr-code-1.png
--------------------------------------------------------------------------------
/assets/qr-code-2.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/qr-code-2.png
--------------------------------------------------------------------------------
/assets/qr-code-3.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/eddyoc/react-native-custom-qr-codes-expo/e09a6fde01637d5cbd3a12c960a489b559720ed1/assets/qr-code-3.png
--------------------------------------------------------------------------------
/index.js:
--------------------------------------------------------------------------------
1 | export { default as QRCode } from './lib/QRCode';
2 |
--------------------------------------------------------------------------------
/lib/QRCode.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | QRCode.js
4 |
5 | This is a Customisable QR Code Component for React Native Applications.
6 |
7 | --Geoff Natin 08/7/17 21:49
8 |
9 | */
10 |
11 |
12 | //-----------------------------Imports-----------------------------------
13 | import React, { PureComponent } from 'react';
14 | import { View, Image, Text, Button } from 'react-native';
15 | import PropTypes from 'prop-types';
16 | import { generateQRCode } from './QRCodeGenerator.js';
17 | import { drawPiece } from './styles';
18 | import Svg, { Rect, Defs, ClipPath, LinearGradient, Stop } from 'react-native-svg';
19 |
20 | //-----------------------------Component---------------------------------
21 | export default class QRCode extends PureComponent {
22 |
23 | //-----------------------Properties---------------------
24 | static propTypes = {
25 | content: PropTypes.string,
26 | size: PropTypes.number,
27 | padding: PropTypes.number,
28 | color: PropTypes.string,
29 | linearGradient: PropTypes.arrayOf(PropTypes.string),
30 | gradientDirection: PropTypes.arrayOf(PropTypes.number),
31 | backgroundColor: PropTypes.string,
32 | innerEyeStyle: PropTypes.oneOf(['square', 'circle', 'diamond']),
33 | outerEyeStyle: PropTypes.oneOf(['square', 'circle', 'diamond']),
34 | codeStyle: PropTypes.oneOf(['square', 'circle', 'diamond', 'dot', 'ninja', 'sharp']),
35 | logo: Image.propTypes.source,
36 | backgroundImage: Image.propTypes.source,
37 | logoSize: PropTypes.number,
38 | ecl: PropTypes.oneOf(['L', 'M', 'Q', 'H'])
39 | };
40 |
41 | static defaultProps = {
42 | content: "No Content",
43 | size: 250,
44 | padding: 1,
45 | color: 'black',
46 | gradientDirection: [0, 0, 170, 0],
47 | backgroundColor: 'white',
48 | codeStyle: 'square',
49 | outerEyeStyle: 'square',
50 | innerEyeStyle: 'square',
51 | logoSize: 100,
52 | ecl: 'H'
53 | };
54 |
55 | //-----------------------Methods-----------------------
56 |
57 | //Returns an array of SVG Elements that represent the pieces of the QR Code
58 | getPieces() {
59 | var qr = generateQRCode(this.props);
60 |
61 | var modules = qr.qrcode.modules;
62 |
63 | var size = this.props.size;
64 | var length = modules.length;
65 | var xsize = size / (length + 2 * this.props.padding);
66 | var ysize = size / (length + 2 * this.props.padding);
67 | var logoX = ((this.props.size / 2) - (this.props.logoSize / 2));
68 | var logoY = ((this.props.size / 2) - (this.props.logoSize / 2));
69 | var logoSize = this.props.logoSize;
70 |
71 | var pieces = [];
72 | var nonPieces = [];
73 |
74 | //Add the SVG element of each piece in the body of the QR Code
75 | for (var y = 0; y < length; y++) {
76 | for (var x = 0; x < length; x++) {
77 | var module = modules[x][y];
78 | var px = (x * xsize + this.props.padding * xsize);
79 | var py = (y * ysize + this.props.padding * ysize);
80 |
81 | //TODO: Add function to compute if pieces overlap with circular logos (more complex. Must see if tl or br is inside the radius from the centre of the circle (pythagoras theorem?))
82 | var overlapsWithLogo = (
83 |
84 | px > logoX && px < (logoX + logoSize) && py > logoY && py < (logoY + logoSize) ||//Piece's top left is inside the logo area
85 | (px + xsize) > logoX && (px + xsize) < (logoX + logoSize) && (py + ysize) > logoY && (py + ysize) < (logoY + logoSize)//Piece's bottom right is inside the logo area
86 |
87 | );
88 |
89 | if (!this.props.logo || (this.props.logo && !overlapsWithLogo)) {
90 |
91 | if (module) {
92 | pieces.push(this.getPiece(x, y, modules));
93 | } else {
94 | nonPieces.push(this.getPiece(x, y, modules));
95 | }
96 | }
97 | }
98 | }
99 |
100 | if (this.props.backgroundImage) {
101 | const { size } = this.props;
102 | return (
103 |
104 |
111 | {this.displayLogo()}
112 |
113 |
114 |
115 | {nonPieces}
116 |
117 |
118 |
119 |
120 |
121 | );
122 | } else if (this.props.linearGradient) {
123 | const { size, backgroundColor = 'transparent' } = this.props;
124 | return (
125 |
126 |
127 |
128 |
129 | {pieces}
130 |
131 |
133 |
134 |
135 |
136 |
137 |
138 |
139 | {this.displayLogo()}
140 |
141 | );
142 | } else {
143 | const { size, backgroundColor = 'transparent' } = this.props;
144 | return (
145 |
146 |
147 |
148 |
149 | {pieces}
150 |
151 |
152 |
153 |
154 | {this.displayLogo()}
155 |
156 | );
157 | }
158 | }
159 |
160 | //Renders the logo on top of the QR Code if there is one
161 | displayLogo() {
162 | const { logo, size, logoSize } = this.props;
163 |
164 | if (logo) {
165 | return (
166 |
176 | );
177 | } else {
178 | return (
179 |
180 | );
181 | }
182 | }
183 |
184 | //Returns an SVG Element that represents the piece of the QR code at modules[x][y]
185 | getPiece(x, y, modules) {
186 | // Find out which piece type it is
187 | const pieceProps = this.getPieceProperties(x, y, modules);
188 | return drawPiece(x, y, modules, pieceProps, this.props);
189 | }
190 |
191 | // Returns an object with orientation and pieceType representation of the piece type. (See https://github.com/mpaolino/qrlib/tree/master/qrlib/static)
192 | getPieceProperties(x, y, modules) {
193 | var mod_matrix = {};
194 | mod_matrix.topLeft = (x != 0 && y != 0 && modules[x - 1][y - 1]);
195 | mod_matrix.top = (y != 0 && modules[x][y - 1]);
196 | mod_matrix.topRight = (x != modules.length - 1 && y != 0 && modules[x + 1][y - 1]);
197 | mod_matrix.left = (x != 0 && modules[x - 1][y]);
198 | mod_matrix.right = (x != modules.length - 1 && modules[x + 1][y]);
199 | mod_matrix.bottomLeft = (x != 0 && y != modules.length - 1 && modules[x - 1][y + 1]);
200 | mod_matrix.bottom = (y != modules.length - 1 && modules[x][y + 1]);
201 | mod_matrix.bottomRight = (x != modules.length - 1 && y != modules.length - 1 && modules[x + 1][y + 1]);
202 |
203 | // (surroundingCount holds the number of pieces above or to the side of this piece)
204 | var surroundingCount = 0;
205 | if (mod_matrix.top) {
206 | surroundingCount++;
207 | }
208 | if (mod_matrix.left) {
209 | surroundingCount++;
210 | }
211 | if (mod_matrix.right) {
212 | surroundingCount++;
213 | }
214 | if (mod_matrix.bottom) {
215 | surroundingCount++;
216 | }
217 |
218 | var pieceProperties = {};
219 | var orientation = 0;
220 |
221 | //Determine what the piece properties are from its surrounding pieces.
222 | // (surroundingCount holds the number of pieces above or to the side of this piece)
223 | // (See https://github.com/mpaolino/qrlib/tree/master/qrlib/static)
224 | switch (surroundingCount) {
225 | case 0:
226 | pieceProperties.pieceType = '1a';
227 | if (mod_matrix.right) {
228 | orientation = 90;
229 | } else if (mod_matrix.bottom) {
230 | orientation = 180;
231 | } else if (mod_matrix.left) {
232 | orientation = 270;
233 | }
234 | pieceProperties.orientation = orientation;
235 | return pieceProperties;
236 | case 1:
237 | pieceProperties.pieceType = '2b';
238 | pieceProperties.orientation = 0;
239 | return pieceProperties;
240 | case 2:
241 | if ((mod_matrix.top && mod_matrix.bottom) || (mod_matrix.left && mod_matrix.right)) {
242 | var orientation = (mod_matrix.top && mod_matrix.bottom) ? 0 : 90;
243 | pieceProperties.pieceType = '1b3b';
244 | pieceProperties.orientation = orientation;
245 | return pieceProperties;
246 | } else {
247 | var orientation = 0;
248 | if (mod_matrix.top && mod_matrix.right) {
249 | pieceProperties.orientation = 90;
250 | pieceProperties.pieceType = mod_matrix.topRight ? '2a1b1a' : '2a1b';
251 | return pieceProperties;
252 | } else if (mod_matrix.right && mod_matrix.bottom) {
253 | pieceProperties.orientation = 180;
254 | pieceProperties.pieceType = mod_matrix.bottomRight ? '2a1b1a' : '2a1b';
255 | return pieceProperties;
256 | } else if (mod_matrix.left && mod_matrix.bottom) {
257 | pieceProperties.orientation = 270;
258 | pieceProperties.pieceType = mod_matrix.bottomLeft ? '2a1b1a' : '2a1b';
259 | return pieceProperties;
260 | } else {
261 | pieceProperties.pieceType = mod_matrix.topLeft ? '2a1b1a' : '2a1b';
262 | return pieceProperties;
263 | }
264 | }
265 | case 3:
266 | pieceProperties.pieceType = '2a1b2c';
267 | var orientation = 0;
268 | if (mod_matrix.top && mod_matrix.right && mod_matrix.bottom) {
269 | orientation = 90;
270 | } else if (mod_matrix.right && mod_matrix.bottom && mod_matrix.left) {
271 | orientation = 180;
272 | } else if (mod_matrix.bottom && mod_matrix.left && mod_matrix.top) {
273 | orientation = 270;
274 | }
275 | pieceProperties.orientation = orientation;
276 | return pieceProperties;
277 | case 4:
278 | pieceProperties.pieceType = '2a1b2c3b';
279 | pieceProperties.orientation = 0;
280 | return pieceProperties;
281 | }
282 | }
283 |
284 | //---------------------Rendering-----------------------
285 |
286 | render() {
287 | return this.getPieces();
288 | }
289 | }
290 |
--------------------------------------------------------------------------------
/lib/QRCodeGenerator.js:
--------------------------------------------------------------------------------
1 | /**
2 | * @fileoverview
3 | * - modified davidshimjs/qrcodejs library for use in node.js
4 | * - Using the 'QRCode for Javascript library'
5 | * - Fixed dataset of 'QRCode for Javascript library' for support full-spec.
6 | * - this library has no dependencies.
7 | *
8 | * @version 0.9.1 (2016-02-12)
9 | * @author davidshimjs, papnkukn
10 | * @see http://www.d-project.com/
11 | * @see http://jeromeetienne.github.com/jquery-qrcode/
12 | * @see https://github.com/davidshimjs/qrcodejs
13 | */
14 |
15 | //---------------------------------------------------------------------
16 | // QRCode for JavaScript
17 | //
18 | // Copyright (c) 2009 Kazuhiko Arase
19 | //
20 | // URL: http://www.d-project.com/
21 | //
22 | // Licensed under the MIT license:
23 | // http://www.opensource.org/licenses/mit-license.php
24 | //
25 | // The word "QR Code" is registered trademark of
26 | // DENSO WAVE INCORPORATED
27 | // http://www.denso-wave.com/qrcode/faqpatent-e.html
28 | //
29 | //---------------------------------------------------------------------
30 |
31 | //Returns an SVG of a QR Code created using the properties object
32 | export function generateQRCode(props){
33 | var myQRCode = new QRCode(props);
34 | return myQRCode;
35 | }
36 |
37 | function QR8bitByte(data) {
38 | this.mode = QRMode.MODE_8BIT_BYTE;
39 | this.data = data;
40 | this.parsedData = [];
41 |
42 | // Added to support UTF-8 Characters
43 | for (var i = 0, l = this.data.length; i < l; i++) {
44 | var byteArray = [];
45 | var code = this.data.charCodeAt(i);
46 |
47 | if (code > 0x10000) {
48 | byteArray[0] = 0xF0 | ((code & 0x1C0000) >>> 18);
49 | byteArray[1] = 0x80 | ((code & 0x3F000) >>> 12);
50 | byteArray[2] = 0x80 | ((code & 0xFC0) >>> 6);
51 | byteArray[3] = 0x80 | (code & 0x3F);
52 | } else if (code > 0x800) {
53 | byteArray[0] = 0xE0 | ((code & 0xF000) >>> 12);
54 | byteArray[1] = 0x80 | ((code & 0xFC0) >>> 6);
55 | byteArray[2] = 0x80 | (code & 0x3F);
56 | } else if (code > 0x80) {
57 | byteArray[0] = 0xC0 | ((code & 0x7C0) >>> 6);
58 | byteArray[1] = 0x80 | (code & 0x3F);
59 | } else {
60 | byteArray[0] = code;
61 | }
62 |
63 | this.parsedData.push(byteArray);
64 | }
65 |
66 | this.parsedData = Array.prototype.concat.apply([], this.parsedData);
67 |
68 | if (this.parsedData.length != this.data.length) {
69 | this.parsedData.unshift(191);
70 | this.parsedData.unshift(187);
71 | this.parsedData.unshift(239);
72 | }
73 | }
74 |
75 | QR8bitByte.prototype = {
76 | getLength: function (buffer) {
77 | return this.parsedData.length;
78 | },
79 | write: function (buffer) {
80 | for (var i = 0, l = this.parsedData.length; i < l; i++) {
81 | buffer.put(this.parsedData[i], 8);
82 | }
83 | }
84 | };
85 |
86 | function QRCodeModel(typeNumber, errorCorrectLevel) {
87 | this.typeNumber = typeNumber;
88 | this.errorCorrectLevel = errorCorrectLevel;
89 | this.modules = null;
90 | this.moduleCount = 0;
91 | this.dataCache = null;
92 | this.dataList = [];
93 | }
94 |
95 | QRCodeModel.prototype={addData:function(data){var newData=new QR8bitByte(data);this.dataList.push(newData);this.dataCache=null;},isDark:function(row,col){if(row<0||this.moduleCount<=row||col<0||this.moduleCount<=col){throw new Error(row+","+col);}
96 | return this.modules[row][col];},getModuleCount:function(){return this.moduleCount;},make:function(){this.makeImpl(false,this.getBestMaskPattern());},makeImpl:function(test,maskPattern){this.moduleCount=this.typeNumber*4+17;this.modules=new Array(this.moduleCount);for(var row=0;row=7){this.setupTypeNumber(test);}
98 | if(this.dataCache==null){this.dataCache=QRCodeModel.createData(this.typeNumber,this.errorCorrectLevel,this.dataList);}
99 | this.mapData(this.dataCache,maskPattern);},setupPositionProbePattern:function(row,col){for(var r=-1;r<=7;r++){if(row+r<=-1||this.moduleCount<=row+r)continue;for(var c=-1;c<=7;c++){if(col+c<=-1||this.moduleCount<=col+c)continue;if((0<=r&&r<=6&&(c==0||c==6))||(0<=c&&c<=6&&(r==0||r==6))||(2<=r&&r<=4&&2<=c&&c<=4)){this.modules[row+r][col+c]=true;}else{this.modules[row+r][col+c]=false;}}}},getBestMaskPattern:function(){var minLostPoint=0;var pattern=0;for(var i=0;i<8;i++){this.makeImpl(true,i);var lostPoint=QRUtil.getLostPoint(this);if(i==0||minLostPoint>lostPoint){minLostPoint=lostPoint;pattern=i;}}
100 | return pattern;},createMovieClip:function(target_mc,instance_name,depth){var qr_mc=target_mc.createEmptyMovieClip(instance_name,depth);var cs=1;this.make();for(var row=0;row>i)&1)==1);this.modules[Math.floor(i/3)][i%3+this.moduleCount-8-3]=mod;}
106 | for(var i=0;i<18;i++){var mod=(!test&&((bits>>i)&1)==1);this.modules[i%3+this.moduleCount-8-3][Math.floor(i/3)]=mod;}},setupTypeInfo:function(test,maskPattern){var data=(this.errorCorrectLevel<<3)|maskPattern;var bits=QRUtil.getBCHTypeInfo(data);for(var i=0;i<15;i++){var mod=(!test&&((bits>>i)&1)==1);if(i<6){this.modules[i][8]=mod;}else if(i<8){this.modules[i+1][8]=mod;}else{this.modules[this.moduleCount-15+i][8]=mod;}}
107 | for(var i=0;i<15;i++){var mod=(!test&&((bits>>i)&1)==1);if(i<8){this.modules[8][this.moduleCount-i-1]=mod;}else if(i<9){this.modules[8][15-i-1+1]=mod;}else{this.modules[8][15-i-1]=mod;}}
108 | this.modules[this.moduleCount-8][8]=(!test);},mapData:function(data,maskPattern){var inc=-1;var row=this.moduleCount-1;var bitIndex=7;var byteIndex=0;for(var col=this.moduleCount-1;col>0;col-=2){if(col==6)col--;while(true){for(var c=0;c<2;c++){if(this.modules[row][col-c]==null){var dark=false;if(byteIndex>>bitIndex)&1)==1);}
109 | var mask=QRUtil.getMask(maskPattern,row,col-c);if(mask){dark=!dark;}
110 | this.modules[row][col-c]=dark;bitIndex--;if(bitIndex==-1){byteIndex++;bitIndex=7;}}}
111 | row+=inc;if(row<0||this.moduleCount<=row){row-=inc;inc=-inc;break;}}}}};QRCodeModel.PAD0=0xEC;QRCodeModel.PAD1=0x11;QRCodeModel.createData=function(typeNumber,errorCorrectLevel,dataList){var rsBlocks=QRRSBlock.getRSBlocks(typeNumber,errorCorrectLevel);var buffer=new QRBitBuffer();for(var i=0;itotalDataCount*8){throw new Error("code length overflow. ("
114 | +buffer.getLengthInBits()
115 | +">"
116 | +totalDataCount*8
117 | +")");}
118 | if(buffer.getLengthInBits()+4<=totalDataCount*8){buffer.put(0,4);}
119 | while(buffer.getLengthInBits()%8!=0){buffer.putBit(false);}
120 | while(true){if(buffer.getLengthInBits()>=totalDataCount*8){break;}
121 | buffer.put(QRCodeModel.PAD0,8);if(buffer.getLengthInBits()>=totalDataCount*8){break;}
122 | buffer.put(QRCodeModel.PAD1,8);}
123 | return QRCodeModel.createBytes(buffer,rsBlocks);};QRCodeModel.createBytes=function(buffer,rsBlocks){var offset=0;var maxDcCount=0;var maxEcCount=0;var dcdata=new Array(rsBlocks.length);var ecdata=new Array(rsBlocks.length);for(var r=0;r=0)?modPoly.get(modIndex):0;}}
125 | var totalCodeCount=0;for(var i=0;i=0){d^=(QRUtil.G15<<(QRUtil.getBCHDigit(d)-QRUtil.getBCHDigit(QRUtil.G15)));}
129 | return((data<<10)|d)^QRUtil.G15_MASK;},getBCHTypeNumber:function(data){var d=data<<12;while(QRUtil.getBCHDigit(d)-QRUtil.getBCHDigit(QRUtil.G18)>=0){d^=(QRUtil.G18<<(QRUtil.getBCHDigit(d)-QRUtil.getBCHDigit(QRUtil.G18)));}
130 | return(data<<12)|d;},getBCHDigit:function(data){var digit=0;while(data!=0){digit++;data>>>=1;}
131 | return digit;},getPatternPosition:function(typeNumber){return QRUtil.PATTERN_POSITION_TABLE[typeNumber-1];},getMask:function(maskPattern,i,j){switch(maskPattern){case QRMaskPattern.PATTERN000:return(i+j)%2==0;case QRMaskPattern.PATTERN001:return i%2==0;case QRMaskPattern.PATTERN010:return j%3==0;case QRMaskPattern.PATTERN011:return(i+j)%3==0;case QRMaskPattern.PATTERN100:return(Math.floor(i/2)+Math.floor(j/3))%2==0;case QRMaskPattern.PATTERN101:return(i*j)%2+(i*j)%3==0;case QRMaskPattern.PATTERN110:return((i*j)%2+(i*j)%3)%2==0;case QRMaskPattern.PATTERN111:return((i*j)%3+(i+j)%2)%2==0;default:throw new Error("bad maskPattern:"+maskPattern);}},getErrorCorrectPolynomial:function(errorCorrectLength){var a=new QRPolynomial([1],0);for(var i=0;i5){lostPoint+=(3+sameCount-5);}}}
137 | for(var row=0;row=256){n-=255;}
144 | return QRMath.EXP_TABLE[n];},EXP_TABLE:new Array(256),LOG_TABLE:new Array(256)};for(var i=0;i<8;i++){QRMath.EXP_TABLE[i]=1<>>(7-index%8))&1)==1;},put:function(num,length){for(var i=0;i>>(length-i-1))&1)==1);}},getLengthInBits:function(){return this.length;},putBit:function(bit){var bufIndex=Math.floor(this.length/8);if(this.buffer.length<=bufIndex){this.buffer.push(0);}
159 | if(bit){this.buffer[bufIndex]|=(0x80>>>(this.length%8));}
160 | this.length++;}};var QRCodeLimitLength=[[17,14,11,7],[32,26,20,14],[53,42,32,24],[78,62,46,34],[106,84,60,44],[134,106,74,58],[154,122,86,64],[192,152,108,84],[230,180,130,98],[271,213,151,119],[321,251,177,137],[367,287,203,155],[425,331,241,177],[458,362,258,194],[520,412,292,220],[586,450,322,250],[644,504,364,280],[718,560,394,310],[792,624,442,338],[858,666,482,382],[929,711,509,403],[1003,779,565,439],[1091,857,611,461],[1171,911,661,511],[1273,997,715,535],[1367,1059,751,593],[1465,1125,805,625],[1528,1190,868,658],[1628,1264,908,698],[1732,1370,982,742],[1840,1452,1030,790],[1952,1538,1112,842],[2068,1628,1168,898],[2188,1722,1228,958],[2303,1809,1283,983],[2431,1911,1351,1051],[2563,1989,1423,1093],[2699,2099,1499,1139],[2809,2213,1579,1219],[2953,2331,1663,1273]];
161 |
162 |
163 | //---------------------------------------------------------------QR Code Object-----------------------------------------------------------------
164 |
165 | /** Constructor */
166 | function QRCode(options) {
167 | var instance = this;
168 |
169 | //Default options
170 | this.options = {
171 | padding: 4,
172 | width: 256,
173 | height: 256,
174 | typeNumber: 4,
175 | color: "#000000",
176 | background: "#ffffff",
177 | ecl: "H"
178 | };
179 |
180 | //In case the options is string
181 | if (typeof options === 'string') {
182 | options = {
183 | content: options
184 | };
185 | }
186 |
187 | //Merge options
188 | if (options) {
189 | for (var i in options) {
190 | this.options[i] = options[i];
191 | }
192 | }
193 |
194 | if (typeof this.options.content !== 'string') {
195 | throw new Error("Expected 'content' as string!");
196 | }
197 |
198 | if (this.options.content.length === 0 /* || this.options.content.length > 7089 */) {
199 | throw new Error("Expected 'content' to be non-empty!");
200 | }
201 |
202 | if (!(this.options.padding >= 0)) {
203 | throw new Error("Expected 'padding' value to be non-negative!");
204 | }
205 |
206 | if (!(this.options.width > 0) || !(this.options.height > 0)) {
207 | throw new Error("Expected 'width' or 'height' value to be higher than zero!");
208 | }
209 |
210 | //Gets the error correction level
211 | function _getErrorCorrectLevel(ecl) {
212 | switch (ecl) {
213 | case "L":
214 | return QRErrorCorrectLevel.L;
215 |
216 | case "M":
217 | return QRErrorCorrectLevel.M;
218 |
219 | case "Q":
220 | return QRErrorCorrectLevel.Q;
221 |
222 | case "H":
223 | return QRErrorCorrectLevel.H;
224 |
225 | default:
226 | throw new Error("Unknown error correction level: " + ecl);
227 | }
228 | }
229 |
230 | //Get type number
231 | function _getTypeNumber(content, ecl) {
232 | var length = _getUTF8Length(content);
233 |
234 | var type = 1;
235 | var limit = 0;
236 | for (var i = 0, len = QRCodeLimitLength.length; i <= len; i++) {
237 | var table = QRCodeLimitLength[i];
238 | if (!table) {
239 | throw new Error("Content too long: expected " + limit + " but got " + length);
240 | }
241 |
242 | switch (ecl) {
243 | case "L":
244 | limit = table[0];
245 | break;
246 |
247 | case "M":
248 | limit = table[1];
249 | break;
250 |
251 | case "Q":
252 | limit = table[2];
253 | break;
254 |
255 | case "H":
256 | limit = table[3];
257 | break;
258 |
259 | default:
260 | throw new Error("Unknwon error correction level: " + ecl);
261 | }
262 |
263 | if (length <= limit) {
264 | break;
265 | }
266 |
267 | type++;
268 | }
269 |
270 | if (type > QRCodeLimitLength.length) {
271 | throw new Error("Content too long");
272 | }
273 |
274 | return type;
275 | }
276 |
277 | //Gets text length
278 | function _getUTF8Length(content) {
279 | var result = encodeURI(content).toString().replace(/\%[0-9a-fA-F]{2}/g, 'a');
280 | return result.length + (result.length != content ? 3 : 0);
281 | }
282 |
283 | //Generate QR Code matrix
284 | var content = this.options.content;
285 | var type = _getTypeNumber(content, this.options.ecl);
286 | var ecl = _getErrorCorrectLevel(this.options.ecl);
287 | this.qrcode = new QRCodeModel(type, ecl);
288 | this.qrcode.addData(content);
289 | this.qrcode.make();
290 | }
291 |
292 | //----------------------------------------------------Drawing out the QR Code as an SVG image------------------------------------------------------------
293 |
294 | /** Generates QR Code as SVG image */
295 | QRCode.prototype.svg = function(opt) {
296 | if (typeof opt == "undefined") {
297 | opt = { container: "svg" };
298 | }
299 |
300 | var options = this.options;
301 | var modules = this.qrcode.modules;
302 |
303 | var EOL = '\r\n';
304 | var width = options.width;
305 | var height = options.height;
306 | var length = modules.length;
307 | var style = options.style;
308 | var xsize = width / (length + 2 * options.padding);
309 | var ysize = height / (length + 2 * options.padding);
310 |
311 | var rect = ' ' + EOL;
312 |
313 | //Add the SVG element of each square in the body of the QR Code
314 | for (var y = 0; y < length; y++) {
315 | for (var x = 0; x < length; x++) {
316 | var module = modules[x][y];
317 | if (module) {
318 | //rect += ' ' + EOL;
319 | //options.style = 'sharp-edge';
320 | rect += getShape(x,y,modules,options);
321 | //rect += ' ' + EOL;
322 | }
323 | }
324 | }
325 |
326 | //This works when creating a big black sharp-edge
327 | //rect = ' ' + EOL;
328 |
329 | var svg = "";
330 | switch (opt.container) {
331 | case "svg":
332 | // !!!! The following line of code may need access to the internet to run...
333 | svg += '' + EOL + '' + EOL;
334 | svg += rect;
335 | svg += ' ';
336 | break;
337 |
338 | case "g":
339 | svg += '' + EOL;
340 | svg += rect;
341 | svg += ' ';
342 | break;
343 |
344 | default:
345 | svg += rect;
346 | break;
347 | }
348 |
349 | return svg;
350 | };
351 |
352 | /*Returns an svg element in the right shape determined by the surrounding modules and the qr code style*/
353 | function getShape(x,y,modules,options){
354 |
355 | //Get the surrounding modules matrix
356 | var mod_matrix = {};
357 | mod_matrix.topLeft = (x!=0 && y!=0 && modules[x-1][y-1]);
358 | mod_matrix.top = (y!=0 && modules[x][y-1]);
359 | mod_matrix.topRight = (x!=modules.length-1 && y!=0 && modules[x+1][y-1]);
360 | mod_matrix.left = (x!=0 && modules[x-1][y]);
361 | mod_matrix.right = (x!=modules.length-1 && modules[x+1][y]);
362 | mod_matrix.bottomLeft = (x!=0 && y!=modules.length-1 && modules[x-1][y+1]);
363 | mod_matrix.bottom = (y!=modules.length-1 && modules[x][y+1]);
364 | mod_matrix.bottomRight = (x!=modules.length-1 && y!=modules.length-1 && modules[x+1][y+1]);
365 |
366 | var surroundingCount = 0;
367 | if(mod_matrix.top){surroundingCount++;}
368 | if(mod_matrix.left){surroundingCount++;}
369 | if(mod_matrix.right){surroundingCount++;}
370 | if(mod_matrix.bottom){surroundingCount++;}
371 |
372 | //Find out box shape from surroundingCount and the orientation of those surrounding modules
373 | switch(surroundingCount){
374 | case 0:
375 | return getShapeZero(x,y,options,modules);
376 | case 1:
377 | return getShapeOne(x,y,options,modules,mod_matrix);
378 | case 2:
379 | return getShapeTwo(x,y,options,modules,mod_matrix);
380 | case 3:
381 | return getShapeThree(x,y,options,modules,mod_matrix);
382 | case 4:
383 | return getShapeFour(x,y,options,modules,mod_matrix);
384 | default:
385 | return getShapeZero(x,y,options,modules);
386 | }
387 | //This function checks that arrays a1 and a2 are the same:
388 | /* a1.length==a2.length && a1.every(function(v,i) { return v === a2[i]}) */
389 |
390 | }
391 |
392 | //Returns an SVG element for a box with no surrounding boxes
393 | function getShapeZero(x,y,options,modules){
394 |
395 | var EOL = '\r\n';
396 | var width = options.width;
397 | var height = options.height;
398 | var length = modules.length;
399 | var style = options.style;
400 | var xsize = width / (length + 2 * options.padding);
401 | var ysize = height / (length + 2 * options.padding);
402 | var px = (x * xsize + options.padding * xsize);
403 | var py = (y * ysize + options.padding * ysize);
404 |
405 | switch(options.style){
406 | case 'square':
407 | return ' ' + EOL;
408 | case 'circle':
409 | return ' ' + EOL;
410 | case 'sharp-edge':
411 | return ' ' + EOL;
412 | case 'ninja':
413 | return ' '
414 | }
415 | }
416 |
417 | //Returns an SVG element for a box with one surrounding box
418 | function getShapeOne(x,y,options,modules,mod_matrix){
419 |
420 | var EOL = '\r\n';
421 | var width = options.width;
422 | var height = options.height;
423 | var length = modules.length;
424 | var style = options.style;
425 | var xsize = width / (length + 2 * options.padding);
426 | var ysize = height / (length + 2 * options.padding);
427 | var px = (x * xsize + options.padding * xsize);
428 | var py = (y * ysize + options.padding * ysize);
429 |
430 | var orientation = 0;
431 | if(mod_matrix.right){orientation=90;}
432 | else if(mod_matrix.bottom){orientation=180;}
433 | else if(mod_matrix.left){orientation=270;}
434 |
435 | //Returning a 1b
436 | switch(options.style){
437 | case 'square':
438 | return ' ' + EOL;
439 | case 'circle':
440 | return ' ' + EOL;
441 | case 'sharp-edge':
442 | return ' ' + EOL;
443 | }
444 | }
445 |
446 | //Returns an SVG element for a box with two surrounding boxes
447 | function getShapeTwo(x,y,options,modules,mod_matrix){
448 |
449 | var EOL = '\r\n';
450 | var width = options.width;
451 | var height = options.height;
452 | var length = modules.length;
453 | var style = options.style;
454 | var xsize = width / (length + 2 * options.padding);
455 | var ysize = height / (length + 2 * options.padding);
456 | var px = (x * xsize + options.padding * xsize);
457 | var py = (y * ysize + options.padding * ysize);
458 |
459 | //If in the middle of a straight line, return a 1b3b
460 | if( (mod_matrix.top && mod_matrix.bottom) || (mod_matrix.left && mod_matrix.right) ){
461 | var orientation = (mod_matrix.top && mod_matrix.bottom) ? 0 : 90;
462 | switch(options.style){
463 | case 'square':
464 | return ' ' + EOL;
465 | case 'circle':
466 | return ' ' + EOL;
467 | case 'sharp-edge':
468 | return ' ' + EOL;
469 | }
470 | }
471 |
472 | //If a diagonal is in between the two surrounding (module is on a corner), return a 2a1b1a
473 | if(mod_matrix.topLeft || mod_matrix.topRight || mod_matrix.bottomLeft || mod_matrix.bottomRight){
474 |
475 | var orientation = 0;
476 | if(mod_matrix.top && mod_matrix.topRight && mod_matrix.right){orientation=90;}
477 | else if(mod_matrix.right && mod_matrix.bottomRight && mod_matrix.bottom){orientation=180;}
478 | else if(mod_matrix.left && mod_matrix.bottomLeft && mod_matrix.bottom){orientation=270;}
479 |
480 | switch(options.style){
481 | case 'square':
482 | return ' ' + EOL;
483 | case 'circle':
484 | return ' ' + EOL;
485 | case 'sharp-edge':
486 | return ' ' + EOL;
487 | }
488 | }
489 |
490 | //Else in the center of a right angle
491 | var orientation = 0;
492 | if(mod_matrix.top && mod_matrix.right){orientation=90;}
493 | else if(mod_matrix.right && mod_matrix.bottom){orientation=180;}
494 | else if(mod_matrix.bottom && mod_matrix.left){orientation=270;}
495 |
496 | switch(options.style){
497 | case 'square':
498 | return ' ' + EOL;
499 | case 'circle':
500 | return ' ' + EOL;
501 | case 'sharp-edge':
502 | return ' ' + EOL;
503 | }
504 | }
505 |
506 | //Returns an SVG element for a box with one surrounding box
507 | function getShapeThree(x,y,options,modules,mod_matrix){
508 |
509 | var EOL = '\r\n';
510 | var width = options.width;
511 | var height = options.height;
512 | var length = modules.length;
513 | var style = options.style;
514 | var xsize = width / (length + 2 * options.padding);
515 | var ysize = height / (length + 2 * options.padding);
516 | var px = (x * xsize + options.padding * xsize);
517 | var py = (y * ysize + options.padding * ysize);
518 |
519 | //in two supplementary right angle
520 | var orientation = 0;
521 | if(mod_matrix.top && mod_matrix.right && mod_matrix.bottom){orientation=90;}
522 | else if(mod_matrix.right && mod_matrix.bottom && mod_matrix.left){orientation=180;}
523 | else if(mod_matrix.bottom && mod_matrix.left && mod_matrix.top){orientation=270;}
524 |
525 | switch(options.style){
526 | case 'square':
527 | return ' ' + EOL;
528 | case 'circle':
529 | return ' ' + EOL;
530 | case 'sharp-edge':
531 | return ' ' + EOL;
532 | }
533 | }
534 |
535 | //Returns an SVG element for a box with one surrounding box
536 | function getShapeFour(x,y,options,modules,mod_matrix){
537 |
538 | var EOL = '\r\n';
539 | var width = options.width;
540 | var height = options.height;
541 | var length = modules.length;
542 | var style = options.style;
543 | var xsize = width / (length + 2 * options.padding);
544 | var ysize = height / (length + 2 * options.padding);
545 | var px = (x * xsize + options.padding * xsize);
546 | var py = (y * ysize + options.padding * ysize);
547 |
548 | //Else in the center of a horizontal-vertical cross
549 | var orientation = 0;
550 |
551 | switch(options.style){
552 | case 'square':
553 | return ' ' + EOL;
554 | case 'circle':
555 | return ' ' + EOL;
556 | case 'sharp-edge':
557 | return ' ' + EOL;
558 | }
559 | }
560 |
561 | if (typeof module != "undefined") {
562 | module.exports = { QRCode, generateQRCode };
563 | }
564 |
--------------------------------------------------------------------------------
/lib/styles/codeStyles/circle.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | circle.js
4 |
5 | This file exports a function for drawing a circle centre piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Circle } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'circle' codeStyle
14 | export const drawCirclePiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize)+xsize/2;
21 | var py = (y * ysize + props.padding * ysize)+ysize/2;
22 | return (
23 |
24 | );
25 | };
26 |
--------------------------------------------------------------------------------
/lib/styles/codeStyles/diamond.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | diamond.js
4 |
5 | This file exports a function for drawing a diamond centre piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Rect, G } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'diamond' codeStyle
14 | export const drawDiamondPiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize);
21 | var py = (y * ysize + props.padding * ysize);
22 | return (
23 |
24 |
25 |
26 | );
27 | };
28 |
--------------------------------------------------------------------------------
/lib/styles/codeStyles/dot.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | dot.js
4 |
5 | This file exports a function for drawing a dot centre piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Circle } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'dot' codeStyle
14 | export const drawDotPiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize)+xsize/2;
21 | var py = (y * ysize + props.padding * ysize)+ysize/2;
22 | return (
23 |
24 | );
25 | }
26 |
--------------------------------------------------------------------------------
/lib/styles/codeStyles/index.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | index.js
4 |
5 | This file exports a function for drawing the centre pieces of a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 |
11 | import { drawSquarePiece } from './square';
12 | import { drawCirclePiece } from './circle';
13 | import { drawDotPiece } from './dot';
14 | import { drawDiamondPiece } from './diamond';
15 | import { drawSharpPiece } from './sharp';
16 | import { drawNinjaPiece } from './ninja';
17 |
18 | //Returns an SVG Element for a centre piece in the style of the codeStyle
19 | export function drawCentrePiece(x,y,modules,pieceProperties,props){
20 | switch(props.codeStyle){
21 | case 'square':
22 | return drawSquarePiece(x,y,modules,pieceProperties,props);
23 | case 'circle':
24 | return drawCirclePiece(x,y,modules,pieceProperties,props);
25 | case 'dot':
26 | return drawDotPiece(x,y,modules,pieceProperties,props);
27 | case 'diamond':
28 | return drawDiamondPiece(x,y,modules,pieceProperties,props);
29 | case 'sharp':
30 | return drawSharpPiece(x,y,modules,pieceProperties,props);
31 | case 'ninja':
32 | return drawNinjaPiece(x,y,modules,pieceProperties,props);
33 | default:
34 | return drawSquarePiece(x,y,modules,pieceProperties,props);
35 | }
36 | }
37 |
--------------------------------------------------------------------------------
/lib/styles/codeStyles/ninja.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | ninja.js
4 |
5 | This file exports a function for drawing a ninja centre piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Rect } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'ninja' codeStyle
14 | export const drawNinjaPiece = (x,y,modules,pieceProperties,props) => {
15 |
16 | var orientation = pieceProperties.orientation;
17 | var pieceType = pieceProperties.pieceType;
18 | var width = props.size;
19 | var height = props.size;
20 | var length = modules.length;
21 | var xsize = width / (length + 2 * props.padding);
22 | var ysize = height / (length + 2 * props.padding);
23 | var px = (x * xsize + props.padding * xsize);
24 | var py = (y * ysize + props.padding * ysize);
25 |
26 | // !!!! These aren't the proper paths yet
27 | switch(pieceType){
28 | case '2b':
29 | return ( );
30 | case '1b':
31 | return ( );
32 | case '1b3b':
33 | return ( );
34 | case '2a1b':
35 | return ( );
36 | case '2a1b1a':
37 | return ( );
38 | case '2a1b2c':
39 | return ( );
40 | case '2a1b2c3b':
41 | return ( );
42 | default:
43 | return ( );
44 | }
45 | };
46 |
--------------------------------------------------------------------------------
/lib/styles/codeStyles/sharp.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | sharp.js
4 |
5 | This file exports a function for drawing a sharp centre piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Rect, Circle } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'sharp' codeStyle
14 | export const drawSharpPiece = (x,y,modules,pieceProperties,props) => {
15 | var orientation = pieceProperties.orientation;
16 | var pieceType = pieceProperties.pieceType;
17 | var width = props.size;
18 | var height = props.size;
19 | var length = modules.length;
20 | var xsize = width / (length + 2 * props.padding);
21 | var ysize = height / (length + 2 * props.padding);
22 | var px = (x * xsize + props.padding * xsize);
23 | var py = (y * ysize + props.padding * ysize);
24 |
25 | // !!!! These aren't the proper paths yet
26 | var str = (xsize)+','+0+' '+(xsize)+','+(ysize)+' '+0+','+(ysize);
27 | var rotationStr = orientation+', '+(xsize/2)+', '+(ysize/2);
28 |
29 | switch(pieceType){
30 | case '1a':
31 | return ( );
32 | case '2b':
33 | return ( );
34 | case '1b3b':
35 | return ( );
36 | case '2a1b':
37 | return ( );
38 | case '2a1b1a':
39 | return ( );
40 | case '2a1b2c':
41 | return ( );
42 | case '2a1b2c3b':
43 | return ( );
44 | default:
45 | return ( );
46 | }
47 | };
48 |
--------------------------------------------------------------------------------
/lib/styles/codeStyles/square.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | square.js
4 |
5 | This file exports a function for drawing a square centre piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Rect } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'square' codeStyle
14 | export function drawSquarePiece(x,y,modules,pieceProperties,props){
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize);
21 | var py = (y * ysize + props.padding * ysize);
22 | return (
23 |
24 | );
25 | }
26 |
--------------------------------------------------------------------------------
/lib/styles/index.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | index.js
4 |
5 | This file exports a function for drawing a piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 |
11 | import { drawOuterEyePiece } from './outerEyeStyles';
12 | import { drawInnerEyePiece } from './innerEyeStyles';
13 | import { drawCentrePiece } from './codeStyles';
14 |
15 | //Returns an SVG Element for a piece in the style of the codeStyle
16 | export function drawPiece(x,y,modules,pieceProperties,props){
17 |
18 | //Check the QR Code the piece is a part of: Centre, Inner Eye, or Outer Eye
19 | var length = modules.length;
20 |
21 | if( //If in the corners of the QR Code
22 | (x<7 && y<7) ||
23 | (x<7 && (length-y)<8) ||
24 | ((length-x)<8 && y<7)
25 | ){
26 | if(//If part of the Outer Eye
27 | x==0 ||
28 | y==0 ||
29 | x==6 ||
30 | y==6 ||
31 | x==(length-1) ||
32 | y==(length-1) ||
33 | (length-y)==7 ||
34 | (length-x)==7
35 | ){
36 | return drawOuterEyePiece(x,y,modules,pieceProperties,props);
37 | }
38 | else{//If part of Inner Eye
39 | return drawInnerEyePiece(x,y,modules,pieceProperties,props);
40 | }
41 | }
42 | else{
43 | return drawCentrePiece(x,y,modules,pieceProperties,props);
44 | }
45 | }
46 |
--------------------------------------------------------------------------------
/lib/styles/innerEyeStyles/circle.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | circle.js
4 |
5 | This file exports a function for drawing a circle outer eye piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Circle } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'circle' outerEyeStyle
14 | export const drawCirclePiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize)+xsize/2;
21 | var py = (y * ysize + props.padding * ysize)+ysize/2;
22 | return (
23 |
24 | );
25 | };
26 |
--------------------------------------------------------------------------------
/lib/styles/innerEyeStyles/diamond.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | diamond.js
4 |
5 | This file exports a function for drawing a diamond outer eye piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React from 'react';
11 | import { Rect, G } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'diamond' outerEyeStyle
14 | export const drawDiamondPiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize);
21 | var py = (y * ysize + props.padding * ysize);
22 | return (
23 |
24 |
25 |
26 | );
27 | };
28 |
--------------------------------------------------------------------------------
/lib/styles/innerEyeStyles/index.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | index.js
4 |
5 | This file exports a function for drawing the inner eye pieces of a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 |
11 | import { drawSquarePiece } from './square';
12 | import { drawCirclePiece } from './circle';
13 | import { drawDiamondPiece } from './diamond';
14 |
15 | //Returns an SVG Element for an outer eye piece in the style of the innerEyeStyle
16 | export function drawInnerEyePiece(x,y,modules,pieceProperties,props){
17 | switch(props.innerEyeStyle){
18 | case 'square':
19 | return drawSquarePiece(x,y,modules,pieceProperties,props);
20 | case 'circle':
21 | return drawCirclePiece(x,y,modules,pieceProperties,props);
22 | case 'diamond':
23 | return drawDiamondPiece(x,y,modules,pieceProperties,props);
24 | default:
25 | return drawSquarePiece(x,y,modules,pieceProperties,props);
26 | }
27 | }
28 |
--------------------------------------------------------------------------------
/lib/styles/innerEyeStyles/square.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | square.js
4 |
5 | This file exports a function for drawing a square outer eye piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React from 'react';
11 | import { Rect } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'square' outerEyeStyle
14 | export const drawSquarePiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize);
21 | var py = (y * ysize + props.padding * ysize);
22 | return (
23 |
24 | );
25 | };
26 |
--------------------------------------------------------------------------------
/lib/styles/outerEyeStyles/circle.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | circle.js
4 |
5 | This file exports a function for drawing a circle outer eye piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React from 'react';
11 | import { Circle } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'circle' outerEyeStyle
14 | export const drawCirclePiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize)+xsize/2;
21 | var py = (y * ysize + props.padding * ysize)+ysize/2;
22 | return (
23 |
24 | );
25 | };
26 |
--------------------------------------------------------------------------------
/lib/styles/outerEyeStyles/diamond.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | diamond.js
4 |
5 | This file exports a function for drawing a diamond outer eye piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Rect, G } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'diamond' outerEyeStyle
14 | export const drawDiamondPiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize);
21 | var py = (y * ysize + props.padding * ysize);
22 | return (
23 |
24 |
25 |
26 | );
27 | };
28 |
--------------------------------------------------------------------------------
/lib/styles/outerEyeStyles/index.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | index.js
4 |
5 | This file exports a function for drawing the outer eye pieces of a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 |
11 | import { drawSquarePiece } from './square';
12 | import { drawCirclePiece } from './circle';
13 | import { drawDiamondPiece } from './diamond';
14 |
15 | //Returns an SVG Element for an outer eye piece in the style of the outerEyeStyle
16 | export function drawOuterEyePiece(x,y,modules,pieceProperties,props){
17 | switch(props.outerEyeStyle){
18 | case 'square':
19 | return drawSquarePiece(x,y,modules,pieceProperties,props);
20 | case 'circle':
21 | return drawCirclePiece(x,y,modules,pieceProperties,props);
22 | case 'diamond':
23 | return drawDiamondPiece(x,y,modules,pieceProperties,props);
24 | default:
25 | return drawSquarePiece(x,y,modules,pieceProperties,props);
26 | }
27 | }
28 |
--------------------------------------------------------------------------------
/lib/styles/outerEyeStyles/square.js:
--------------------------------------------------------------------------------
1 | /*
2 |
3 | square.js
4 |
5 | This file exports a function for drawing a square outer eye piece for a QRCode
6 |
7 | --Geoff Natin 11/1/18 17:41
8 |
9 | */
10 | import React, { Component } from 'react';
11 | import { Rect } from 'react-native-svg';
12 |
13 | //Returns an SVG Element for a piece of the 'square' outerEyeStyle
14 | export const drawSquarePiece = (x,y,modules,pieceProperties,props) => {
15 | var length = modules.length;
16 | var width = props.size;
17 | var height = props.size;
18 | var xsize = width / (length + 2 * props.padding);
19 | var ysize = height / (length + 2 * props.padding);
20 | var px = (x * xsize + props.padding * xsize);
21 | var py = (y * ysize + props.padding * ysize);
22 | return (
23 |
24 | );
25 | };
26 |
--------------------------------------------------------------------------------
/package-lock.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "react-native-custom-qr-codes-expo",
3 | "version": "2.0.0",
4 | "lockfileVersion": 1,
5 | "requires": true,
6 | "dependencies": {
7 | "asap": {
8 | "version": "2.0.6",
9 | "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz",
10 | "integrity": "sha1-5QNHYR1+aQlDIIu9r+vLwvuGbUY="
11 | },
12 | "core-js": {
13 | "version": "1.2.7",
14 | "resolved": "https://registry.npmjs.org/core-js/-/core-js-1.2.7.tgz",
15 | "integrity": "sha1-ZSKUwUZR2yj6k70tX/KYOk8IxjY="
16 | },
17 | "encoding": {
18 | "version": "0.1.12",
19 | "resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.12.tgz",
20 | "integrity": "sha1-U4tm8+5izRq1HsMjgp0flIDHS+s=",
21 | "requires": {
22 | "iconv-lite": "~0.4.13"
23 | }
24 | },
25 | "fbjs": {
26 | "version": "0.8.16",
27 | "resolved": "https://registry.npmjs.org/fbjs/-/fbjs-0.8.16.tgz",
28 | "integrity": "sha1-XmdDL1UNxBtXK/VYR7ispk5TN9s=",
29 | "requires": {
30 | "core-js": "^1.0.0",
31 | "isomorphic-fetch": "^2.1.1",
32 | "loose-envify": "^1.0.0",
33 | "object-assign": "^4.1.0",
34 | "promise": "^7.1.1",
35 | "setimmediate": "^1.0.5",
36 | "ua-parser-js": "^0.7.9"
37 | }
38 | },
39 | "iconv-lite": {
40 | "version": "0.4.19",
41 | "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz",
42 | "integrity": "sha1-90aPYBNfXl2tM5nAqBvpoWA6CCs="
43 | },
44 | "is-stream": {
45 | "version": "1.1.0",
46 | "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz",
47 | "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ="
48 | },
49 | "isomorphic-fetch": {
50 | "version": "2.2.1",
51 | "resolved": "https://registry.npmjs.org/isomorphic-fetch/-/isomorphic-fetch-2.2.1.tgz",
52 | "integrity": "sha1-YRrhrPFPXoH3KVB0coGf6XM1WKk=",
53 | "requires": {
54 | "node-fetch": "^1.0.1",
55 | "whatwg-fetch": ">=0.10.0"
56 | }
57 | },
58 | "js-tokens": {
59 | "version": "3.0.2",
60 | "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz",
61 | "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls="
62 | },
63 | "loose-envify": {
64 | "version": "1.3.1",
65 | "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.3.1.tgz",
66 | "integrity": "sha1-0aitM/qc4OcT1l/dCsi3SNR4yEg=",
67 | "requires": {
68 | "js-tokens": "^3.0.0"
69 | }
70 | },
71 | "node-fetch": {
72 | "version": "1.7.3",
73 | "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-1.7.3.tgz",
74 | "integrity": "sha1-mA9vcthSEaU0fGsrwYxbhMPrR+8=",
75 | "requires": {
76 | "encoding": "^0.1.11",
77 | "is-stream": "^1.0.1"
78 | }
79 | },
80 | "object-assign": {
81 | "version": "4.1.1",
82 | "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz",
83 | "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM="
84 | },
85 | "promise": {
86 | "version": "7.3.1",
87 | "resolved": "https://registry.npmjs.org/promise/-/promise-7.3.1.tgz",
88 | "integrity": "sha1-BktyYCsY+Q8pGSuLG8QY/9Hr078=",
89 | "requires": {
90 | "asap": "~2.0.3"
91 | }
92 | },
93 | "prop-types": {
94 | "version": "15.6.0",
95 | "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.6.0.tgz",
96 | "integrity": "sha1-zq8IMCL8RrSjX2nhPvda7Q1jmFY=",
97 | "requires": {
98 | "fbjs": "^0.8.16",
99 | "loose-envify": "^1.3.1",
100 | "object-assign": "^4.1.1"
101 | }
102 | },
103 | "setimmediate": {
104 | "version": "1.0.5",
105 | "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz",
106 | "integrity": "sha1-KQy7Iy4waULX1+qbg3Mqt4VvgoU="
107 | },
108 | "ua-parser-js": {
109 | "version": "0.7.17",
110 | "resolved": "https://registry.npmjs.org/ua-parser-js/-/ua-parser-js-0.7.17.tgz",
111 | "integrity": "sha1-6exflJi57JEOeuOsYmqAXE0J7Kw="
112 | },
113 | "whatwg-fetch": {
114 | "version": "2.0.3",
115 | "resolved": "https://registry.npmjs.org/whatwg-fetch/-/whatwg-fetch-2.0.3.tgz",
116 | "integrity": "sha1-nITsLc9oGH/wC8ZOEnS0QhduHIQ="
117 | }
118 | }
119 | }
120 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "react-native-custom-qr-codes-expo",
3 | "version": "2.2.0",
4 | "main": "index.js",
5 | "description": "A customisable QR code component for React Native applications. Compatible with Expo",
6 | "keywords": [
7 | "react-native",
8 | "react-native-component",
9 | "react",
10 | "mobile",
11 | "ios",
12 | "android",
13 | "qr-code",
14 | "custom-qr-code"
15 | ],
16 | "author": {
17 | "name": "Geoffrey Natin",
18 | "email": "nating@tcd.ie",
19 | "url": "https://github.com/nating"
20 | },
21 | "homepage": "https://github.com/eddyoc/react-native-custom-qr-codes-expo",
22 | "repository": {
23 | "type": "git",
24 | "url": "git://github.com/eddyoc/react-native-custom-qr-codes-expo.git"
25 | },
26 | "bugs": {
27 | "url": "https://github.com/eddyoc/react-native-custom-qr-codes-expo/issues"
28 | },
29 | "license": "MIT",
30 | "dependencies": {
31 | "prop-types": "^15.7.2"
32 | },
33 | "peerDependencies": {
34 | "expo": "~34.0.3",
35 | "react-native-svg": "~9.5.1"
36 | }
37 | }
38 |
--------------------------------------------------------------------------------