public static QrSegment MakeAlphanumeric(string text)
        {
            Utils.CheckNull(text, nameof(text));

            if (text.Any(c => !ALPHANUMERIC_CHARSET.Contains(c)))
            {
                throw new ArgumentException("String contains unencodable characters in alphanumeric mode");
            }

            var bb = new BitBuffer();
            int i;

            for (i = 0; i <= text.Length - 2; i += 2)
            {
                var temp = ALPHANUMERIC_CHARSET.IndexOf(text[i]) * 45;
                temp += ALPHANUMERIC_CHARSET.IndexOf(text[i + 1]);
                bb.AppendBits(temp, 11);
            }

            if (i < text.Length)
            {
                bb.AppendBits(ALPHANUMERIC_CHARSET.IndexOf(text[i]), 6);
            }

            return(new QrSegment(Mode.ALPHANUMERIC, text.Length, bb));
        }
        public static QrSegment MakeEci(int assignVal)
        {
            var bb = new BitBuffer();

            if (assignVal < 0)
            {
                throw new ArgumentException("ECI assignment value out of range");
            }
            else if (assignVal < (1 << 7))
            {
                bb.AppendBits(assignVal, 8);
            }
            else if (assignVal < (1 << 14))
            {
                bb.AppendBits(2, 2);
                bb.AppendBits(assignVal, 14);
            }
            else if (assignVal < 1_000_000)
            {
                bb.AppendBits(6, 3);
                bb.AppendBits(assignVal, 21);
            }
            else
            {
                throw new ArgumentException("ECI assignment value out of range");
            }

            return(new QrSegment(Mode.ECI, 0, bb));
        }
        public static QrSegment MakeBytes(byte[] data)
        {
            Utils.CheckNull(data, nameof(data));

            var bb = new BitBuffer();

            foreach (var b in data)
            {
                bb.AppendBits(b & 0xFF, 8);
            }

            return(new QrSegment(Mode.BYTE, data.Length, bb));
        }
        public static QrSegment MakeKanji(string text)
        {
            Utils.CheckNull(text, nameof(text));

            var bb = new BitBuffer();

            foreach (var c in text)
            {
                var val = UNICODE_TO_QR_KANJI[c];
                if (val == -1)
                {
                    throw new ArgumentException("String contains non-kanji-mode characters");
                }
                bb.AppendBits(val, 13);
            }
            return(new QrSegment(Mode.KANJI, text.Length, bb));
        }
        public static QrSegment MakeNumeric(string digits)
        {
            Utils.CheckNull(digits, nameof(digits));
            if (digits.Any(c => !char.IsDigit(c)))
            {
                throw new ArgumentException("String contains non-numeric characters");
            }

            var bb = new BitBuffer();

            for (int i = 0; i < digits.Length;)
            {
                var n = Math.Min(digits.Length - i, 3);
                bb.AppendBits(int.Parse(digits.AsSpan().Slice(i, n)), n * 3 + 1);
                i += n;
            }
            return(new QrSegment(Mode.NUMERIC, digits.Length, bb));
        }
Exemple #6
0
        public static QrCode EncodeSegments(List <QrSegment> segs, Ecc ecl, int minVersion, int maxVersion, int mask, bool boostEcl)
        {
            Utils.CheckNull(segs, nameof(segs));

            if (!(MIN_VERSION <= minVersion && minVersion <= maxVersion && maxVersion <= MAX_VERSION) || mask < -1 || mask > 7)
            {
                throw new ArgumentException("Invalid value");
            }

            int version, dataUsedBits;

            for (version = minVersion; ; version++)
            {
                var capacityBits = GetNumDataCodewords(version, ecl) * 8;
                dataUsedBits = QrSegment.GetTotalBits(segs, version);
                if (dataUsedBits != -1 && dataUsedBits <= capacityBits)
                {
                    break;
                }

                if (version >= maxVersion)
                {
                    var msg = "Segment too long";
                    if (dataUsedBits != -1)
                    {
                        msg = string.Format("Data length = {0} bits, Max capacity = {1} bits", dataUsedBits, capacityBits);
                    }
                    throw new DataTooLongException(msg);
                }
            }

            foreach (var newEcl in new Ecc[] { Ecc.Low, Ecc.Medium, Ecc.Quartitle, Ecc.High })
            {
                if (boostEcl && dataUsedBits <= GetNumDataCodewords(version, newEcl) * 8)
                {
                    ecl = newEcl;
                }
            }

            var bb = new BitBuffer();

            foreach (var seg in segs)
            {
                bb.AppendBits(seg.Mode.ModeBits, 4);
                bb.AppendBits(seg.NumChars, seg.Mode.NumCharCountBits(version));
                bb.AppendData(seg.Data);
            }

            var dataCapacityBits = GetNumDataCodewords(version, ecl) * 8;

            bb.AppendBits(0, Math.Min(4, dataCapacityBits - bb.Length));
            bb.AppendBits(0, (8 - bb.Length % 8) % 8);

            for (var padByte = 0xEC; bb.Length < dataCapacityBits; padByte ^= 0xEC ^ 0x11)
            {
                bb.AppendBits(padByte, 8);
            }

            var dataCodewords = new byte[bb.Length / 8];

            for (var i = 0; i < bb.Length; i++)
            {
                dataCodewords[i >> 3] = (byte)(dataCodewords[i >> 3] | bb.GetBit(i) << (7 - (i & 7)));
            }

            // Create the QR Code object
            return(new QrCode(version, ecl, dataCodewords, mask));
        }