63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
|
# File 'ext/quirc/quirc.c', line 63
VALUE quirc_recognizer_t_recognize(VALUE self, VALUE image_data, VALUE width, VALUE height) {
quirc_recognizer_t *qr;
uint8_t *image;
int w, h;
int total_pixels;
int total_codes;
VALUE results;
Check_Type(image_data, T_STRING);
total_pixels = NUM2INT(width) * NUM2INT(height);
TypedData_Get_Struct(self, quirc_recognizer_t, &quirc_recognizer_data_type, qr);
if (quirc_resize(qr->quirc, NUM2INT(width), NUM2INT(height)) == -1) {
rb_raise(rb_eNoMemError, "%s", "(quirc_resize) failed to allocate memory");
}
image = quirc_begin(qr->quirc, &w, &h);
total_pixels = w * h;
// Filling the image buffer. One byte per pixel.
if (RSTRING_LEN(image_data) >= total_pixels) {
memcpy(image, StringValuePtr(image_data), total_pixels);
} else {
// rb_raise(rb_eArgError, "%s", "Expect an 8-bit image");
}
quirc_end(qr->quirc);
total_codes = quirc_count(qr->quirc);
results = rb_ary_new_capa(total_codes);
for (int i = 0; i < total_codes; ++i) {
struct quirc_code code;
struct quirc_data data;
quirc_decode_error_t err;
VALUE result;
quirc_extract(qr->quirc, i, &code);
err = quirc_decode(&code, &data);
if (err == QUIRC_ERROR_DATA_ECC) {
quirc_flip(&code);
err = quirc_decode(&code, &data);
}
if (err != QUIRC_SUCCESS) {
rb_warn("(quirc_decode) %s", quirc_strerror(err));
continue;
}
result = rb_funcall(cQuircData, rb_intern("new"), 0);
rb_iv_set(result, "@version", INT2FIX(data.version));
rb_iv_set(result, "@ecc_level", INT2FIX(data.ecc_level));
rb_iv_set(result, "@mask", INT2FIX(data.mask));
rb_iv_set(result, "@data_type", INT2FIX(data.data_type));
rb_iv_set(result, "@payload_len", INT2FIX(data.payload_len));
rb_iv_set(result, "@payload", rb_str_new_cstr((const char *)data.payload));
rb_iv_set(result, "@eci", INT2NUM(data.eci));
rb_ary_push(results, result);
}
return results;
}
|