生成二维码点阵 ,并在 cocos2dx 中绘制

生成二维码点阵 ,并在 cocos2dx 中绘制,第1张

概述点阵生成相关代码 使用 QR_Encode  QR_Encode.EncodeData() 之后, m_nSymbleSize 是 二维码矩阵 宽高, m_byModuleData[i][j]  代表 矩阵 行列位置 是否有值 QR_Encode.h // QR_Encode.h : CQR_Encode クラス宣言およびインターフェイス定義// Date 2006/05/17 Ver. 1.2

点阵生成相关代码 使用 QR_Encode

QR_Encode.EncodeData() 之后,

m_nSymbleSize 是 二维码矩阵 宽高,

m_byModuleData[i][j] 代表 矩阵 行列位置 是否有值



QR_Encode.h

// QR_Encode.h : CQR_Encode クラス宣言およびインターフェイス定義// Date 2006/05/17	Ver. 1.22	Psytec Inc.#ifndef AFX_QR_ENCODE_H__AC886DF7_C0AE_4C9F_AC7A_Fcda8CB1DD37__INCLUDED_#define AFX_QR_ENCODE_H__AC886DF7_C0AE_4C9F_AC7A_Fcda8CB1DD37__INCLUDED_// 誤り訂正レベル#define QR_LEVEL_L	0#define QR_LEVEL_M	1#define QR_LEVEL_Q	2#define QR_LEVEL_H	3// データモード#define QR_MODE_NUMERAL		0#define QR_MODE_AlphaBET	1#define QR_MODE_8BIT		2#define QR_MODE_KANJI		3// バージョン(型番)グループ#define QR_VRESION_S	0 // 1 ~ 9#define QR_VRESION_M	1 // 10 ~ 26#define QR_VRESION_L	2 // 27 ~ 40#define MAX_ALLCODEWORD	 3706 // #define MAX_DATACODEWORD 2956 // #define MAX_CODEBLOCK	  153 // #define MAX_MODulESIZE	  177 // // ビットマップ描画時マージン#define QR_margin	1#define min(x,y) ((x)<(y)?(x):(y))/////////////////////////////////////////////////////////////////////////////typedef struct tagRS_BLOCKINFO{    int ncRSBlock;		// RSブロック数    int ncAllCodeWord;	// ブロック内コードワード数    int ncdataCodeWord;	// データコードワード数(コードワード数 - RSコードワード数)} RS_BLOCKINFO,*LPRS_BLOCKINFO;/////////////////////////////////////////////////////////////////////////////// QRコードバージョン(型番)関連情報typedef struct tagQR_VERSIONINFO{    int nVersionNo;	   // バージョン(型番)番号(1~40)    int ncAllCodeWord; // 総コードワード数    // 以下配列添字は誤り訂正率(0 = L,1 = M,2 = Q,3 = H)     int ncdataCodeWord[4];	// データコードワード数(総コードワード数 - RSコードワード数)    int ncAlignPoint;	// アライメントパターン座標数    int nAlignPoint[6];	// アライメントパターン中心座標    RS_BLOCKINFO RS_BlockInfo1[4]; // RSブロック情報(1)    RS_BLOCKINFO RS_BlockInfo2[4]; // RSブロック情報(2)} QR_VERSIONINFO,*LPQR_VERSIONINFO;/////////////////////////////////////////////////////////////////////////////// CQR_Encode クラスnamespace playcrab{	class CQR_Encode	{		// 構築/消滅	public:		CQR_Encode();		~CQR_Encode();	public:		int m_nLevel;		// 		int m_nVersion;		// 		bool m_bautoExtent;	// 		int m_nMaskingNo;	// 	public:		int m_nSymbleSize;		unsigned char m_byModuleData[MAX_MODulESIZE][MAX_MODulESIZE]; // [x][y]		// bit5:		// bit4:		// bit1:		// bit0:		// 20h	private:		int m_ncdataCodeWordBit; // 		unsigned char m_byDataCodeWord[MAX_DATACODEWORD]; // 		int m_ncdataBlock;		unsigned char m_byBlockMode[MAX_DATACODEWORD];		int m_nBlockLength[MAX_DATACODEWORD];		int m_ncAllCodeWord; //		unsigned char m_byAllCodeWord[MAX_ALLCODEWORD]; // 		unsigned char m_byRSWork[MAX_CODEBLOCK]; // 		// 	public:		bool EncodeData(int nLevel,int nVersion,bool bautoExtent,int nMaskingNo,char * lpsSource,int ncSource = 0);	private:		int GetEncodeVersion(int nVersion,int ncLength);		bool EncodeSourceData(char * lpsSource,int ncLength,int nVerGroup);		int GetBitLength(unsigned char nMode,int ncdata,int nVerGroup);		int SetBitStream(int nIndex,unsigned short wData,int ncdata);		bool IsNumeralData(unsigned char c);		bool IsAlphabetData(unsigned char c);		bool IsKanjIData(unsigned char c1,unsigned char c2);		unsigned char AlphabetToBinaly(unsigned char c);		unsigned short KanjiToBinaly(unsigned short wc);		voID GetRSCodeWord(unsigned char* lpbyRSWork,int ncdataCodeWord,int ncRSCodeWord);		// モジュール配置関連ファンクション	private:		voID FormatModule();		voID SetFunctionModule();		voID SetFinderPattern(int x,int y);		voID SetAlignmentPattern(int x,int y);		voID SetVersionPattern();		voID SetCodeWordPattern();		voID SetMaskingPattern(int nPatternNo);		voID SetFormatInfoPattern(int nPatternNo);		int  CountPenalty();	};}/////////////////////////////////////////////////////////////////////////////#endif // !defined(AFX_QR_ENCODE_H__AC886DF7_C0AE_4C9F_AC7A_Fcda8CB1DD37__INCLUDED_)

