| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215 |
- #include "qrcode.h"
- #include "rpng.h"
- #include "file.h"
- #include "elog.h"
- #define QRC_RESIZE
- #if 1
- #define LOGD log_d
- #define LOGE log_e
- #else
- #define LOGD printf
- #define LOGE printf
- #endif
- static const uint8_t base64_enc_map[64] =
- {
- 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J',
- 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T',
- 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd',
- 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n',
- 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x',
- 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7',
- '8', '9', '+', '/'
- };
- static int base64_len(int n)
- {
- return ((n / 3) + (n % 3 ? 1 : 0)) * 4 + 1;
- }
- static int base64_encode(uint8_t *src, size_t slen, uint8_t *dst, size_t dlen)
- {
- size_t i, n;
- int C1, C2, C3;
- uint8_t *p;
-
- if( slen == 0 ) {
- return -1;
- }
-
- n = (slen / 3 + ( slen % 3 != 0 )) * 4;
- if( ( dlen < n + 1 ) || ( NULL == dst ) ) {
- return -1;
- }
-
- n = ( slen / 3 ) * 3;
- for( i = 0, p = dst; i < n; i += 3 ) {
- C1 = *src++;
- C2 = *src++;
- C3 = *src++;
-
- *p++ = base64_enc_map[(C1 >> 2) & 0x3F];
- *p++ = base64_enc_map[(((C1 & 3) << 4) + (C2 >> 4)) & 0x3F];
- *p++ = base64_enc_map[(((C2 & 15) << 2) + (C3 >> 6)) & 0x3F];
- *p++ = base64_enc_map[C3 & 0x3F];
- }
-
- if( i < slen ) {
- C1 = *src++;
- C2 = ( ( i + 1 ) < slen ) ? *src++ : 0;
-
- *p++ = base64_enc_map[(C1 >> 2) & 0x3F];
- *p++ = base64_enc_map[(((C1 & 3) << 4) + (C2 >> 4)) & 0x3F];
-
- if( ( i + 1 ) < slen )
- *p++ = base64_enc_map[((C2 & 15) << 2) & 0x3F];
- else *p++ = '=';
-
- *p++ = '=';
- }
- *p = 0;
-
- return (p - dst);
- }
- //////////////////////////////////////////////////////////////
- #if 1
- static inline int in_array(int x, int y, int w, int h)
- {
- if (x >= 0 && x < w && y >= 0 && y < h)
- return 1;
- else
- return 0;
- }
- static uint32_t* rgb_resize(uint32_t* in, int w, int h, int w2, int h2)
- {
- int i,j,x1, y1, x2, y2;
- double f11, f12, f21, f22;
- double a,b,c,d,e,f;
- double h_times = (double)h2 / (double)h,
- w_times = (double)w2 / (double)w;
- uint32_t *out=(uint32_t*)malloc(h2*w2*4);
- if(out) {
- for (i=0; i<h2; i++){
- for (j=0; j<w2; j++) {
- #if 0
- double x = j / w_times;
- double y = i / h_times;
- x1 = (int)(x - 1);
- x2 = (int)(x + 1);
- y1 = (int)(y - 1);
- y2 = (int)(y + 1);
- f11 = in_array(x1, y1, h, w) ? in[y1*w+x1] : 0;
- f12 = in_array(x1, y2, h, w) ? in[y2*w+x1] : 0;
- f21 = in_array(x2, y1, h, w) ? in[y1*w+x2] : 0;
- f22 = in_array(x2, y2, h, w) ? in[y2*w+x2] : 0;
- a = f11 * (x2 - x) * (y2 - y);
- b = f12 * (x2 - x) * (y - y1);
- c = f21 * (x - x1) * (y2 - y);
- d = f22 * (x - x1) * (y - y1);
- e = (x2 - x1) * (y2 - y1);
- f = (a +b + c + d) / e;
- out[i*w2+j] = (uint32_t)f;
- #else
- int x = j / w_times;
- int y = i / h_times;
- out[i*w2+j] = in[y*w+x];
- #endif
- }
- }
- }
- return out;
- }
- #else
- #endif
- #define RGBA(r,g,b,a) (((a)<<24) | ((r)<<16) | ((g)<<8) | (b))
- int qrc_to_png(char *txt, char *path)
- {
- int r,x,y;
- QRCode qrc;
- int size,size2;
- int ver=8,ecc=ECC_QUARTILE;
- uint16_t bufsz=qrcode_getBufferSize(ver);
- uint8_t *pQRC=(uint8_t*)malloc(bufsz);
-
- r = qrcode_initText(&qrc, pQRC, ver, ecc, txt);
- if(!pQRC || r<0) {
- if(pQRC) free(pQRC);
- return -1;
- }
- size = qrc.size;
- uint32_t *pRGB=(uint32_t*)malloc(size*size*4);
- if(!pRGB) {
- free(pQRC);
- return -1;
- }
- for (y=0; y<size; y++) { // row
- for (x=0; x<size; x++) {// module pixel (height)
- if (qrcode_getModule(&qrc, x, y)) {
- pRGB[y*size+x] = RGBA(0,0,0,255);
- }
- else {
- pRGB[y*qrc.size+x] = RGBA(255,255,255,255);
- }
- }
- }
- #ifdef QRC_RESIZE
- size2 = size*6;
- uint32_t *pRGB2 = rgb_resize(pRGB, size, size, size2, size2);
- if(!pRGB2) {
- free(pQRC); free(pRGB);
- return -1;
- }
- free(pRGB);
- pRGB = pRGB2;
- size = size2;
- #endif
- int pngSize=0;
- char *pPNG = rpng_save_image_to_memory((const char*)pRGB, size, size, 4, 8, &pngSize);
- if(pPNG) {
- r = file_save(path, pPNG, pngSize);
- #if 0 //def QRC_BASE64
- char *p64buf=NULL;
- int b64len = base64_len(pngSize)+8;
- p64buf = (char*)malloc(b64len);
- if(p64buf) {
- int d64len = base64_encode((uint8_t*)pPNG, pngSize, (uint8_t*)p64buf, b64len);
- p64buf[d64len] = 0;
- }
- #endif
- RPNG_FREE(pPNG);
- }
- free(pRGB);
- free(pQRC);
-
- return 0;
- }
- int qrc_free(void *p)
- {
- if(!p) {
- return -1;
- }
- free(p);
- return 0;
- }
|