\r
package com.google.zxing.qrcode.decoder;\r
\r
+import com.google.zxing.common.BitMatrix;\r
+\r
/**\r
* <p>Encapsulates data masks for the data bits in a QR code, per ISO 18004:2006 6.8. Implementations\r
* of this class can un-mask a raw BitMatrix. For simplicity, they will unmask the entire BitMatrix,\r
* <p>Implementations of this method reverse the data masking process applied to a QR Code and\r
* make its bits ready to read.</p>\r
*\r
- * @param bits representation of QR Code bits from {@link com.google.zxing.common.BitMatrix#getBits()}\r
+ * @param bits representation of QR Code bits\r
* @param dimension dimension of QR Code, represented by bits, being unmasked\r
*/\r
- abstract void unmaskBitMatrix(int[] bits, int dimension);\r
+ final void unmaskBitMatrix(BitMatrix bits, int dimension) {\r
+ for (int y = 0; y < dimension; y++) {\r
+ for (int x = 0; x < dimension; x++) {\r
+ if (isMasked(x, y)) {\r
+ bits.flip(x, y);\r
+ }\r
+ }\r
+ }\r
+ }\r
+\r
+ abstract boolean isMasked(int x, int y);\r
\r
/**\r
* @param reference a value between 0 and 7 indicating one of the eight possible\r
}\r
\r
/**\r
- * 000: mask bits for which (i + j) mod 2 == 0\r
+ * 000: mask bits for which (x + y) mod 2 == 0\r
*/\r
private static class DataMask000 extends DataMask {\r
- private static final int BITMASK = 0x55555555; // = 010101...\r
-\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- // This one's easy. Because the dimension of BitMatrix is always odd,\r
- // we can merely flip every other bit\r
- int max = bits.length;\r
- for (int i = 0; i < max; i++) {\r
- bits[i] ^= BITMASK;\r
- }\r
+ boolean isMasked(int x, int y) {\r
+ return ((x + y) & 0x01) == 0;\r
}\r
}\r
\r
/**\r
- * 001: mask bits for which i mod 2 == 0\r
+ * 001: mask bits for which x mod 2 == 0\r
*/\r
private static class DataMask001 extends DataMask {\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- int bitMask = 0;\r
- int count = 0;\r
- int offset = 0;\r
- for (int j = 0; j < dimension; j++) {\r
- for (int i = 0; i < dimension; i++) {\r
- if ((i & 0x01) == 0) {\r
- bitMask |= 1 << count;\r
- }\r
- if (++count == 32) {\r
- bits[offset++] ^= bitMask;\r
- count = 0;\r
- bitMask = 0;\r
- }\r
- }\r
- }\r
- bits[offset] ^= bitMask;\r
+ boolean isMasked(int x, int y) {\r
+ return (x & 0x01) == 0;\r
}\r
}\r
\r
/**\r
- * 010: mask bits for which j mod 3 == 0\r
+ * 010: mask bits for which y mod 3 == 0\r
*/\r
private static class DataMask010 extends DataMask {\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- int bitMask = 0;\r
- int count = 0;\r
- int offset = 0;\r
- for (int j = 0; j < dimension; j++) {\r
- boolean columnMasked = j % 3 == 0;\r
- for (int i = 0; i < dimension; i++) {\r
- if (columnMasked) {\r
- bitMask |= 1 << count;\r
- }\r
- if (++count == 32) {\r
- bits[offset++] ^= bitMask;\r
- count = 0;\r
- bitMask = 0;\r
- }\r
- }\r
- }\r
- bits[offset] ^= bitMask;\r
+ boolean isMasked(int x, int y) {\r
+ return y % 3 == 0;\r
}\r
}\r
\r
/**\r
- * 011: mask bits for which (i + j) mod 3 == 0\r
+ * 011: mask bits for which (x + y) mod 3 == 0\r
*/\r
private static class DataMask011 extends DataMask {\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- int bitMask = 0;\r
- int count = 0;\r
- int offset = 0;\r
- for (int j = 0; j < dimension; j++) {\r
- for (int i = 0; i < dimension; i++) {\r
- if ((i + j) % 3 == 0) {\r
- bitMask |= 1 << count;\r
- }\r
- if (++count == 32) {\r
- bits[offset++] ^= bitMask;\r
- count = 0;\r
- bitMask = 0;\r
- }\r
- }\r
- }\r
- bits[offset] ^= bitMask;\r
+ boolean isMasked(int x, int y) {\r
+ return (x + y) % 3 == 0;\r
}\r
}\r
\r
/**\r
- * 100: mask bits for which (i/2 + j/3) mod 2 == 0\r
+ * 100: mask bits for which (x/2 + y/3) mod 2 == 0\r
*/\r
private static class DataMask100 extends DataMask {\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- int bitMask = 0;\r
- int count = 0;\r
- int offset = 0;\r
- for (int j = 0; j < dimension; j++) {\r
- int jComponentParity = (j / 3) & 0x01;\r
- for (int i = 0; i < dimension; i++) {\r
- if (((i >> 1) & 0x01) == jComponentParity) {\r
- bitMask |= 1 << count;\r
- }\r
- if (++count == 32) {\r
- bits[offset++] ^= bitMask;\r
- count = 0;\r
- bitMask = 0;\r
- }\r
- }\r
- }\r
- bits[offset] ^= bitMask;\r
+ boolean isMasked(int x, int y) {\r
+ return (((x >>> 1) + (y/3)) & 0x01) == 0;\r
}\r
}\r
\r
/**\r
- * 101: mask bits for which ij mod 2 + ij mod 3 == 0\r
+ * 101: mask bits for which xy mod 2 + xy mod 3 == 0\r
*/\r
private static class DataMask101 extends DataMask {\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- int bitMask = 0;\r
- int count = 0;\r
- int offset = 0;\r
- for (int j = 0; j < dimension; j++) {\r
- for (int i = 0; i < dimension; i++) {\r
- int product = i * j;\r
- if (((product & 0x01) == 0) && product % 3 == 0) {\r
- bitMask |= 1 << count;\r
- }\r
- if (++count == 32) {\r
- bits[offset++] ^= bitMask;\r
- count = 0;\r
- bitMask = 0;\r
- }\r
- }\r
- }\r
- bits[offset] ^= bitMask;\r
+ boolean isMasked(int x, int y) {\r
+ int temp = x * y;\r
+ return (temp & 0x01) + (temp % 3) == 0;\r
}\r
}\r
\r
/**\r
- * 110: mask bits for which (ij mod 2 + ij mod 3) mod 2 == 0\r
+ * 110: mask bits for which (xy mod 2 + xy mod 3) mod 2 == 0\r
*/\r
private static class DataMask110 extends DataMask {\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- int bitMask = 0;\r
- int count = 0;\r
- int offset = 0;\r
- for (int j = 0; j < dimension; j++) {\r
- for (int i = 0; i < dimension; i++) {\r
- int product = i * j;\r
- if ((((product & 0x01) + product % 3) & 0x01) == 0) {\r
- bitMask |= 1 << count;\r
- }\r
- if (++count == 32) {\r
- bits[offset++] ^= bitMask;\r
- count = 0;\r
- bitMask = 0;\r
- }\r
- }\r
- }\r
- bits[offset] ^= bitMask;\r
+ boolean isMasked(int x, int y) {\r
+ int temp = x * y;\r
+ return (((temp & 0x01) + (temp % 3)) & 0x01) == 0;\r
}\r
}\r
\r
* 111: mask bits for which ((i+j)mod 2 + ij mod 3) mod 2 == 0\r
*/\r
private static class DataMask111 extends DataMask {\r
- void unmaskBitMatrix(int[] bits, int dimension) {\r
- int bitMask = 0;\r
- int count = 0;\r
- int offset = 0;\r
- for (int j = 0; j < dimension; j++) {\r
- for (int i = 0; i < dimension; i++) {\r
- if (((((i + j) & 0x01) + (i * j) % 3) & 0x01) == 0) {\r
- bitMask |= 1 << count;\r
- }\r
- if (++count == 32) {\r
- bits[offset++] ^= bitMask;\r
- count = 0;\r
- bitMask = 0;\r
- }\r
- }\r
- }\r
- bits[offset] ^= bitMask;\r
+ boolean isMasked(int x, int y) {\r
+ return ((((x + y) & 0x01) + ((x * y) % 3)) & 0x01) == 0;\r
}\r
}\r
}\r