QR_Encode.cpp
// QR_Encode.cpp : CQR_Encode クラス インプリメンテーション ファイル// Date 2006/05/17	Ver. 1.22	Psytec Inc.#include "QR_Encode.h"#include <stdlib.h>#include <string.h>static QR_VERSIONINFO QR_VersonInfo[] = { { 0 },//{ 1,// Ver.126,19,16,13,9,1,26,0 },{ 2,// Ver.244,34,28,22,18,44,{ 3,// Ver.370,55,70,2,35,17,{ 4,// Ver.4100,80,64,48,36,100,50,32,24,4,25,{ 5,// Ver.5134,108,86,62,46,30,134,67,43,33,15,11,12 },{ 6,// Ver.6172,136,76,60,68,27,{ 7,// Ver.7196,156,124,88,66,38,98,78,49,31,14,39,40,14 },{ 8,// Ver.8242,194,154,110,42,121,97,61,41,15 },{ 9,// Ver.9292,232,182,132,146,116,3,58,12,59,37,13 },{ 10,// Ver.10346,274,216,122,69,6,87,20,16 },{ 11,// Ver.11404,324,254,180,140,54,101,81,51,23,8,{ 12,// Ver.12466,370,290,206,158,92,7,117,93,47,21,{ 13,// Ver.13532,428,334,244,133,107,45,{ 14,// Ver.14581,461,365,261,197,145,115,5,65,{ 15,// Ver.15655,523,415,295,223,109,{ 16,// Ver.16733,589,453,325,253,74,73,123,99,{ 17,// Ver.17815,647,507,367,283,135,10,75,{ 18,// Ver.18901,721,563,397,313,56,82,150,120,151,{ 19,// Ver.19991,795,627,445,341,141,113,142,114,71,{ 20,// Ver.201085,861,669,485,385,90,{ 21,// Ver.211156,932,714,512,406,72,94,144,17 },{ 22,// Ver.221258,1006,782,568,442,139,111,112,{ 23,// Ver.231364,1094,860,614,464,102,152,{ 24,// Ver.241474,1174,914,664,514,106,147,148,118,{ 25,// Ver.251588,1276,1000,718,538,84,{ 26,// Ver.261706,1370,1062,754,596,143,{ 27,// Ver.271828,1468,1128,808,628,53,153,{ 28,// Ver.281921,1531,1193,871,661,{ 29,// Ver.292051,1631,1267,911,701,126,{ 30,// Ver.302185,1735,1373,985,745,52,104,130,{ 31,// Ver.312323,1843,1455,1033,793,29,{ 32,// Ver.322465,1955,1541,1115,845,138,{ 33,// Ver.332611,2071,1171,901,{ 34,// Ver.342761,2191,1725,1231,961,{ 35,// Ver.352876,2306,1812,1286,986,{ 36,// Ver.363034,2434,1914,1354,1054,128,{ 37,// Ver.373196,2566,1992,1426,1096,{ 38,// Ver.383362,2702,2102,1502,1142,162,{ 39,// Ver.393532,2812,2216,1582,1222,166,{ 40,// Ver.403706,2956,2334,1666,170,149,119,16 }};/////////////////////////////////////////////////////////////////////////////// GF(2^8)α指数→整数変換テーブルstatic unsigned char byExpToInt[] = { 1,205,234,201,96,192,157,212,181,238,193,159,160,186,105,210,185,222,161,95,190,188,202,137,240,231,211,187,214,177,127,225,163,91,226,217,175,208,189,103,129,248,237,199,236,204,184,218,169,79,168,77,164,85,57,228,213,183,230,209,191,198,63,252,229,215,179,246,241,255,227,219,171,196,220,165,174,200,224,221,167,83,89,178,242,249,239,195,155,172,245,247,243,251,235,203,176,125,250,233,207,131,173,1 };/////////////////////////////////////////////////////////////////////////////// GF(2^8)α整数→指数変換テーブルstatic unsigned char byIntToExp[] = { 0,175 };/////////////////////////////////////////////////////////////////////////////// 誤り訂正生成多項式α係数static unsigned char byRSExp7[] = { 87,21 };static unsigned char byRSExp10[] = { 251,45 };static unsigned char byRSExp13[] = { 74,78 };static unsigned char byRSExp15[] = { 8,105 };static unsigned char byRSExp16[] = { 120,120 };static unsigned char byRSExp17[] = { 43,136 };static unsigned char byRSExp18[] = { 215,153 };static unsigned char byRSExp20[] = { 17,190 };static unsigned char byRSExp22[] = { 210,231 };static unsigned char byRSExp24[] = { 229,21 };static unsigned char byRSExp26[] = { 173,70 };static unsigned char byRSExp28[] = { 168,123 };static unsigned char byRSExp30[] = { 41,180 };static unsigned char byRSExp32[] = { 10,241 };static unsigned char byRSExp34[] = { 111,51 };static unsigned char byRSExp36[] = { 200,120 };static unsigned char byRSExp38[] = { 159,193 };static unsigned char byRSExp40[] = { 59,15 };static unsigned char byRSExp42[] = { 250,96 };static unsigned char byRSExp44[] = { 190,181 };static unsigned char byRSExp46[] = { 112,15 };static unsigned char byRSExp48[] = { 228,108 };static unsigned char byRSExp50[] = { 232,205 };static unsigned char byRSExp52[] = { 116,51 };static unsigned char byRSExp54[] = { 183,156 };static unsigned char byRSExp56[] = { 106,10 };static unsigned char byRSExp58[] = { 82,123 };static unsigned char byRSExp60[] = { 107,240 };static unsigned char byRSExp62[] = { 65,106 };static unsigned char byRSExp64[] = { 45,231 };static unsigned char byRSExp66[] = { 5,105 };static unsigned char byRSExp68[] = { 247,238 };//static unsigned char*  byRSExp[] = { 0,byRSExp7,byRSExp10,byRSExp13,byRSExp15,byRSExp16,byRSExp17,byRSExp18,byRSExp20,byRSExp22,byRSExp24,byRSExp26,byRSExp28,byRSExp30,byRSExp32,byRSExp34,byRSExp36,byRSExp38,byRSExp40,byRSExp42,byRSExp44,byRSExp46,byRSExp48,byRSExp50,byRSExp52,byRSExp54,byRSExp56,byRSExp58,byRSExp60,byRSExp62,byRSExp64,byRSExp66,byRSExp68 };// 文字数インジケータビット長(バージョングループ別,{S,M,L})static int nIndicatorLenNumeral[] = { 10,14 };static int nIndicatorLenAlphabet[] = { 9,13 };static int nIndicatorLen8Bit[] = { 8,16 };static int nIndicatorLenKanji[] = { 8,12 };/////////////////////////////////////////////////////////////////////////////// QR_Encode クラスの構築/消滅namespace playcrab{CQR_Encode::CQR_Encode(){}//CQR_Encode::~CQR_Encode(){}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::EncodeDatabool CQR_Encode::EncodeData(int nLevel,char* lpsSource,int ncSource){    int i,j;    m_nLevel = nLevel;    m_nMaskingNo = nMaskingNo;    // データ長が指定されていない場合は lstrlen によって取得    int ncLength = ncSource > 0 ? ncSource : strlen(lpsSource);    if (ncLength == 0)        return 0; // データなし    // バージョン(型番)チェック    int nEncodeVersion = GetEncodeVersion(nVersion,lpsSource,ncLength);    if (nEncodeVersion == 0)        return 0; // 容量オーバー    if (nVersion == 0)    {        // 型番自動        m_nVersion = nEncodeVersion;    }    else    {        if (nEncodeVersion <= nVersion)        {            m_nVersion = nVersion;        }        else        {            if (bautoExtent)                m_nVersion = nEncodeVersion; // バージョン(型番)自動拡張            else                return 0; // 容量オーバー        }    }    // ターミネータコード"0000"付加    int ncdataCodeWord = QR_VersonInfo[m_nVersion].ncdataCodeWord[nLevel];    int ncTerminater = min(4,(ncdataCodeWord * 8) - m_ncdataCodeWordBit);    if (ncTerminater > 0)        m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,ncTerminater);    // パディングコード"11101100,00010001"付加    unsigned char bypaddingCode = 0xec;    for (i = (m_ncdataCodeWordBit + 7) / 8; i < ncdataCodeWord; ++i)    {        m_byDataCodeWord[i] = bypaddingCode;        bypaddingCode = (unsigned char)(bypaddingCode == 0xec ? 0x11 : 0xec);    }    // 総コードワード算出エリアクリア    m_ncAllCodeWord = QR_VersonInfo[m_nVersion].ncAllCodeWord;    memset(m_byAllCodeWord,m_ncAllCodeWord);    int nDataCwIndex = 0; // データコードワード処理位置    // データブロック分割数    int ncBlock1 = QR_VersonInfo[m_nVersion].RS_BlockInfo1[nLevel].ncRSBlock;    int ncBlock2 = QR_VersonInfo[m_nVersion].RS_BlockInfo2[nLevel].ncRSBlock;    int ncBlockSum = ncBlock1 + ncBlock2;    int nBlockNo = 0; // 処理中ブロック番号    // ブロック別データコードワード数    int ncdataCw1 = QR_VersonInfo[m_nVersion].RS_BlockInfo1[nLevel].ncdataCodeWord;    int ncdataCw2 = QR_VersonInfo[m_nVersion].RS_BlockInfo2[nLevel].ncdataCodeWord;    // データコードワードインターリーブ配置    for (i = 0; i < ncBlock1; ++i)    {        for (j = 0; j < ncdataCw1; ++j)        {            m_byAllCodeWord[(ncBlockSum * j) + nBlockNo] = m_byDataCodeWord[nDataCwIndex++];        }        ++nBlockNo;    }    for (i = 0; i < ncBlock2; ++i)    {        for (j = 0; j < ncdataCw2; ++j)        {            if (j < ncdataCw1)            {                m_byAllCodeWord[(ncBlockSum * j) + nBlockNo] = m_byDataCodeWord[nDataCwIndex++];            }            else            {                // 2種目ブロック端数分配置                m_byAllCodeWord[(ncBlockSum * ncdataCw1) + i] = m_byDataCodeWord[nDataCwIndex++];            }        }        ++nBlockNo;    }    // ブロック別RSコードワード数(※現状では同数)    int ncRSCw1 = QR_VersonInfo[m_nVersion].RS_BlockInfo1[nLevel].ncAllCodeWord - ncdataCw1;    int ncRSCw2 = QR_VersonInfo[m_nVersion].RS_BlockInfo2[nLevel].ncAllCodeWord - ncdataCw2;    /////////////////////////////////////////////////////////////////////////    // RSコードワード算出    nDataCwIndex = 0;    nBlockNo = 0;    for (i = 0; i < ncBlock1; ++i)    {        memset(m_byRSWork,sizeof(m_byRSWork));        memmove(m_byRSWork,m_byDataCodeWord + nDataCwIndex,ncdataCw1);        GetRSCodeWord(m_byRSWork,ncdataCw1,ncRSCw1);        // RSコードワード配置        for (j = 0; j < ncRSCw1; ++j)        {            m_byAllCodeWord[ncdataCodeWord + (ncBlockSum * j) + nBlockNo] = m_byRSWork[j];        }        nDataCwIndex += ncdataCw1;        ++nBlockNo;    }    for (i = 0; i < ncBlock2; ++i)    {        memset(m_byRSWork,ncdataCw2);        GetRSCodeWord(m_byRSWork,ncdataCw2,ncRSCw2);        // RSコードワード配置        for (j = 0; j < ncRSCw2; ++j)        {            m_byAllCodeWord[ncdataCodeWord + (ncBlockSum * j) + nBlockNo] = m_byRSWork[j];        }        nDataCwIndex += ncdataCw2;        ++nBlockNo;    }    m_nSymbleSize = m_nVersion * 4 + 17;    // モジュール配置    FormatModule();    return 1;}///////////////////////////////////////////////////////////////////////////////////// CQR_Encode::GetEncodeVersion//// 用  途:エンコード時バージョン(型番)取得//// 引  数:調査開始バージョン、エンコードデータ、エンコードデータ長//// 戻り値:バージョン番号(容量オーバー時=0)//int CQR_Encode::GetEncodeVersion(int nVersion,int ncLength){    int nVerGroup = nVersion >= 27 ? QR_VRESION_L : (nVersion >= 10 ? QR_VRESION_M : QR_VRESION_S);    int i,j;    for (i = nVerGroup; i <= QR_VRESION_L; ++i)    {        if (EncodeSourceData(lpsSource,ncLength,i))        {            if (i == QR_VRESION_S)            {                for (j = 1; j <= 9; ++j)                {                    if ((m_ncdataCodeWordBit + 7) / 8 <= QR_VersonInfo[j].ncdataCodeWord[m_nLevel])                        return j;                }            }            else if (i == QR_VRESION_M)            {                for (j = 10; j <= 26; ++j)                {                    if ((m_ncdataCodeWordBit + 7) / 8 <= QR_VersonInfo[j].ncdataCodeWord[m_nLevel])                        return j;                }            }            else if (i == QR_VRESION_L)            {                for (j = 27; j <= 40; ++j)                {                    if ((m_ncdataCodeWordBit + 7) / 8 <= QR_VersonInfo[j].ncdataCodeWord[m_nLevel])                        return j;                }            }        }    }    return 0;}///////////////////////////////////////////////////////////////////////////////// CQR_Encode::EncodeSourceData// 用  途:入力データエンコード// 引  数:入力データ、入力データ長、バージョン(型番)グループ// 戻り値:エンコード成功時=1bool CQR_Encode::EncodeSourceData(char* lpsSource,int nVerGroup){    memset(m_nBlockLength,sizeof(m_nBlockLength));    int i,j;    // どのモードが何文字(バイト)継続しているかを調査    for (m_ncdataBlock = i = 0; i < ncLength; ++i)    {        unsigned char byMode;        if (i < ncLength - 1 && IsKanjIData(lpsSource[i],lpsSource[i + 1]))            byMode = QR_MODE_KANJI;        else if (IsNumeralData(lpsSource[i]))            byMode = QR_MODE_NUMERAL;        else if (IsAlphabetData(lpsSource[i]))            byMode = QR_MODE_AlphaBET;        else            byMode = QR_MODE_8BIT;        if (i == 0)            m_byBlockMode[0] = byMode;        if (m_byBlockMode[m_ncdataBlock] != byMode)            m_byBlockMode[++m_ncdataBlock] = byMode;        ++m_nBlockLength[m_ncdataBlock];        if (byMode == QR_MODE_KANJI)        {            // 漢字は文字数ではなく	数で記録            ++m_nBlockLength[m_ncdataBlock];            ++i;        }    }    ++m_ncdataBlock;    /////////////////////////////////////////////////////////////////////////    // 隣接する英数字モードブロックと数字モードブロックの並びをを条件により結合    int ncSrcBits,ncDstBits; // 元のビット長と単一の英数字モードブロック化した場合のビット長    int nBlock = 0;    while (nBlock < m_ncdataBlock - 1)    {        int ncJoinFront,ncJoinBehind; // 前後8ビットバイトモードブロックと結合した場合のビット長        int nJoinposition = 0; // 8ビットバイトモードブロックとの結合:-1=前と結合、0=結合しない、1=後ろと結合        // 「数字-英数字」または「英数字-数字」の並び        if ((m_byBlockMode[nBlock] == QR_MODE_NUMERAL  && m_byBlockMode[nBlock + 1] == QR_MODE_AlphaBET) ||            (m_byBlockMode[nBlock] == QR_MODE_AlphaBET && m_byBlockMode[nBlock + 1] == QR_MODE_NUMERAL))        {            // 元のビット長と単一の英数字モードブロック化した場合のビット長を比較            ncSrcBits = GetBitLength(m_byBlockMode[nBlock],m_nBlockLength[nBlock],nVerGroup) +                GetBitLength(m_byBlockMode[nBlock + 1],m_nBlockLength[nBlock + 1],nVerGroup);            ncDstBits = GetBitLength(QR_MODE_AlphaBET,m_nBlockLength[nBlock] + m_nBlockLength[nBlock + 1],nVerGroup);            if (ncSrcBits > ncDstBits)            {                // 前後に8ビットバイトモードブロックがある場合、それらとの結合が有利かどうかをチェック                if (nBlock >= 1 && m_byBlockMode[nBlock - 1] == QR_MODE_8BIT)                {                    // 前に8ビットバイトモードブロックあり                    ncJoinFront = GetBitLength(QR_MODE_8BIT,m_nBlockLength[nBlock - 1] + m_nBlockLength[nBlock],nVerGroup) +                        GetBitLength(m_byBlockMode[nBlock + 1],nVerGroup);                    if (ncJoinFront > ncDstBits + GetBitLength(QR_MODE_8BIT,m_nBlockLength[nBlock - 1],nVerGroup))                        ncJoinFront = 0; // 8ビットバイトモードブロックとは結合しない                }                else                    ncJoinFront = 0;                if (nBlock < m_ncdataBlock - 2 && m_byBlockMode[nBlock + 2] == QR_MODE_8BIT)                {                    // 後ろに8ビットバイトモードブロックあり                    ncJoinBehind = GetBitLength(m_byBlockMode[nBlock],nVerGroup) +                        GetBitLength(QR_MODE_8BIT,m_nBlockLength[nBlock + 1] + m_nBlockLength[nBlock + 2],nVerGroup);                    if (ncJoinBehind > ncDstBits + GetBitLength(QR_MODE_8BIT,m_nBlockLength[nBlock + 2],nVerGroup))                        ncJoinBehind = 0; // 8ビットバイトモードブロックとは結合しない                }                else                    ncJoinBehind = 0;                if (ncJoinFront != 0 && ncJoinBehind != 0)                {                    // 前後両方に8ビットバイトモードブロックがある場合はデータ長が短くなる方を優先                    nJoinposition = (ncJoinFront < ncJoinBehind) ? -1 : 1;                }                else                {                    nJoinposition = (ncJoinFront != 0) ? -1 : ((ncJoinBehind != 0) ? 1 : 0);                }                if (nJoinposition != 0)                {                    // 8ビットバイトモードブロックとの結合                    if (nJoinposition == -1)                    {                        m_nBlockLength[nBlock - 1] += m_nBlockLength[nBlock];                        // 後続をシフト                        for (i = nBlock; i < m_ncdataBlock - 1; ++i)                        {                            m_byBlockMode[i] = m_byBlockMode[i + 1];                            m_nBlockLength[i] = m_nBlockLength[i + 1];                        }                    }                    else                    {                        m_byBlockMode[nBlock + 1] = QR_MODE_8BIT;                        m_nBlockLength[nBlock + 1] += m_nBlockLength[nBlock + 2];                        // 後続をシフト                        for (i = nBlock + 2; i < m_ncdataBlock - 1; ++i)                        {                            m_byBlockMode[i] = m_byBlockMode[i + 1];                            m_nBlockLength[i] = m_nBlockLength[i + 1];                        }                    }                    --m_ncdataBlock;                }                else                {                    // 英数字と数字の並びを単一の英数字モードブロックに統合                    if (nBlock < m_ncdataBlock - 2 && m_byBlockMode[nBlock + 2] == QR_MODE_AlphaBET)                    {                        // 結合しようとするブロックの後ろに続く英数字モードブロックを結合                        m_nBlockLength[nBlock + 1] += m_nBlockLength[nBlock + 2];                        // 後続をシフト                        for (i = nBlock + 2; i < m_ncdataBlock - 1; ++i)                        {                            m_byBlockMode[i] = m_byBlockMode[i + 1];                            m_nBlockLength[i] = m_nBlockLength[i + 1];                        }                        --m_ncdataBlock;                    }                    m_byBlockMode[nBlock] = QR_MODE_AlphaBET;                    m_nBlockLength[nBlock] += m_nBlockLength[nBlock + 1];                    // 後続をシフト                    for (i = nBlock + 1; i < m_ncdataBlock - 1; ++i)                    {                        m_byBlockMode[i] = m_byBlockMode[i + 1];                        m_nBlockLength[i] = m_nBlockLength[i + 1];                    }                    --m_ncdataBlock;                    if (nBlock >= 1 && m_byBlockMode[nBlock - 1] == QR_MODE_AlphaBET)                    {                        // 結合したブロックの前の英数字モードブロックを結合                        m_nBlockLength[nBlock - 1] += m_nBlockLength[nBlock];                        // 後続をシフト                        for (i = nBlock; i < m_ncdataBlock - 1; ++i)                        {                            m_byBlockMode[i] = m_byBlockMode[i + 1];                            m_nBlockLength[i] = m_nBlockLength[i + 1];                        }                        --m_ncdataBlock;                    }                }                continue; // 現在位置のブロックを再調査            }        }        ++nBlock; // 次ブロックを調査    }    /////////////////////////////////////////////////////////////////////////    // 連続する短いモードブロックを8ビットバイトモードブロック化    nBlock = 0;    while (nBlock < m_ncdataBlock - 1)    {        ncSrcBits = GetBitLength(m_byBlockMode[nBlock],nVerGroup)            + GetBitLength(m_byBlockMode[nBlock + 1],nVerGroup);        ncDstBits = GetBitLength(QR_MODE_8BIT,nVerGroup);        // 前に8ビットバイトモードブロックがある場合、重複するインジケータ分を減算        if (nBlock >= 1 && m_byBlockMode[nBlock - 1] == QR_MODE_8BIT)            ncDstBits -= (4 + nIndicatorLen8Bit[nVerGroup]);        // 後ろに8ビットバイトモードブロックがある場合、重複するインジケータ分を減算        if (nBlock < m_ncdataBlock - 2 && m_byBlockMode[nBlock + 2] == QR_MODE_8BIT)            ncDstBits -= (4 + nIndicatorLen8Bit[nVerGroup]);        if (ncSrcBits > ncDstBits)        {            if (nBlock >= 1 && m_byBlockMode[nBlock - 1] == QR_MODE_8BIT)            {                // 結合するブロックの前にある8ビットバイトモードブロックを結合                m_nBlockLength[nBlock - 1] += m_nBlockLength[nBlock];                // 後続をシフト                for (i = nBlock; i < m_ncdataBlock - 1; ++i)                {                    m_byBlockMode[i] = m_byBlockMode[i + 1];                    m_nBlockLength[i] = m_nBlockLength[i + 1];                }                --m_ncdataBlock;                --nBlock;            }            if (nBlock < m_ncdataBlock - 2 && m_byBlockMode[nBlock + 2] == QR_MODE_8BIT)            {                // 結合するブロックの後ろにある8ビットバイトモードブロックを結合                m_nBlockLength[nBlock + 1] += m_nBlockLength[nBlock + 2];                // 後続をシフト                for (i = nBlock + 2; i < m_ncdataBlock - 1; ++i)                {                    m_byBlockMode[i] = m_byBlockMode[i + 1];                    m_nBlockLength[i] = m_nBlockLength[i + 1];                }                --m_ncdataBlock;            }            m_byBlockMode[nBlock] = QR_MODE_8BIT;            m_nBlockLength[nBlock] += m_nBlockLength[nBlock + 1];            // 後続をシフト            for (i = nBlock + 1; i < m_ncdataBlock - 1; ++i)            {                m_byBlockMode[i] = m_byBlockMode[i + 1];                m_nBlockLength[i] = m_nBlockLength[i + 1];            }            --m_ncdataBlock;            // 結合したブロックの前から再調査            if (nBlock >= 1)                --nBlock;            continue;        }        ++nBlock; // 次ブロックを調査    }    /////////////////////////////////////////////////////////////////////////    // ビット配列化    int ncComplete = 0; // 処理済データカウンタ    unsigned short wbincode;    m_ncdataCodeWordBit = 0; // ビット単位処理カウンタ    memset(m_byDataCodeWord,MAX_DATACODEWORD);    for (i = 0; i < m_ncdataBlock && m_ncdataCodeWordBit != -1; ++i)    {        if (m_byBlockMode[i] == QR_MODE_NUMERAL)        {            /////////////////////////////////////////////////////////////////            // 数字モード            // インジケータ(0001b)            m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,4);            // 文字数セット            m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,(unsigned short)m_nBlockLength[i],nIndicatorLenNumeral[nVerGroup]);            // ビット列保存            for (j = 0; j < m_nBlockLength[i]; j += 3)            {                if (j < m_nBlockLength[i] - 2)                {                    wbincode = (unsigned short)(((lpsSource[ncComplete + j] - '0') * 100) +                        ((lpsSource[ncComplete + j + 1] - '0') * 10) +                        (lpsSource[ncComplete + j + 2] - '0'));                    m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,wbincode,10);                }                else if (j == m_nBlockLength[i] - 2)                {                    // 端数2バイト                    wbincode = (unsigned short)(((lpsSource[ncComplete + j] - '0') * 10) +                        (lpsSource[ncComplete + j + 1] - '0'));                    m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,7);                }                else if (j == m_nBlockLength[i] - 1)                {                    // 端数1バイト                    wbincode = (unsigned short)(lpsSource[ncComplete + j] - '0');                    m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,4);                }            }            ncComplete += m_nBlockLength[i];        }        else if (m_byBlockMode[i] == QR_MODE_AlphaBET)        {            /////////////////////////////////////////////////////////////////            // 英数字モード            // モードインジケータ(0010b)            m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,nIndicatorLenAlphabet[nVerGroup]);            // ビット列保存            for (j = 0; j < m_nBlockLength[i]; j += 2)            {                if (j < m_nBlockLength[i] - 1)                {                    wbincode = (unsigned short)((AlphabetToBinaly(lpsSource[ncComplete + j]) * 45) +                        AlphabetToBinaly(lpsSource[ncComplete + j + 1]));                    m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,11);                }                else                {                    // 端数1バイト                    wbincode = (unsigned short)AlphabetToBinaly(lpsSource[ncComplete + j]);                    m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,6);                }            }            ncComplete += m_nBlockLength[i];        }        else if (m_byBlockMode[i] == QR_MODE_8BIT)        {            /////////////////////////////////////////////////////////////////            // 8ビットバイトモード            // モードインジケータ(0100b)            m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,nIndicatorLen8Bit[nVerGroup]);            // ビット列保存            for (j = 0; j < m_nBlockLength[i]; ++j)            {                m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,(unsigned short)lpsSource[ncComplete + j],8);            }            ncComplete += m_nBlockLength[i];        }        else // m_byBlockMode[i] == QR_MODE_KANJI        {            /////////////////////////////////////////////////////////////////            // 漢字モード            // モードインジケータ(1000b)            m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,(unsigned short)(m_nBlockLength[i] / 2),nIndicatorLenKanji[nVerGroup]);            // 漢字モードでビット列保存            for (j = 0; j < m_nBlockLength[i] / 2; ++j)            {                unsigned short wbincode = KanjiToBinaly((unsigned short)(((unsigned char)lpsSource[ncComplete + (j * 2)] << 8) + (unsigned char)lpsSource[ncComplete + (j * 2) + 1]));                m_ncdataCodeWordBit = SetBitStream(m_ncdataCodeWordBit,13);            }            ncComplete += m_nBlockLength[i];        }    }    return (m_ncdataCodeWordBit != -1);}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::GetBitLengthint CQR_Encode::GetBitLength(unsigned char nMode,int nVerGroup){    int ncBits = 0;    switch (nMode)    {    case QR_MODE_NUMERAL:        ncBits = 4 + nIndicatorLenNumeral[nVerGroup] + (10 * (ncdata / 3));        switch (ncdata % 3)        {        case 1:            ncBits += 4;            break;        case 2:            ncBits += 7;            break;        default: // case 0:            break;        }        break;    case QR_MODE_AlphaBET:        ncBits = 4 + nIndicatorLenAlphabet[nVerGroup] + (11 * (ncdata / 2)) + (6 * (ncdata % 2));        break;    case QR_MODE_8BIT:        ncBits = 4 + nIndicatorLen8Bit[nVerGroup] + (8 * ncdata);        break;    default: // case QR_MODE_KANJI:        ncBits = 4 + nIndicatorLenKanji[nVerGroup] + (13 * (ncdata / 2));        break;    }    return ncBits;}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetBitStreamint CQR_Encode::SetBitStream(int nIndex,int ncdata){    int i;    if (nIndex == -1 || nIndex + ncdata > MAX_DATACODEWORD * 8)        return -1;    for (i = 0; i < ncdata; ++i)    {        if (wData & (1 << (ncdata - i - 1)))        {            m_byDataCodeWord[(nIndex + i) / 8] |= 1 << (7 - ((nIndex + i) % 8));        }    }    return nIndex + ncdata;}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::IsNumeralDatabool CQR_Encode::IsNumeralData(unsigned char c){    if (c >= '0' && c <= '9')        return 1;    return 0;}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::IsAlphabetDatabool CQR_Encode::IsAlphabetData(unsigned char c){    if (c >= '0' && c <= '9')        return 1;    if (c >= 'A' && c <= 'Z')        return 1;    if (c == ' ' || c == '$' || c == '%' || c == '*' || c == '+' || c == '-' || c == '.' || c == '/' || c == ':')        return 1;    return 0;}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::IsKanjIDatabool CQR_Encode::IsKanjIData(unsigned char c1,unsigned char c2){    if (((c1 >= 0x81 && c1 <= 0x9f) || (c1 >= 0xe0 && c1 <= 0xeb)) && (c2 >= 0x40))    {        if ((c1 == 0x9f && c2 > 0xfc) || (c1 == 0xeb && c2 > 0xbf))            return 0;        return 1;    }    return 0;}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::AlphabetToBinalyunsigned char CQR_Encode::AlphabetToBinaly(unsigned char c){    if (c >= '0' && c <= '9') return (unsigned char)(c - '0');    if (c >= 'A' && c <= 'Z') return (unsigned char)(c - 'A' + 10);    if (c == ' ') return 36;    if (c == '$') return 37;    if (c == '%') return 38;    if (c == '*') return 39;    if (c == '+') return 40;    if (c == '-') return 41;    if (c == '.') return 42;    if (c == '/') return 43;    return 44; // c == ':'}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::KanjiToBinalyunsigned short CQR_Encode::KanjiToBinaly(unsigned short wc){    if (wc >= 0x8140 && wc <= 0x9ffc)        wc -= 0x8140;    else // (wc >= 0xe040 && wc <= 0xebbf)        wc -= 0xc140;    return (unsigned short)(((wc >> 8) * 0xc0) + (wc & 0x00ff));}/////////////////////////////////////////////////////////////////////////////////// CQR_Encode::GetRSCodeWordvoID CQR_Encode::GetRSCodeWord(unsigned char* lpbyRSWork,int ncRSCodeWord){    int i,j;    for (i = 0; i < ncdataCodeWord; ++i)    {        if (lpbyRSWork[0] != 0)        {            unsigned char nExpFirst = byIntToExp[lpbyRSWork[0]]; // 初項係数より乗数算出            for (j = 0; j < ncRSCodeWord; ++j)            {                // 各項乗数に初項乗数を加算(% 255 → α^255 = 1)                unsigned char nExpElement = (unsigned char)(((int)(byRSExp[ncRSCodeWord][j] + nExpFirst)) % 255);                // 排他論理和による剰余算出                lpbyRSWork[j] = (unsigned char)(lpbyRSWork[j + 1] ^ byExpToInt[nExpElement]);            }            // 残り桁をシフト            for (j = ncRSCodeWord; j < ncdataCodeWord + ncRSCodeWord - 1; ++j)                lpbyRSWork[j] = lpbyRSWork[j + 1];        }        else        {            // 残り桁をシフト            for (j = 0; j < ncdataCodeWord + ncRSCodeWord - 1; ++j)                lpbyRSWork[j] = lpbyRSWork[j + 1];        }    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::FormatModulevoID CQR_Encode::FormatModule(){    int i,j;    memset(m_byModuleData,sizeof(m_byModuleData));    SetFunctionModule();    // データパターン配置    SetCodeWordPattern();    if (m_nMaskingNo == -1)    {        // 最適マスキングパターン選択        m_nMaskingNo = 0;        SetMaskingPattern(m_nMaskingNo); // マスキング        SetFormatInfoPattern(m_nMaskingNo); // フォーマット情報パターン配置        int nMinPenalty = CountPenalty();        for (i = 1; i <= 7; ++i)        {            SetMaskingPattern(i); // マスキング            SetFormatInfoPattern(i); // フォーマット情報パターン配置            int nPenalty = CountPenalty();            if (nPenalty < nMinPenalty)            {                nMinPenalty = nPenalty;                m_nMaskingNo = i;            }        }    }    SetMaskingPattern(m_nMaskingNo); // マスキング    SetFormatInfoPattern(m_nMaskingNo); // フォーマット情報パターン配置    // モジュールパターンをブール値に変換    for (i = 0; i < m_nSymbleSize; ++i)    {        for (j = 0; j < m_nSymbleSize; ++j)        {            m_byModuleData[i][j] = (unsigned char)((m_byModuleData[i][j] & 0x11) != 0);        }    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetFunctionModulevoID CQR_Encode::SetFunctionModule(){    int i,j;    // 位置検出パターン    SetFinderPattern(0,0);    SetFinderPattern(m_nSymbleSize - 7,0);    SetFinderPattern(0,m_nSymbleSize - 7);    // 位置検出パターンセパレータ    for (i = 0; i < 8; ++i)    {        m_byModuleData[i][7] = m_byModuleData[7][i] = '\x20';        m_byModuleData[m_nSymbleSize - 8][i] = m_byModuleData[m_nSymbleSize - 8 + i][7] = '\x20';        m_byModuleData[i][m_nSymbleSize - 8] = m_byModuleData[7][m_nSymbleSize - 8 + i] = '\x20';    }    // フォーマット情報記述位置を機能モジュール部として登録    for (i = 0; i < 9; ++i)    {        m_byModuleData[i][8] = m_byModuleData[8][i] = '\x20';    }    for (i = 0; i < 8; ++i)    {        m_byModuleData[m_nSymbleSize - 8 + i][8] = m_byModuleData[8][m_nSymbleSize - 8 + i] = '\x20';    }    // バージョン情報パターン    SetVersionPattern();    // 位置合わせパターン    for (i = 0; i < QR_VersonInfo[m_nVersion].ncAlignPoint; ++i)    {        SetAlignmentPattern(QR_VersonInfo[m_nVersion].nAlignPoint[i],6);        SetAlignmentPattern(6,QR_VersonInfo[m_nVersion].nAlignPoint[i]);        for (j = 0; j < QR_VersonInfo[m_nVersion].ncAlignPoint; ++j)        {            SetAlignmentPattern(QR_VersonInfo[m_nVersion].nAlignPoint[i],QR_VersonInfo[m_nVersion].nAlignPoint[j]);        }    }    // タイミングパターン    for (i = 8; i <= m_nSymbleSize - 9; ++i)    {        m_byModuleData[i][6] = (i % 2) == 0 ? '\x30' : '\x20';        m_byModuleData[6][i] = (i % 2) == 0 ? '\x30' : '\x20';    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetFinderPatternvoID CQR_Encode::SetFinderPattern(int x,int y){    static unsigned char byPattern[] = { 0x7f,// 1111111b        0x41,// 1000001b        0x5d,// 1011101b        0x5d,// 1011101b        0x41,// 1000001b        0x7f }; // 1111111b    int i,j;    for (i = 0; i < 7; ++i)    {        for (j = 0; j < 7; ++j)        {            m_byModuleData[x + j][y + i] = (byPattern[i] & (1 << (6 - j))) ? '\x30' : '\x20';        }    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetAlignmentPatternvoID CQR_Encode::SetAlignmentPattern(int x,int y){    static unsigned char byPattern[] = { 0x1f,// 11111b        0x11,// 10001b        0x15,// 10101b        0x11,// 10001b        0x1f }; // 11111b    int i,j;    if (m_byModuleData[x][y] & 0x20)        return; // 機能モジュールと重複するため除外    x -= 2; y -= 2; // 左上隅座標に変換    for (i = 0; i < 5; ++i)    {        for (j = 0; j < 5; ++j)        {            m_byModuleData[x + j][y + i] = (byPattern[i] & (1 << (4 - j))) ? '\x30' : '\x20';        }    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetVersionPatternvoID CQR_Encode::SetVersionPattern(){    int i,j;    if (m_nVersion <= 6)        return;    int nVerData = m_nVersion << 12;    // 剰余ビット算出    for (i = 0; i < 6; ++i)    {        if (nVerData & (1 << (17 - i)))        {            nVerData ^= (0x1f25 << (5 - i));        }    }    nVerData += m_nVersion << 12;    for (i = 0; i < 6; ++i)    {        for (j = 0; j < 3; ++j)        {            m_byModuleData[m_nSymbleSize - 11 + j][i] = m_byModuleData[i][m_nSymbleSize - 11 + j] =                (nVerData & (1 << (i * 3 + j))) ? '\x30' : '\x20';        }    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetCodeWordPatternvoID CQR_Encode::SetCodeWordPattern(){    int x = m_nSymbleSize;    int y = m_nSymbleSize - 1;    int nCoef_x = 1; // x軸配置向き    int nCoef_y = 1; // y軸配置向き    int i,j;    for (i = 0; i < m_ncAllCodeWord; ++i)    {        for (j = 0; j < 8; ++j)        {            do            {                x += nCoef_x;                nCoef_x *= -1;                if (nCoef_x < 0)                {                    y += nCoef_y;                    if (y < 0 || y == m_nSymbleSize)                    {                        y = (y < 0) ? 0 : m_nSymbleSize - 1;                        nCoef_y *= -1;                        x -= 2;                        if (x == 6) // タイミングパターン                            --x;                    }                }            } while (m_byModuleData[x][y] & 0x20); // 機能モジュールを除外            m_byModuleData[x][y] = (m_byAllCodeWord[i] & (1 << (7 - j))) ? '\x02' : '\x00';        }    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetMaskingPatternvoID CQR_Encode::SetMaskingPattern(int nPatternNo){    int i,j;    for (i = 0; i < m_nSymbleSize; ++i)    {        for (j = 0; j < m_nSymbleSize; ++j)        {            if (!(m_byModuleData[j][i] & 0x20)) // 機能モジュールを除外            {                bool bMask;                switch (nPatternNo)                {                case 0:                    bMask = ((i + j) % 2 == 0);                    break;                case 1:                    bMask = (i % 2 == 0);                    break;                case 2:                    bMask = (j % 3 == 0);                    break;                case 3:                    bMask = ((i + j) % 3 == 0);                    break;                case 4:                    bMask = (((i / 2) + (j / 3)) % 2 == 0);                    break;                case 5:                    bMask = (((i * j) % 2) + ((i * j) % 3) == 0);                    break;                case 6:                    bMask = ((((i * j) % 2) + ((i * j) % 3)) % 2 == 0);                    break;                default: // case 7:                    bMask = ((((i * j) % 3) + ((i + j) % 2)) % 2 == 0);                    break;                }                m_byModuleData[j][i] = (unsigned char)((m_byModuleData[j][i] & 0xfe) | (((m_byModuleData[j][i] & 0x02) > 1) ^ bMask));            }        }    }}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::SetFormatInfoPatternvoID CQR_Encode::SetFormatInfoPattern(int nPatternNo){    int nFormatInfo;    int i;    switch (m_nLevel)    {    case QR_LEVEL_M:        nFormatInfo = 0x00; // 00nnnb        break;    case QR_LEVEL_L:        nFormatInfo = 0x08; // 01nnnb        break;    case QR_LEVEL_Q:        nFormatInfo = 0x18; // 11nnnb        break;    default: // case QR_LEVEL_H:        nFormatInfo = 0x10; // 10nnnb        break;    }    nFormatInfo += nPatternNo;    int nFormatData = nFormatInfo << 10;    // 剰余ビット算出    for (i = 0; i < 5; ++i)    {        if (nFormatData & (1 << (14 - i)))        {            nFormatData ^= (0x0537 << (4 - i)); // 10100110111b        }    }    nFormatData += nFormatInfo << 10;    // マスキング    nFormatData ^= 0x5412; // 101010000010010b    // 左上位置検出パターン周り配置    for (i = 0; i <= 5; ++i)        m_byModuleData[8][i] = (nFormatData & (1 << i)) ? '\x30' : '\x20';    m_byModuleData[8][7] = (nFormatData & (1 << 6)) ? '\x30' : '\x20';    m_byModuleData[8][8] = (nFormatData & (1 << 7)) ? '\x30' : '\x20';    m_byModuleData[7][8] = (nFormatData & (1 << 8)) ? '\x30' : '\x20';    for (i = 9; i <= 14; ++i)        m_byModuleData[14 - i][8] = (nFormatData & (1 << i)) ? '\x30' : '\x20';    // 右上位置検出パターン下配置    for (i = 0; i <= 7; ++i)        m_byModuleData[m_nSymbleSize - 1 - i][8] = (nFormatData & (1 << i)) ? '\x30' : '\x20';    // 左下位置検出パターン右配置    m_byModuleData[8][m_nSymbleSize - 8] = '\x30'; // 固定暗モジュール    for (i = 8; i <= 14; ++i)        m_byModuleData[8][m_nSymbleSize - 15 + i] = (nFormatData & (1 << i)) ? '\x30' : '\x20';}/////////////////////////////////////////////////////////////////////////////// CQR_Encode::CountPenaltyint CQR_Encode::CountPenalty(){    int nPenalty = 0;    int i,j,k;    // 同色の列の隣接モジュール    for (i = 0; i < m_nSymbleSize; ++i)    {        for (j = 0; j < m_nSymbleSize - 4; ++j)        {            int nCount = 1;            for (k = j + 1; k < m_nSymbleSize; k++)            {                if (((m_byModuleData[i][j] & 0x11) == 0) == ((m_byModuleData[i][k] & 0x11) == 0))                    ++nCount;                else                    break;            }            if (nCount >= 5)            {                nPenalty += 3 + (nCount - 5);            }            j = k - 1;        }    }    // 同色の行の隣接モジュール    for (i = 0; i < m_nSymbleSize; ++i)    {        for (j = 0; j < m_nSymbleSize - 4; ++j)        {            int nCount = 1;            for (k = j + 1; k < m_nSymbleSize; k++)            {                if (((m_byModuleData[j][i] & 0x11) == 0) == ((m_byModuleData[k][i] & 0x11) == 0))                    ++nCount;                else                    break;            }            if (nCount >= 5)            {                nPenalty += 3 + (nCount - 5);            }            j = k - 1;        }    }    for (i = 0; i < m_nSymbleSize - 1; ++i)    {        for (j = 0; j < m_nSymbleSize - 1; ++j)        {            if ((((m_byModuleData[i][j] & 0x11) == 0) == ((m_byModuleData[i + 1][j] & 0x11) == 0)) &&                (((m_byModuleData[i][j] & 0x11) == 0) == ((m_byModuleData[i][j + 1] & 0x11) == 0)) &&                (((m_byModuleData[i][j] & 0x11) == 0) == ((m_byModuleData[i + 1][j + 1] & 0x11) == 0)))            {                nPenalty += 3;            }        }    }    for (i = 0; i < m_nSymbleSize; ++i)    {        for (j = 0; j < m_nSymbleSize - 6; ++j)        {            if (((j == 0) || (!(m_byModuleData[i][j - 1] & 0x11))) &&                (m_byModuleData[i][j] & 0x11) &&                (!(m_byModuleData[i][j + 1] & 0x11)) &&                (m_byModuleData[i][j + 2] & 0x11) &&                (m_byModuleData[i][j + 3] & 0x11) &&                (m_byModuleData[i][j + 4] & 0x11) &&                (!(m_byModuleData[i][j + 5] & 0x11)) &&                (m_byModuleData[i][j + 6] & 0x11) &&                ((j == m_nSymbleSize - 7) || (!(m_byModuleData[i][j + 7] & 0x11))))            {                // 前または後に4以上の明パターン                if (((j < 2 || !(m_byModuleData[i][j - 2] & 0x11)) &&                    (j < 3 || !(m_byModuleData[i][j - 3] & 0x11)) &&                    (j < 4 || !(m_byModuleData[i][j - 4] & 0x11))) ||                    ((j >= m_nSymbleSize - 8 || !(m_byModuleData[i][j + 8] & 0x11)) &&                    (j >= m_nSymbleSize - 9 || !(m_byModuleData[i][j + 9] & 0x11)) &&                    (j >= m_nSymbleSize - 10 || !(m_byModuleData[i][j + 10] & 0x11))))                {                    nPenalty += 40;                }            }        }    }    // 同一行における 1:1:3:1:1 比率(暗:明:暗:明:暗)のパターン    for (i = 0; i < m_nSymbleSize; ++i)    {        for (j = 0; j < m_nSymbleSize - 6; ++j)        {            if (((j == 0) || (!(m_byModuleData[j - 1][i] & 0x11))) && // 明 または シンボル外                (m_byModuleData[j][i] & 0x11) && // 暗 - 1                (!(m_byModuleData[j + 1][i] & 0x11)) && // 明 - 1                (m_byModuleData[j + 2][i] & 0x11) && // 暗 ┐                (m_byModuleData[j + 3][i] & 0x11) && // 暗 │3                (m_byModuleData[j + 4][i] & 0x11) && // 暗 ┘                (!(m_byModuleData[j + 5][i] & 0x11)) && // 明 - 1                (m_byModuleData[j + 6][i] & 0x11) && // 暗 - 1                ((j == m_nSymbleSize - 7) || (!(m_byModuleData[j + 7][i] & 0x11))))   // 明 または シンボル外            {                // 前または後に4以上の明パターン                if (((j < 2 || !(m_byModuleData[j - 2][i] & 0x11)) &&                    (j < 3 || !(m_byModuleData[j - 3][i] & 0x11)) &&                    (j < 4 || !(m_byModuleData[j - 4][i] & 0x11))) ||                    ((j >= m_nSymbleSize - 8 || !(m_byModuleData[j + 8][i] & 0x11)) &&                    (j >= m_nSymbleSize - 9 || !(m_byModuleData[j + 9][i] & 0x11)) &&                    (j >= m_nSymbleSize - 10 || !(m_byModuleData[j + 10][i] & 0x11))))                {                    nPenalty += 40;                }            }        }    }    // 全体に対する暗モジュールの占める割合    int nCount = 0;    for (i = 0; i < m_nSymbleSize; ++i)    {        for (j = 0; j < m_nSymbleSize; ++j)        {            if (!(m_byModuleData[i][j] & 0x11))            {                ++nCount;            }        }    }    nPenalty += (abs(50 - ((nCount * 100) / (m_nSymbleSize * m_nSymbleSize))) / 5) * 10;    return nPenalty;}}


