private static int[] PolynomialDevision(ErrorCorrectionLvl ErrCorr, int version, int[] FullDataInts) { int ErrCorrectionCodewordsCount; int[] MessagePolynomial; AlphaPow[] GeneratorPolinomial; int DevisionSteps; int[] GeneratorPolinomialInt; int[] XORresult; ErrCorrectionCodewordsCount = ErrorCorrectionTable.GetErrorCorrectionCodewordsPerBlock(ErrCorr, version); MessagePolynomial = FullDataInts; GeneratorPolinomial = Helper.generatePolinomial(ErrCorrectionCodewordsCount); Array.Reverse(GeneratorPolinomial); DevisionSteps = MessagePolynomial.Length; // int[] mult = new int[ErrCorrectionCodewordsCount]; //DevisionSteps->ErrCorrectionCodewordsCount MessagePolynomial = Helper.joinArrs <int> (MessagePolynomial, mult); AlphaPow[] mult1 = new AlphaPow[MessagePolynomial.Length - GeneratorPolinomial.Length]; for (int i = 0; i < mult1.Length; i++) { mult1[i] = new AlphaPow(-1, false); } GeneratorPolinomial = Helper.joinArrs <AlphaPow> (GeneratorPolinomial, mult1); GeneratorPolinomialInt = new int[GeneratorPolinomial.Length]; bool[][] Codewords = new bool[DevisionSteps][]; //first step AlphaPow[] GenPolRes = new AlphaPow[GeneratorPolinomial.Length]; Array.Copy(GeneratorPolinomial, GenPolRes, GeneratorPolinomial.Length); for (int j = 0; j < GeneratorPolinomial.Length; j++) { if (GenPolRes[j].pow == -1) { GeneratorPolinomialInt[j] = 0; } else { AlphaPow a = new AlphaPow(AlphaPow.getPow(MessagePolynomial[0]), false); GenPolRes[j] *= a; GeneratorPolinomialInt[j] = GenPolRes[j].getInt(); //GeneratorPolinomial[j] = new AlphaPow( AlphaPow.getPow( GeneratorPolinomialInt[j] ^ MessagePolynomial[j]),false); } } XORresult = new int[GeneratorPolinomial.Length]; for (int j = 0; j < GeneratorPolinomial.Length; j++) { XORresult[j] = GeneratorPolinomialInt[j] ^ MessagePolynomial[j]; } if (XORresult[0] == 0) { int[] tempIntArr = new int[XORresult.Length - 1]; Array.Copy(XORresult, 1, tempIntArr, 0, tempIntArr.Length); XORresult = new int[tempIntArr.Length]; Array.Copy(tempIntArr, XORresult, tempIntArr.Length); } AlphaPow[] tempArr = new AlphaPow[GeneratorPolinomial.Length - 1]; Array.Copy(GeneratorPolinomial, 0, tempArr, 0, GeneratorPolinomial.Length - 1); GeneratorPolinomial = new AlphaPow[tempArr.Length]; Array.Copy(tempArr, GeneratorPolinomial, tempArr.Length); ////////////////// bool[][] DataCodewords = new bool[DevisionSteps][]; DataCodewords[0] = new bool[8]; bool[] tempT = Encode.Binary( XORresult[0]); for (int up = 0; up < 8; up++) { DataCodewords[0][up] = tempT[up]; } Array.Copy(tempT, DataCodewords[0], 8); for (int i = 1; i < DevisionSteps; i++) { DataCodewords[i] = new bool[8]; //Array.Copy(Encoder.Binary(XORresult[0]), DataCodewords[i], 8); for (int up = 0; up < 8; up++) { DataCodewords[0][up] = Encode.Binary(XORresult[0])[up]; } Array.Copy(GeneratorPolinomial, GenPolRes, GeneratorPolinomial.Length); for (int j = 0; j < GeneratorPolinomial.Length; j++) { if (GenPolRes[j].pow == -1) { GeneratorPolinomialInt[j] = 0; } else { AlphaPow a = new AlphaPow(AlphaPow.getPow(XORresult[0]), false); GenPolRes[j] *= a; GeneratorPolinomialInt[j] = GenPolRes[j].getInt(); //GeneratorPolinomial[j] = new AlphaPow( AlphaPow.getPow( GeneratorPolinomialInt[j] ^ MessagePolynomial[j]),false); } } int[] XORtemp = new int[XORresult.Length]; Array.Copy(XORresult, XORtemp, XORresult.Length); XORresult = new int[GeneratorPolinomial.Length]; for (int j = 0; j < GeneratorPolinomial.Length; j++) { XORresult[j] = GeneratorPolinomialInt[j] ^ XORtemp[j]; } if (XORresult[0] == 0) { int[] tempIntArr = new int[XORresult.Length - 1]; Array.Copy(XORresult, 1, tempIntArr, 0, tempIntArr.Length); XORresult = new int[tempIntArr.Length]; Array.Copy(tempIntArr, XORresult, tempIntArr.Length); } tempArr = new AlphaPow[GeneratorPolinomial.Length - 1]; Array.Copy(GeneratorPolinomial, 0, tempArr, 0, GeneratorPolinomial.Length - 1); GeneratorPolinomial = new AlphaPow[tempArr.Length]; Array.Copy(tempArr, GeneratorPolinomial, tempArr.Length); } int size = XORresult.Length; //for ( int i = 0 ; i < size ; i++ ) { // if ( XORresult[i] == 0 ) { // int[] Xtemp = new int[i]; // Array.Copy ( XORresult , 0 , Xtemp , 0 , i ); // XORresult = new int[Xtemp.Length]; // Array.Copy ( Xtemp , XORresult , Xtemp.Length ); // break; // } //} ////////////////// for (int i = size - 1; i >= 0; i--) { if (XORresult[i] == 0) { int[] Xtemp = new int[i]; Array.Copy(XORresult, 0, Xtemp, 0, i); XORresult = new int[Xtemp.Length]; Array.Copy(Xtemp, XORresult, Xtemp.Length); } else { break; } } return(XORresult); }
public static Bitmap GetImage(EncodeProperties properties, out int QRCodeVersion, MaskPatterns maskPattern = MaskPatterns.Pattern0) { if (properties == null) { throw new NullReferenceException("empty properties"); } // ReSharper disable once InconsistentNaming Bitmap QRCodeBitmap = new Bitmap(properties.Size, properties.Size); int maxLength; int version; bool[] modeSequence; bool[] InputData; int RequestedCapacity; bool[] Terminator; bool[] Additoin0s; bool[] FullData; bool[] CharacterCountIndicator; int CharacterCountIndicatorLength; CharacterCapacities.GetMaxCapacityAndVersion(properties.Text, properties.ErrorCorrectionLvl, properties.Mode, out version, out maxLength); CharacterCountIndicatorLength = CharacterCapacities.GetCharacterCountIndicatorLength(version, properties.Mode); switch (properties.Mode) { case EncodeMode.Numeric: InputData = Encode.Numeric(properties.Text); modeSequence = new[] { false, false, false, true }; break; case EncodeMode.Alphanumeric: InputData = Encode.Alphanumeric(properties.Text); modeSequence = new[] { false, false, true, false }; break; default: throw new NotImplementedException(); break; } CharacterCountIndicator = GetCharacterCountIndicator(properties.Text, CharacterCountIndicatorLength); #region fill Data to Max Capacity (Terminator) RequestedCapacity = ErrorCorrectionTable.getTotalDataCodeBits((int)properties.ErrorCorrectionLvl, version); int missingSymbCount = RequestedCapacity - InputData.Length - CharacterCountIndicatorLength - modeSequence.Length; if (missingSymbCount > 4) { Terminator = new bool[4]; Terminator[0] = false; Terminator[1] = false; Terminator[2] = false; Terminator[3] = false; int adding = 8 - (InputData.Length + CharacterCountIndicatorLength + modeSequence.Length + Terminator.Length) % 8; if (adding == 8) { adding = 0; } Additoin0s = new bool[adding]; for (int i = 0; i < adding; i++) { Additoin0s[i] = false; } Helper.joinArrs <bool> (ref Terminator, Additoin0s); bool[] Pad1 = { true, true, true, false, true, true, false, false }; bool[] Pad2 = { false, false, false, true, false, false, false, true }; missingSymbCount = RequestedCapacity - InputData.Length - CharacterCountIndicatorLength - modeSequence.Length - Terminator.Length; while (missingSymbCount > 0) { Helper.joinArrs <bool> (ref Terminator, Pad1); missingSymbCount = RequestedCapacity - InputData.Length - CharacterCountIndicatorLength - modeSequence.Length - Terminator.Length; if (missingSymbCount > 0) { Helper.joinArrs <bool> (ref Terminator, Pad2); } else { break; } missingSymbCount = RequestedCapacity - InputData.Length - CharacterCountIndicatorLength - modeSequence.Length - Terminator.Length; } } else { Terminator = new bool[missingSymbCount]; Additoin0s = new bool[0]; for (int i = 0; i < missingSymbCount; i++) { Terminator[i] = false; } } #endregion FullData = modeSequence; Helper.joinArrs <bool>(ref FullData, CharacterCountIndicator); Helper.joinArrs <bool> (ref FullData, InputData); Helper.joinArrs <bool> (ref FullData, Terminator); #region BLOCKING and polynomial devisions int numOfBlocksInGroup1 = ErrorCorrectionTable.GetNumOfBlocksInGroup1(properties.ErrorCorrectionLvl, version); int numOfBlocksInGroup2 = ErrorCorrectionTable.GetNumOfBlocksInGroup2(properties.ErrorCorrectionLvl, version); int numOfCodeWordsInBlocksInGroup1 = ErrorCorrectionTable.GetNumOfCodeWordsInBlocksInGroup1(properties.ErrorCorrectionLvl, version); int numOfCodeWordsInBlocksInGroup2 = ErrorCorrectionTable.GetNumOfCodeWordsInBlocksInGroup2(properties.ErrorCorrectionLvl, version); int numOfECCodewordsPerBlock = ErrorCorrectionTable.GetErrorCorrectionCodewordsPerBlock(properties.ErrorCorrectionLvl, version); int iteratorFullData = 0; BlockOfCodeWords[] groupOfDataCodewords1 = null; BlockOfCodeWords[] groupOfDataCodewords2 = null; BlockOfCodeWords[] groupOfECCodewords1 = null; BlockOfCodeWords[] groupOfECCodewords2 = null; int[] FullDataInts = Encode.UnBinary(FullData, 8); if (numOfBlocksInGroup1 > 0) { groupOfDataCodewords1 = new BlockOfCodeWords[numOfBlocksInGroup1]; groupOfECCodewords1 = new BlockOfCodeWords[numOfBlocksInGroup1]; for (int i = 0; i < numOfBlocksInGroup1; i++) { groupOfDataCodewords1[i] = new BlockOfCodeWords(); groupOfDataCodewords1[i].CodeWords = new int[numOfCodeWordsInBlocksInGroup1]; for (int j = 0; j < numOfCodeWordsInBlocksInGroup1; j++) { groupOfDataCodewords1[i].CodeWords[j] = FullDataInts[iteratorFullData]; iteratorFullData++; } groupOfECCodewords1[i] = new BlockOfCodeWords(); groupOfECCodewords1[i].CodeWords = PolynomialDevision(properties.ErrorCorrectionLvl, version, groupOfDataCodewords1[i].CodeWords); } } if (numOfBlocksInGroup2 > 0) { groupOfDataCodewords2 = new BlockOfCodeWords[numOfBlocksInGroup2]; groupOfECCodewords2 = new BlockOfCodeWords[numOfBlocksInGroup2]; for (int i = 0; i < numOfBlocksInGroup2; i++) { groupOfDataCodewords2[i] = new BlockOfCodeWords(); groupOfDataCodewords2[i].CodeWords = new int[numOfCodeWordsInBlocksInGroup2]; for (int j = 0; j < numOfCodeWordsInBlocksInGroup2; j++) { groupOfDataCodewords2[i].CodeWords[j] = FullDataInts[iteratorFullData]; iteratorFullData++; } groupOfECCodewords2[i] = new BlockOfCodeWords(); groupOfECCodewords2[i].CodeWords = PolynomialDevision(properties.ErrorCorrectionLvl, version, groupOfDataCodewords2[i].CodeWords); } } int[] FullMessageData = new int[FullDataInts.Length]; int[] FullMessageEC = new int[ groupOfDataCodewords2 == null ? numOfBlocksInGroup1 * numOfECCodewordsPerBlock : (numOfBlocksInGroup1 + numOfBlocksInGroup2) * numOfECCodewordsPerBlock]; int iteratorFullMessageData = 0; int iteratorFullMessageEC = 0; int forMam = numOfCodeWordsInBlocksInGroup2 > 0 ? numOfCodeWordsInBlocksInGroup2 : numOfCodeWordsInBlocksInGroup1; for (int i = 0; i < forMam; i++) { if (groupOfDataCodewords1 != null && numOfCodeWordsInBlocksInGroup1 > i) { for (int j = 0; j < numOfBlocksInGroup1; j++) { FullMessageData[iteratorFullMessageData] = groupOfDataCodewords1[j].CodeWords[i]; iteratorFullMessageData++; } } if (groupOfDataCodewords2 != null) { for (int j = 0; j < numOfBlocksInGroup2; j++) { FullMessageData[iteratorFullMessageData] = groupOfDataCodewords2[j].CodeWords[i]; iteratorFullMessageData++; } } } for (int i = 0; i < numOfECCodewordsPerBlock; i++) { if (groupOfECCodewords1 != null) { for (int j = 0; j < numOfBlocksInGroup1; j++) { FullMessageEC[iteratorFullMessageEC] = groupOfECCodewords1[j].CodeWords[i]; iteratorFullMessageEC++; } } if (groupOfECCodewords2 != null) { for (int j = 0; j < numOfBlocksInGroup2; j++) { FullMessageEC[iteratorFullMessageEC] = groupOfECCodewords2[j].CodeWords[i]; iteratorFullMessageEC++; } } } var LastFullMessageInts = Helper.joinArrs(FullMessageData, FullMessageEC); var LastFullMessageBools = new bool[0]; for (int i = 0; i < LastFullMessageInts.Length; i++) { Helper.joinArrs <bool> (ref LastFullMessageBools, Encode.Binary(LastFullMessageInts[i])); } #endregion //var XORresult = PolynomialDevision ( properties.ErrorCorrectionLvl , version , FullDataInts ); //var ErrCorrKeyWord = new bool[0]; //for ( int i = 0 ; i < XORresult.Length ; i++ ) { // Helper.joinArrs<bool> ( ref ErrCorrKeyWord , Encode.Binary ( XORresult[i] ) ); //} QRCodeVersion = version; return(Generate(version, CharacterCountIndicator, InputData, Terminator, modeSequence, LastFullMessageBools, 5, properties.ErrorCorrectionLvl, maskPattern)); }