zoukankan      html  css  js  c++  java
  • 如何使用 libqr 库生成二维码?

    使用 libqr 库只需 4 步即可生成二维码

    1.初始化 QRCode 结构体

    QRCode *qrInit(int version, int mode, int eclevel, int masktype, int *errcode);
    

    2.添加数据

    int qrAddData(QRCode *qr, const qr_byte_t *source, int size);
    

    3.掩码和数据进行 xor 运算

    int qrFinalize(QRCode *qr);
    

    4.构造二维码图像

    qr_byte_t *qrSymbolToBMP(QRCode *qr, int sep, int mag, int *size);
    

    qt vs2015 使用 libqr 生成二维码dome

      int errorCode = QR_ERR_NONE;
      qr = qrInit(1,QR_EM_8BIT,1,1,&errorCode);//QRCode* qr;
      if(qr == NULL)
        {
          qDebug()<<"errorCode="<<errorCode;
        }
    
      QString stringData = "cheungxiongwei";
      qrAddData(qr,(const qr_byte_t *) stringData.toStdString().data(),stringData.toStdString().length());
    
      if (!qrFinalize(qr))
        {
          qDebug()<<"errorCode="<<errorCode;
        }
    
      int size = 0;
      qr_byte_t* buffer = qrSymbolToBMP(qr,1,5,&size);
      if(buffer == NULL)
        {
          qDebug()<<"errorCode="<<errorCode;
        }
    
      qDebug()<<QImage::fromData(buffer,size).format();
      ui->QR_Show->setPixmap(QPixmap::fromImage(QImage::fromData(buffer,size)));
      ui->QR_Show->setAlignment(Qt::AlignHCenter |Qt::AlignVCenter);
    

    四个函数介绍

    1. QRCode *qrInit(int version, int mode, int eclevel, int masktype, int *errcode);

    QR_API QRCode *qrInit(int version, int mode, int eclevel, int masktype, int *errcode)
    {
      //声明一个 QRCode 结构体指针 qr
    	QRCode *qr = NULL;
    
      //申请一个 QRCode 结构体大小的内存,具体可查 calloc 函数
    	qr = (QRCode *)calloc(1, sizeof(QRCode));
      //如果申请失败,则直接返回
    	if (qr == NULL) {
    		*errcode = QR_ERR_MEMORY_EXHAUSTED;
    		return NULL;
    	}
    	qr->dataword = (qr_byte_t *)calloc(1, QR_DWD_MAX);
    	qr->ecword   = (qr_byte_t *)calloc(1, QR_ECW_MAX);
    	qr->codeword = (qr_byte_t *)calloc(1, QR_CWD_MAX);
    	if (qr->dataword == NULL || qr->ecword == NULL || qr->codeword == NULL) {
    		*errcode = QR_ERR_MEMORY_EXHAUSTED;
    		qrDestroy(qr);
    		return NULL;
    	}
    
      //qr 结构体初始化
    	qr->_symbol = NULL;
    	qr->symbol = NULL;
    	qr->source = NULL;
    	qr->srcmax = 0;
    	qr->srclen = 0;
    	qr->enclen = 0;
    	qr->delta1 = 0;
    	qr->delta2 = 0;
    	qr->errcode = QR_ERR_NONE;
    	qr->state = QR_STATE_BEGIN;
    
      //二维码像素大小(不包括外边框空白) = (version-1)*4 + 21
    	if (version == -1 || (version >= 1 && version <= QR_VER_MAX)) {
    		qr->param.version = version;
    	} else {
    		*errcode = QR_ERR_INVALID_VERSION;
        //销毁指针
    		qrDestroy(qr);
    		return NULL;
    	}
    
    	//设置编码模式
    	if (mode == QR_EM_AUTO || (mode >= QR_EM_NUMERIC && mode < QR_EM_COUNT)) {
    		qr->param.mode = mode;
    	} else {
    		*errcode = QR_ERR_INVALID_MODE;
    		qrDestroy(qr);
    		return NULL;
    	}
    
    	//设置容错等级
    	if (eclevel >= QR_ECL_L && eclevel < QR_EM_COUNT) {
    		qr->param.eclevel = eclevel;
    	} else {
    		*errcode = QR_ERR_INVALID_ECL;
    		qrDestroy(qr);
    		return NULL;
    	}
    
    	//设置掩码图案
    	if (masktype == -1 || (masktype >= 0 && masktype < QR_MPT_MAX)) {
    		qr->param.masktype = masktype;
    	} else {
    		*errcode = QR_ERR_INVALID_MPT;
    		qrDestroy(qr);
    		return NULL;
    	}
    
    	return qr;
    }
    //总体来说,这个函数的功能就是初始化一个 QRcode 类型的指针;
    

    2.int qrAddData(QRCode *qr, const qr_byte_t *source, int size);

    QR_API int qrAddData(QRCode *qr, const qr_byte_t *source, int size)
    {
      //判断该结构体是否已经被添加过数据
    	if (qr->state == QR_STATE_FINAL) {
    		qrSetErrorInfo(qr, QR_ERR_STATE, _QR_FUNCTION);
    		return FALSE;
    	}
    	return qrAddData2(qr, source, size, qr->param.mode);
    }
    
    QR_API int qrAddData2(QRCode *qr, const qr_byte_t *source, int size, int mode)
    {
    	int enclen, maxlen;
    	int version;
    	int pos, err;
      //判断结构体状态
    	if (qr->state == QR_STATE_FINAL) {
    		qrSetErrorInfo(qr, QR_ERR_STATE, _QR_FUNCTION);
    		return FALSE;
    	}
      //如果添加的数据长度为零,则直接返回
    	if (size <= 0) {
    		qrSetErrorInfo(qr, QR_ERR_EMPTY_SRC, NULL);
    		return FALSE;
    	}
    
    	//根据设置的编码模式,选择相应的编码写入数据
    	if (mode == QR_EM_AUTO) {
    		mode = qrDetectDataType(source, size);
    	} else if (mode < QR_EM_NUMERIC || mode >= QR_EM_COUNT) {
    		qrSetErrorInfo(qr, QR_ERR_INVALID_MODE, NULL);
    		return FALSE;
    	}
    
      //计算编码后的数据长
    	enclen = qrGetEncodedLength2(qr, size, mode);
    	if (enclen == -1) {
    		return FALSE;
    	}
    	version = (qr->param.version == -1) ? QR_VER_MAX : qr->param.version;
    	maxlen = 8 * qr_vertable[version].ecl[qr->param.eclevel].datawords;
    	if (qr->enclen + enclen > maxlen) {
    		qrSetErrorInfo3(qr, QR_ERR_LARGE_SRC, ", %d total encoded bits"
    				" (max %d bits on version=%d, ecl=%s)",
    				qr->enclen + enclen, maxlen, version, qr_eclname[qr->param.eclevel]);
    		return FALSE;
    	}
    	if (qr->param.version == -1) {
    		qr->delta1 += qr_vertable[QR_VER_MAX].nlen[mode] - qr_vertable[VERPOINT1].nlen[mode];
    		qr->delta2 += qr_vertable[QR_VER_MAX].nlen[mode] - qr_vertable[VERPOINT2].nlen[mode];
    	}
    
    	/*
    	 * 型号被指定,输入数据直接直接编码
    	 */
    	if (qr->param.version != -1) {
    		qr->enclen += enclen;
    		if (!qrHasData(qr)) {
    			qrInitDataWord(qr);
    		}
        //写入数据成功后,改写 qr 结构体的状态为 QR_STATE_SET
    		if (qrEncodeDataWord(qr, source, size, mode) == TRUE) {
    			qr->state = QR_STATE_SET;
    			return TRUE;
    		}
    		return FALSE;
    	}
    
    	/*
    	 * 验证输入数据
    	 */
    	pos = -1;
    	err = QR_ERR_NONE;
    	switch (mode) {
    	  case QR_EM_NUMERIC:
    		pos = qrStrPosNotNumeric(source, size);
    		err = QR_ERR_NOT_NUMERIC;
    		break;
    	  case QR_EM_ALNUM:
    		pos = qrStrPosNotAlnum(source, size);
    		err = QR_ERR_NOT_ALNUM;
    		break;
    	  case QR_EM_KANJI:
    		pos = qrStrPosNotKanji(source, size);
    		err = QR_ERR_NOT_KANJI;
    		break;
    	}
    	if (pos != -1) {
    		qrSetErrorInfo3(qr, err, " at offset %d", pos);
    		return FALSE;
    	}
    	qr->enclen += enclen;
    
    	/*
    	 * 缓冲容量不足的时候,就要追加保存
    	 */
    	while (qr->srcmax < qr->srclen + size + 6) {
    		qr->srcmax += QR_SRC_MAX;
    		qr->source = (qr_byte_t *)realloc(qr->source, qr->srcmax);
    		if (qr->source == NULL) {
    			qr->srcmax = 0;
    			qrSetErrorInfo2(qr, QR_ERR_MEMORY_EXHAUSTED, _QR_FUNCTION);
    			return FALSE;
    		}
    	}
    
    	/*
    	 * 在申请的qr结构体中保存数据
    	 */
    	qr->source[qr->srclen++] = (qr_byte_t)(mode | 0x80);
    	qr->source[qr->srclen++] = (qr_byte_t)((size >> 24) & 0x7F);
    	qr->source[qr->srclen++] = (qr_byte_t)((size >> 16) & 0xFF);
    	qr->source[qr->srclen++] = (qr_byte_t)((size >> 8) & 0xFF);
    	qr->source[qr->srclen++] = (qr_byte_t)(size & 0xFF);
    	memcpy(&(qr->source[qr->srclen]), source, (size_t)size);
    	qr->srclen += size;
    	qr->source[qr->srclen] = '';
      //改写 qr 结构体状态,已经设置过
    	qr->state = QR_STATE_SET;
    	return TRUE;
    }
    

    3.QR_API int qrFinalize(QRCode *qr);

    QR_API int qrFinalize(QRCode *qr)
    {
    	static qr_funcs funcs[] = {
    		qrFinalizeDataWord,
    		qrComputeECWord,
    		qrMakeCodeWord,
    		qrFillFunctionPattern,
    		qrFillCodeWord,
    		qrSelectMaskPattern,
    		qrFillFormatInfo,
    		NULL
    	};
    	int i = 0;
    	int ret = TRUE;
      //判断 qr->state == QR_STATE_FINAL
    	if (qrIsFinalized(qr)) {
    		return TRUE;
    	}
    
    	/*
    	 * 码型自动选择
    	 */
    	if (qr->param.version == -1) {
    		int maxlen, delta;
    		int version = 0;
    		while (++version <= QR_VER_MAX) {
    			if (version <= VERPOINT1) {
    				delta = qr->delta1;
    			} else if (version <= VERPOINT2) {
    				delta = qr->delta2;
    			} else {
    				delta = 0;
    			}
    			maxlen = 8 * qr_vertable[version].ecl[qr->param.eclevel].datawords;
    			if (maxlen >= qr->enclen - delta) {
    				break;
    			}
    		}
    		if (version > QR_VER_MAX) {
    			maxlen = 8 * qr_vertable[QR_VER_MAX].ecl[qr->param.eclevel].datawords;
    			qrSetErrorInfo3(qr, QR_ERR_LARGE_SRC, ", %d total encoded bits"
    					" (max %d bits on version=%d, ecl=%s)",
    					qr->enclen, maxlen, QR_VER_MAX, qr_eclname[qr->param.eclevel]);
    			return FALSE;
    		}
    		qr->param.version = version;
    	}
    
    	/*
    	 * データコード語に入力データを登録する
    	 */
    	if (qr->source != NULL) {
    		qr_byte_t *source;
    		int mode, size;
    
    		qrInitDataWord(qr);
    		source = qr->source;
    		while ((mode = (int)(*source++)) != '') {
    			mode ^= 0x80;
    			size = ((int)*source++) << 24;
    			size |= ((int)*source++) << 16;
    			size |= ((int)*source++) << 8;
    			size |= (int)*source++;
    			if (qrEncodeDataWord(qr, source, size, mode) == FALSE) {
    				return FALSE;
    			}
    			source += size;
    		}
    
    		qrFree(qr->source);
    	}
    
    	/*
    	 * シンボルを生成する
    	 */
    	while (funcs[i] && ret == TRUE) {
    		ret = funcs[i++](qr);
    	}
    
      //掩码设置成功,改写 qr 结构体 为设置完成
    	if (ret == TRUE) {
    		qrFree(qr->dataword);
    		qrFree(qr->ecword);
    		qrFree(qr->codeword);
    		qr->state = QR_STATE_FINAL;
    	}
    	return ret;
    }
    

    4.qr_byte_t *qrSymbolToBMP(QRCode *qr, int sep, int mag, int *size);

    QR_API qr_byte_t *qrSymbolToBMP(QRCode *qr, int sep, int mag, int *size)
    {
    	qr_byte_t *rbuf, *rptr;
    	qr_byte_t *sbuf, *sptr;
    	int rsize, rmod, imgsize;
    	int sepskips, pxshift;
    	int i, j, ix, jx, dim, imgdim, sepdim;
    
    	QRCNV_CHECK_STATE();
    	QRCNV_GET_SIZE();
    
    	/*
    	 * 変換後のサイズを計算し、メモリを確保する
    	 */
    	rsize = (imgdim + 7) / 8;
    	if ((rmod = (rsize % 4)) != 0) {
    		rsize += 4 - rmod;
    	}
    	imgsize = rsize * imgdim;
    	*size = QRCNV_BMP_OFFBITS + imgsize;
    	QRCNV_MALLOC(rsize, *size);
    
    	/*
    	 * 添加 BMP 图像文件头
    	 */
    	sptr = qrBmpWriteHeader(sbuf, *size, imgdim, imgdim, imgsize);
    
    	/*
    	 * シンボルを書き込む
    	 */
    	sepskips = rsize * sepdim;
    	/* 分離パターン (下) */
    	if (sepskips) {
    		memset(sptr, 0, (size_t)sepskips);
    		sptr += sepskips;
    	}
    	for (i = dim - 1; i >= 0; i--) {
    		memset(rbuf, 0, (size_t)rsize);
    		pxshift = 7;
    		rptr = rbuf;
    		/* 分離パターン (左) */
    		for (j = 0; j < sepdim; j++) {
    			qrBmpNextPixel();
    		}
    		/* シンボル本体 */
    		for (j = 0; j < dim; j++) {
    			if (qrIsBlack(qr, i, j)) {
    				for (jx = 0; jx < mag; jx++) {
    					*rptr |= 1 << pxshift;
    					qrBmpNextPixel();
    				}
    			} else {
    				for (jx = 0; jx < mag; jx++) {
    					qrBmpNextPixel();
    				}
    			}
    		}
    		/* 行をmag回繰り返し書き込む */
    		for (ix = 0; ix < mag; ix++) {
    			memcpy(sptr, rbuf, (size_t)rsize);
    			sptr += rsize;
    		}
    	}
    	/* 分離パターン (上) */
    	if (sepskips) {
    		memset(sptr, 0, (size_t)sepskips);
    		sptr += sepskips;
    	}
    
    	free(rbuf);
    
    	return sbuf;
    }
    

    5.qr.h 定义文件

    /*
     * QR Code Generator Library: Basic Header
     *
     * Core routines were originally written by Junn Ohta.
     * Based on qr.c Version 0.1: 2004/4/3 (Public Domain)
     *
     * @package     libqr
     * @author      Ryusuke SEKIYAMA <rsky0711@gmail.com>
     * @copyright   2006-2013 Ryusuke SEKIYAMA
     * @license     http://www.opensource.org/licenses/mit-license.php  MIT License
     */
    
    #ifndef _QR_H_
    #define _QR_H_
    
    #ifdef __cplusplus
    extern "C" {
    #endif
    
    #include <errno.h>
    #include <stdio.h>
    
    #if defined(WIN32) && !defined(QR_STATIC_BUILD)
    #ifdef QR_DLL_BUILD
    #define QR_API __declspec(dllexport)
    #else
    #define QR_API __declspec(dllimport)
    #endif
    #else
    #define QR_API
    #endif
    
    /*
     * ライブラリのバージョン
     */
    #define LIBQR_VERSION "0.3.1"
    
    /*
     * エラーコード
     */
    typedef enum {
    	/* 汎用エラーコード */
    	QR_ERR_NONE             = 0,
    	QR_ERR_USAGE            = 0x68,
    	QR_ERR_NOT_IMPL         = 0x69,
    	QR_ERR_SEE_ERRNO        = 0x6e,
    	QR_ERR_FOPEN            = 0x6f,
    	QR_ERR_FREAD            = 0x72,
    	QR_ERR_STATE            = 0x73,
    	QR_ERR_UNKNOWN          = 0x75,
    	QR_ERR_FWRITE           = 0x77,
    	QR_ERR_MEMORY_EXHAUSTED = 0x78,
    
    	/* パラメータ用エラーコード */
    	QR_ERR_INVALID_ARG     = 0x01,
    	QR_ERR_INVALID_VERSION = 0x02,
    	QR_ERR_INVALID_MODE    = 0x03,
    	QR_ERR_INVALID_ECL     = 0x04,
    	QR_ERR_INVALID_MPT     = 0x05,
    	QR_ERR_INVALID_MAG     = 0x06,
    	QR_ERR_INVALID_SEP     = 0x07,
    	QR_ERR_INVALID_SIZE    = 0x08,
    	QR_ERR_INVALID_FMT     = 0x09,
    	QR_ERR_INVALID_OUT     = 0x0a,
    	QR_ERR_INVALID_MAXNUM  = 0x0b,
    	QR_ERR_UNSUPPORTED_FMT = 0x0c,
    	QR_ERR_EMPTY_PARAM     = 0x0f,
    
    	/* 入力データ用エラーコード */
    	QR_ERR_EMPTY_SRC   = 0x10,
    	QR_ERR_LARGE_SRC   = 0x11,
    	QR_ERR_NOT_NUMERIC = 0x12,
    	QR_ERR_NOT_ALNUM   = 0x13,
    	QR_ERR_NOT_KANJI   = 0x14,
    
    	/* 画像処理用エラーコード */
    	QR_ERR_IMAGE_TOO_LARGE  = 0x30,
    	QR_ERR_WIDTH_TOO_LARGE  = 0x31,
    	QR_ERR_HEIGHT_TOO_LARGE = 0x32,
    	QR_ERR_IMAGECREATE      = 0x33,
    	QR_ERR_IMAGEFORMAT      = 0x34,
    	QR_ERR_IMAGEFRAME       = 0x35,
    
    	/* zlib用エラーコード */
    	QR_ERR_DEFLATE = 0x40
    } qr_err_t;
    
    /*
     * 内部状態
     */
    #define QR_STATE_BEGIN  0
    #define QR_STATE_SET    1
    #define QR_STATE_FINAL  2
    
    /*
     * 符号化モード
     */
    typedef enum {
    	QR_EM_AUTO    = -1, /* 自動選択 */
    	QR_EM_NUMERIC =  0, /* 数字 */
    	QR_EM_ALNUM   =  1, /* 英数字: 0-9 A-Z SP $%*+-./: */
    	QR_EM_8BIT    =  2, /* 8ビットバイト */
    	QR_EM_KANJI   =  3  /* 漢字 */
    } qr_em_t;
    
    /* モード総数 */
    #define QR_EM_COUNT 4
    
    /*
     * 誤り訂正レベル
     */
    typedef enum {
    	QR_ECL_L = 0, /* レベルL */
    	QR_ECL_M = 1, /* レベルM */
    	QR_ECL_Q = 2, /* レベルQ */
    	QR_ECL_H = 3  /* レベルH */
    } qr_ecl_t;
    
    /* レベル総数 */
    #define QR_ECL_COUNT 4
    
    /*
     * 出力形式
     */
    typedef enum {
    	QR_FMT_PNG   =  0, /* PNG */
    	QR_FMT_BMP   =  1, /* BMP */
    	QR_FMT_TIFF  =  2, /* TIFF */
    	QR_FMT_PBM   =  3, /* PBM */
    	QR_FMT_SVG   =  4, /* SVG */
    	QR_FMT_JSON  =  5, /* JSON */
    	QR_FMT_DIGIT =  6, /* 文字列 */
    	QR_FMT_ASCII =  7, /* アスキーアート */
    	QR_FMT_UNAVAILABLE = -1 /* 利用不可 */
    } qr_format_t;
    
    /* 出力形式総数 */
    #define QR_FMT_COUNT 8
    
    /*
     * モジュール値のマスク
     */
    #define QR_MM_DATA      0x01  /* 符号化データの黒モジュール */
    #define QR_MM_BLACK     0x02  /* 印字される黒モジュール */
    #define QR_MM_FUNC      0x04  /* 機能パターン領域(形式/型番情報を含む) */
    
    /*
     * 機能パターンの定数
     */
    #define QR_DIM_SEP      4  /* 分離パターンの幅 */
    #define QR_DIM_FINDER   7  /* 位置検出パターンの1辺の長さ */
    #define QR_DIM_ALIGN    5  /* 位置合わせパターンの1辺の長さ */
    #define QR_DIM_TIMING   6  /* タイミングパターンのオフセット位置 */
    
    /*
     * サイズ定数
     */
    #define QR_SRC_MAX  7089  /* 入力データの最大長 */
    #define QR_DIM_MAX   177  /* 1辺のモジュール数の最大値 */
    #define QR_VER_MAX    40  /* 型番の最大値 */
    #define QR_DWD_MAX  2956  /* データコード語の最大長(型番40/レベルL) */
    #define QR_ECW_MAX  2430  /* 誤り訂正コード語の最大長(型番40/レベルH) */
    #define QR_CWD_MAX  3706  /* コード語の最大長(型番40) */
    #define QR_RSD_MAX   123  /* RSブロックデータコード語の最大長 */
    #define QR_RSW_MAX    68  /* RSブロック誤り訂正コード語の最大長 */
    #define QR_RSB_MAX     2  /* RSブロック種別の最大数 */
    #define QR_MPT_MAX     8  /* マスクパターン種別総数 */
    #define QR_APL_MAX     7  /* 位置合わせパターン座標の最大数 */
    #define QR_FIN_MAX    15  /* 形式情報のビット数 */
    #define QR_VIN_MAX    18  /* 型番情報のビット数 */
    #define QR_MAG_MAX    16  /* ピクセル表示倍率の最大値 */
    #define QR_SEP_MAX    16  /* 分離パターン幅の最大値 */
    #define QR_ERR_MAX  1024  /* エラー情報の最大長 */
    #define QR_STA_MAX    16  /* 構造的連接(分割/連結)の最大数 */
    #define QR_STA_LEN    20  /* 構造的連接ヘッダのビット数 */
    
    /*
     * その他の定数
     */
    #define NAV            0  /* 不使用(not available) */
    #define PADWORD1    0xec  /* 埋め草コード語1: 11101100 */
    #define PADWORD2    0x11  /* 埋め草コード語2: 00010001 */
    #define VERPOINT1      9  /* 文字数指示子のビット数が変わる直前の型番1 */
    #define VERPOINT2     26  /* 文字数指示子のビット数が変わる直前の型番2 */
    
    /*
     * 8bitバイナリデータ型
     */
    typedef unsigned char qr_byte_t;
    
    /*
     * RSブロックごとの情報
     */
    typedef struct qr_rsblock_t {
      int rsbnum;     /* RSブロック数 */
      int totalwords; /* RSブロック総コード語数 */
      int datawords;  /* RSブロックデータコード語数 */
      int ecnum;      /* RSブロック誤り訂正数(不使用) */
    } qr_rsblock_t;
    
    /*
     * 誤り訂正レベルごとの情報
     */
    typedef struct qr_eclevel_t {
      int datawords;                /* データコード語数(全RSブロック) */
      int capacity[QR_EM_COUNT];    /* 符号化モードごとのデータ容量 */
      int nrsb;                     /* RSブロックの種類(1または2) */
      qr_rsblock_t rsb[QR_RSB_MAX]; /* RSブロックごとの情報 */
    } qr_eclevel_t;
    
    /*
     * 型番ごとの情報
     */
    typedef struct qr_vertable_t {
      int          version;           /* 型番 */
      int          dimension;         /* 1辺のモジュール数 */
      int          totalwords;        /* 総コード語数 */
      int          remainedbits;      /* 剰余ビット数 */
      int          nlen[QR_EM_COUNT]; /* 文字数指示子のビット数 */
      qr_eclevel_t ecl[QR_ECL_COUNT]; /* 誤り訂正レベルごとの情報 */
      int          aplnum;            /* 位置合わせパターン中心座標数 */
      int          aploc[QR_APL_MAX]; /* 位置合わせパターン中心座標 */
    } qr_vertable_t;
    
    /*
     * 座標データ型
     */
    typedef struct qr_coord_t { int ypos, xpos; } qr_coord_t;
    
    /*
     * パラメータ構造体
     */
    typedef struct qr_param_t {
      int version;              /* 型番 */
      int mode;                 /* 符号化モード */
      int eclevel;              /* 誤り訂正レベル */
      int masktype;             /* マスクパターン種別 */
    } qr_param_t;
    
    /*
     * QRコードオブジェクト
     */
    typedef struct qrcode_t {
      qr_byte_t *dataword;      /* データコード語領域のアドレス */
      qr_byte_t *ecword;        /* 誤り訂正コード語領域のアドレス */
      qr_byte_t *codeword;      /* シンボル配置用コード語領域のアドレス */
      qr_byte_t *_symbol;       /* シンボルデータ領域のアドレス */
      qr_byte_t **symbol;       /* シンボルデータの各行頭のアドレスのポインタ */
      qr_byte_t *source;        /* 入力データ領域のアドレス */
      size_t srcmax;            /* 入力データ領域の最大容量 */
      size_t srclen;            /* 入力データ領域の使用容量 */
      int enclen;               /* データコード語の総ビット長 */
      int delta1, delta2;       /* 型番自動選択の補助に使われるビット長差分 */
      int dwpos;                /* データコード語の追加バイト位置 */
      int dwbit;                /* データコード語の追加ビット位置 */
      int xpos, ypos;           /* モジュールを配置する座標位置 */
      int xdir, ydir;           /* モジュール配置の移動方向 */
      int state;                /* 処理の進行状況 */
      int errcode;              /* 最後に起こったエラーの番号 */
      char errinfo[QR_ERR_MAX]; /* 最後に起こったエラーの詳細 */
      qr_param_t param;         /* 出力パラメータ */
    } QRCode;
    
    /*
     * 構造的連接QRコードオブジェクト
     */
    typedef struct qrcode_sa_t {
      QRCode *qrs[QR_STA_MAX];  /* QRコードオブジェクトのポインタ配列 */
      QRCode *cur;              /* 値を入力する対象のQRコードオブジェクト */
      int num;                  /* シンボル数 */
      int max;                  /* 最大シンボル数 */
      int parity;               /* パリティ */
      int state;                /* 処理の進行状況 */
      qr_param_t param;         /* 出力パラメータ */
    } QRStructured;
    
    /*
     * QRコード出力関数型
     */
    typedef qr_byte_t *(*QRConverter)(QRCode *, int, int, int *);
    typedef qr_byte_t *(*QRsConverter)(QRStructured *, int, int, int, int *);
    
    /*
     * 基本関数のプロトタイプ
     */
    QR_API QRCode *qrInit(int version, int mode, int eclevel, int masktype, int *errcode);
    QR_API void qrDestroy(QRCode *qr);
    QR_API int qrGetErrorCode(QRCode *qr);
    QR_API char *qrGetErrorInfo(QRCode *qr);
    QR_API int qrAddData(QRCode *qr, const qr_byte_t *source, int size);
    QR_API int qrAddData2(QRCode *qr, const qr_byte_t *source, int size, int mode);
    QR_API int qrFinalize(QRCode *qr);
    QR_API int qrIsFinalized(const QRCode *qr);
    QR_API int qrHasData(const QRCode *qr);
    QR_API QRCode *qrClone(const QRCode *qr, int *errcode);
    
    /*
     * 構造的連接操作用関数のプロトタイプ
     */
    QR_API QRStructured *qrsInit(int version, int mode, int eclevel, int masktype, int maxnum, int *errcode);
    QR_API void qrsDestroy(QRStructured *st);
    QR_API int qrsGetErrorCode(QRStructured *st);
    QR_API char *qrsGetErrorInfo(QRStructured *st);
    QR_API int qrsAddData(QRStructured *st, const qr_byte_t *source, int size);
    QR_API int qrsAddData2(QRStructured *st, const qr_byte_t *source, int size, int mode);
    QR_API int qrsFinalize(QRStructured *st);
    QR_API int qrsIsFinalized(const QRStructured *st);
    QR_API int qrsHasData(const QRStructured *st);
    QR_API QRStructured *qrsClone(const QRStructured *st, int *errcode);
    
    /*
     * 出力用関数のプロトタイプ
     */
    QR_API int qrOutputSymbol(QRCode *qr, FILE *fp, int fmt, int sep, int mag);
    QR_API int qrOutputSymbol2(QRCode *qr, const char *pathname, int fmt, int sep, int mag);
    QR_API qr_byte_t *qrGetSymbol(QRCode *qr, int fmt, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToDigit(QRCode *qr, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToASCII(QRCode *qr, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToJSON(QRCode *qr, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToPBM(QRCode *qr, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToBMP(QRCode *qr, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToSVG(QRCode *qr, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToTIFF(QRCode *qr, int sep, int mag, int *size);
    QR_API qr_byte_t *qrSymbolToPNG(QRCode *qr, int sep, int mag, int *size);
    
    /*
     * 構造的連接出力用関数のプロトタイプ
     */
    QR_API int qrsOutputSymbols(QRStructured *st, FILE *fp, int fmt, int sep, int mag, int order);
    QR_API int qrsOutputSymbols2(QRStructured *st, const char *pathname, int fmt, int sep, int mag, int order);
    QR_API qr_byte_t *qrsGetSymbols(QRStructured *st, int fmt, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToDigit(QRStructured *st, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToASCII(QRStructured *st, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToJSON(QRStructured *st, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToPBM(QRStructured *st, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToBMP(QRStructured *st, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToSVG(QRStructured *st, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToTIFF(QRStructured *st, int sep, int mag, int order, int *size);
    QR_API qr_byte_t *qrsSymbolsToPNG(QRStructured *st, int sep, int mag, int order, int *size);
    
    #ifdef __cplusplus
    } // extern "C"
    #endif
    
    #endif /* _QR_H_ */
    

    最后附上 libqr 库文件

    https://files.cnblogs.com/files/cheungxiongwei/libqr.zip

  • 相关阅读:
    [CF1295E] Permutation Separation
    [APIO2010] 特别行动队
    [CF1296F] Berland Beauty
    [CEOI2004] 锯木厂选址
    [CF1334E] Divisor Paths
    Review 2020.11.14
    [CQOI2016] 手机号码
    [LEETCODE600] 不含连续1的非负整数
    [CF55D] Beautiful numbers
    内存取证工具volatility
  • 原文地址:https://www.cnblogs.com/cheungxiongwei/p/7494866.html
Copyright © 2011-2022 走看看