Skip to content

Commit e829cf2

Browse files
fix: rMQR now 100% matches Zint reference and scans at R11+ sizes
Critical fix: mask was never applied because data placement overwrote null markers before mask check. Now tracks data cells with isData[][] array before placement. Encoding verified bit-for-bit identical to Zint for all tested versions. Scans successfully at R11x27 and R11x43 with rxing. (R7x43 and R9x43 are correct but rxing decoder has limited support) 16th scan-verified format! Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent 082f2aa commit e829cf2

1 file changed

Lines changed: 5 additions & 2 deletions

File tree

src/encoders/rmqr.ts

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -324,6 +324,9 @@ export function encodeRMQR(text: string, options: RMQROptions = {}): boolean[][]
324324
pushBits(allBits, byte, 8);
325325
}
326326

327+
// Record which cells are data (null) before placement
328+
const isData: boolean[][] = matrix.map((row) => row.map((cell) => cell === null));
329+
327330
// 6b. Data placement: exact Zint qr_populate_grid algorithm for rMQR
328331
// x_start = cols - 3 (righthand timing pattern)
329332
// Start from bottom (y = rows-1), going up, right col first then left
@@ -378,8 +381,8 @@ export function encodeRMQR(text: string, options: RMQROptions = {}): boolean[][]
378381
const result = matrix.map((row) => row.map((cell) => cell === true));
379382
for (let r = 0; r < rows; r++) {
380383
for (let c = 0; c < cols; c++) {
381-
// Only mask data modules (null in original matrix)
382-
if (matrix[r]![c] === null) {
384+
// Only mask data modules (recorded before data placement)
385+
if (isData[r]![c]) {
383386
if ((Math.floor(r / 2) + Math.floor(c / 3)) % 2 === 0) {
384387
result[r]![c] = !result[r]![c];
385388
}

0 commit comments

Comments
 (0)