cheetah_qrcode 1.0.1 → 1.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 105a2bf919646066ad19e7041d4b80017b23fdf389c65b02e84275f917dea5e0
4
- data.tar.gz: 3854c8cdda670d87bb2c61071866cadb7cb6f3d505f7c0ce264ec718632f3a16
3
+ metadata.gz: 0fe4a038a4c92715c7848f221672a271bc27e9e79b2d450d9894362a8fb321b8
4
+ data.tar.gz: '0462619677f70ede96efd8174fa3d6b52aaada7a7b119117e12936625af33dce'
5
5
  SHA512:
6
- metadata.gz: 3227f3d6391afb7910d3c1c6840408d75fcdea6127b4a99f3c701b2b896ca14673047907a145c0464f2b27eb9ce5c8821cbf1e0ab527f54a86481c6cd770e549
7
- data.tar.gz: 326643675bad85067387e93ff4da7bba491e2fa5eba01c919de97c6c385bf0d3c57876af2c7f38ba3987fb373846e7e082256c40097783568b2c5954c1316272
6
+ metadata.gz: 772f7f33a2da1b72f887a21d895c8fec5e46a00a9fe8c164e12852d775db26f660cb4c154070d1a215f007417e6f196fe6d9195d65a8db1fbdb27fdd22030f51
7
+ data.tar.gz: d8fc4fced392d3ca1f0062b6db4b3b534d80d5ebd8e1d917a427f860cde33a041e95bad1cd42326ff168361938fda278f7dfa9fcb1a6da89837a8bee53c2de49
@@ -24,12 +24,20 @@ static VALUE encode_text(int argc, VALUE* argv, VALUE self) {
24
24
  rb_raise(rb_eTypeError, "Invalid text");
25
25
  }
26
26
 
