MCPcopy Create free account
hub / github.com/crosspoint-reader/crosspoint-reader / drawQrCode

Method drawQrCode

src/util/QrUtils.cpp:11–66  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

9#include "Logging.h"
10
11void QrUtils::drawQrCode(const GfxRenderer& renderer, const Rect& bounds, const std::string& textPayload) {
12 // Dynamically calculate the QR code version based on text length
13 // Version 4 holds ~114 bytes, Version 10 ~395, Version 20 ~1066, up to 40
14 // qrcode.h max version is 40.
15 // Formula: approx version = size / 26 + 1 (very rough estimate, better to find best fit)
16 size_t len = textPayload.length();
17
18 // Truncate to max QR capacity at a UTF-8 safe boundary to avoid splitting multi-byte sequences
19 static constexpr size_t MAX_QR_CAPACITY = 2953; // Version 40, ECC_LOW, byte mode
20 std::string truncated;
21 const char* payload = textPayload.c_str();
22 if (len > MAX_QR_CAPACITY) {
23 len = utf8SafeTruncateBuffer(textPayload.c_str(), static_cast<int>(MAX_QR_CAPACITY));
24 truncated = textPayload.substr(0, len);
25 payload = truncated.c_str();
26 }
27
28 int version = 4;
29 if (len > 114) version = 10;
30 if (len > 395) version = 20;
31 if (len > 1066) version = 30;
32 if (len > 2110) version = 40;
33
34 // Make sure we have a large enough buffer on the heap to avoid blowing the stack
35 uint32_t bufferSize = qrcode_getBufferSize(version);
36 auto qrcodeBytes = std::make_unique<uint8_t[]>(bufferSize);
37
38 QRCode qrcode;
39 // Initialize the QR code. We use ECC_LOW for max capacity.
40 int8_t res = qrcode_initText(&qrcode, qrcodeBytes.get(), version, ECC_LOW, payload);
41
42 if (res == 0) {
43 // Determine the optimal pixel size.
44 const int maxDim = std::min(bounds.width, bounds.height);
45
46 int px = maxDim / qrcode.size;
47 if (px < 1) px = 1;
48
49 // Calculate centering X and Y
50 const int qrDisplaySize = qrcode.size * px;
51 const int xOff = bounds.x + (bounds.width - qrDisplaySize) / 2;
52 const int yOff = bounds.y + (bounds.height - qrDisplaySize) / 2;
53
54 // Draw the QR Code
55 for (uint8_t cy = 0; cy < qrcode.size; cy++) {
56 for (uint8_t cx = 0; cx < qrcode.size; cx++) {
57 if (qrcode_getModule(&qrcode, cx, cy)) {
58 renderer.fillRect(xOff + px * cx, yOff + px * cy, px, px, true);
59 }
60 }
61 }
62 } else {
63 // If it fails (e.g. text too large), log an error
64 LOG_ERR("QR", "Text too large for QR Code version %d", version);
65 }
66}

Callers

nothing calls this directly

Calls 3

utf8SafeTruncateBufferFunction · 0.85
getMethod · 0.80
fillRectMethod · 0.80

Tested by

no test coverage detected