cocos2dx 使用 drawNode 绘制:

cocos2d::Node* Appinformation::getQR(std::string uri,std::string colorStr){	CQR_Encode m_QREncode;	bool bRet = m_QREncode.EncodeData(0,-1,const_cast<char *> (uri.c_str()));	// 添加生成图像代码,这边我采用的是CCDrawNode这个类直接绘制	if (bRet)	{		int nSize = 5;			// 格子大小		int originalSize = m_QREncode.m_nSymbleSize + (QR_margin * 2);		CCDrawNode *pQRNode = CCDrawNode::create();		CCPoint pt[6];		cccolor4F color;		pt[0] = ccp(0,0);		pt[1] = ccp((m_QREncode.m_nSymbleSize + QR_margin * 2)*nSize,(m_QREncode.m_nSymbleSize + QR_margin * 2)*nSize);		pt[2] = ccp((m_QREncode.m_nSymbleSize + QR_margin * 2)*nSize,0);		pt[3] = pt[0];		pt[4] = ccp(0,(m_QREncode.m_nSymbleSize + QR_margin * 2)*nSize);		pt[5] = pt[1];        color = ccc4f(1,1);		pQRNode->drawpolygon(pt,color,color);		for (int i = 0; i < m_QREncode.m_nSymbleSize; ++i)		{			for (int j = 0; j < m_QREncode.m_nSymbleSize; ++j)			{				pt[0] = ccp((i + QR_margin)*nSize,(j + QR_margin)*nSize);				pt[1] = ccp(((i + QR_margin) + 1)*nSize,((j + QR_margin) + 1)*nSize);				pt[2] = ccp(((i + QR_margin) + 1)*nSize,((j + QR_margin) + 0)*nSize);				pt[3] = pt[0];				pt[4] = ccp(((i + QR_margin) + 0)*nSize,((j + QR_margin) + 1)*nSize);				pt[5] = pt[1];				if (m_QREncode.m_byModuleData[i][j] == 1)				{                    if (!colorStr.empty()) {                        vector<float> rgb(3);                        char szValue[6];                        strcpy(szValue,colorStr.c_str());                                                char * pch;                        pch = strtok (szValue,":");                        int index = 0;                        while (pch != NulL)                        {                            char ch[6];                            int nValude = 0;                            sscanf(pch,"%x",&nValude);                            rgb[index] = (float)nValude / 255;                            pch = strtok (NulL,":");                            index++;                        }                        color = ccc4f(rgb[0],rgb[1],rgb[2],1);                    } else {                        color = ccc4f(0,1);                    }				}                else                {                    color = ccc4f(1,1);                }				pQRNode->drawpolygon(pt,color);			}		}		//CCSize winSize = CCDirector::sharedDirector()->getWinSize();		//pQRNode->setposition(ccp((winSize.wIDth - nSize*m_QREncode.m_nSymbleSize) / 2,winSize.height - (winSize.height - nSize*m_QREncode.m_nSymbleSize) / 2));		//pQRNode->setScaleY(-1);		//addChild(pQRNode);		return pQRNode;	}	return nullptr;}
总结

以上是内存溢出为你收集整理的生成二维码点阵 ,并在 cocos2dx 中绘制全部内容,希望文章能够帮你解决生成二维码点阵 ,并在 cocos2dx 中绘制所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/web/1085340.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-27
下一篇 2022-05-27

发表评论

登录后才能评论

评论列表(0条)

保存