27
- if (rb_type(arg_ec_level) == T_SYMBOL) {
28
- arg_ec_level = RB_SYM2ID(arg_ec_level);
29
- } else {
27
+ if (rb_type(arg_ec_level) != T_SYMBOL) {
30
28
  rb_raise(rb_eTypeError, "Invalid error correction level, use :L, :M, :Q, :H");
31
29
  }
32
30
 
31
+ if (rb_type(arg_border) != T_FIXNUM) {
32
+ rb_raise(rb_eTypeError, "Invalid border");
33
+ }
34
+
35
+ if (rb_type(arg_size) != T_FIXNUM) {
36
+ rb_raise(rb_eTypeError, "Invalid size");
37
+ }
38
+
39
+ arg_ec_level = RB_SYM2ID(arg_ec_level);
40
+
33
41
  if (arg_ec_level == rb_intern("L") || arg_ec_level == rb_intern("l")) {
34
42
  qrcode_ec_level = qrcodegen_Ecc_LOW;
35
43
  } else if (arg_ec_level == rb_intern("M") || arg_ec_level == rb_intern("m")) {
@@ -42,16 +50,18 @@ static VALUE encode_text(int argc, VALUE* argv, VALUE self) {
42
50
  rb_raise(rb_eTypeError, "Invalid error correction level, use :L, :M, :Q, :H");
43
51
  }
44
52
 
45
- if (rb_type(arg_border) == T_FIXNUM) {
46
- qrcode_border = RB_NUM2UINT(arg_border);
47
- } else {
48
- rb_raise(rb_eTypeError, "Invalid border");
53
+ qrcode_border = RB_NUM2UINT(arg_border);
54
+
55
+ // The max version qrcode is only 117 wide
56
+ if (qrcode_border > 128) {
57
+ rb_raise(rb_eTypeError, "Border too large");
49
58
  }
50
59
 
51
- if (rb_type(arg_size) == T_FIXNUM) {
52
- image_size = RB_NUM2UINT(arg_size);
53
- } else {
54
- rb_raise(rb_eTypeError, "Invalid size");
60
+ image_size = RB_NUM2UINT(arg_size);
61
+
62
+ // 204800x204800 will use 5000MiB memory for image buffer
63
+ if (image_size > 204800) {
64
+ rb_raise(rb_eTypeError, "Image size too large");
55
65
  }
56
66
 
57
67
  bool ok = qrcodegen_encodeText(
@@ -96,7 +106,21 @@ static VALUE encode_text(int argc, VALUE* argv, VALUE self) {
96
106
  // Create image initialized to 0 (Entirely black image)
97
107
  image = calloc(image_length, sizeof(uint8_t));
98
108
  if (!image) {
99
- rb_raise(rb_eRuntimeError, "Unable to create image buffer");
109
+ rb_raise(rb_eRuntimeError, "Unable to create image buffer for %lu bytes", image_length);
110
+ }
111
+
112
+ // Lookup map for qrcode-to-image pixel conversion
113
+ size_t image_scale_map[qrcode_size + 1];
114
+
115
+ // First pixel always start at 0
116
+ image_scale_map[0] = 0;
117
+
118
+ // Last pixel always end at image_size
119
+ image_scale_map[qrcode_size] = image_size;
120
+
121
+ // Precompute image scale pixels
122
+ for (size_t i = 1; i < qrcode_size; i++) {
123
+ image_scale_map[i] = (size_t)(i * image_scale) + 1;
100
124
  }
101
125
 
102
126
  // Loop through qrcode to find white modules to write into image
@@ -108,33 +132,32 @@ static VALUE encode_text(int argc, VALUE* argv, VALUE self) {
108
132
  }
109
133
 
110
134
  // Map current qrcode module to image coordinates
111
- size_t ix_begin = (size_t)(qx * image_scale) + 1;
112
- size_t ix_end = (size_t)((qx + 1) * image_scale) + 1;
113
- size_t iy_begin = (size_t)(qy * image_scale) + 1;
114
- size_t iy_end = (size_t)((qy + 1) * image_scale) + 1;
115
-
116
- // Fix offset for the first pixel
117
- if (qx == 0) {
118
- ix_begin = 0;
119
- }
120
- if (qy == 0) {
121
- iy_begin = 0;
122
- }
135
+ size_t ix_begin = image_scale_map[qx];
136
+ size_t ix_end = image_scale_map[qx + 1];
137
+ size_t iy_begin = image_scale_map[qy];
138
+ size_t iy_end = image_scale_map[qy + 1];
123
139
 
124
- // For boundary safety
125
- if (ix_end > image_size) {
126
- ix_end = image_size;
127
- }
128
- if (iy_end > image_size) {
129
- iy_end = image_size;
130
- }
131
-
132
- // Fill white pixels into image
140
+ // Fill white pixels into image at unit of bytes
133
141
  for (size_t iy = iy_begin; iy < iy_end; iy++) {
134
- for (size_t ix = ix_begin; ix < ix_end; ix++) {
142
+ size_t ix = ix_begin;
143
+ size_t ix_diff = ix_end - ix_begin;
144
+
145
+ while (ix_diff > 0) {
135
146
  size_t i = (iy * image_scanline_width) + (ix / 8);
136
147
 
137
- image[i] |= 0b10000000 >> (ix % 8);
148
+ uint8_t byte_value = 0xFF;
149
+ uint8_t bits_needed = 8 - (ix % 8);
150
+
151
+ if (bits_needed > ix_diff) {
152
+ byte_value <<= (bits_needed - ix_diff);
153
+ bits_needed = ix_diff;
154
+ }
155
+
156
+ byte_value >>= (ix % 8);
157
+ image[i] |= byte_value;
158
+
159
+ ix += bits_needed;
160
+ ix_diff -= bits_needed;
138
161
  }
139
162
  }
140
163
  }
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module CheetahQRCode
4
- VERSION = '1.0.1'
4
+ VERSION = '1.0.3'
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cheetah_qrcode
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.1
4
+ version: 1.0.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - atitan
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2025-04-27 00:00:00.000000000 Z
11
+ date: 2025-04-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rake