zxing_cpp 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +13 -0
- data/.gitmodules +3 -0
- data/CHANGELOG.rdoc +6 -0
- data/Gemfile +3 -0
- data/Manifest.txt +331 -0
- data/README.rdoc +138 -0
- data/Rakefile +28 -0
- data/bin/zxd +87 -0
- data/bin/zxe +53 -0
- data/ext/zxing/extconf.rb +27 -0
- data/ext/zxing/zxing-cpp/.gitignore +4 -0
- data/ext/zxing/zxing-cpp/AUTHORS +115 -0
- data/ext/zxing/zxing-cpp/CMakeLists.txt +84 -0
- data/ext/zxing/zxing-cpp/COPYING +201 -0
- data/ext/zxing/zxing-cpp/NOTICE +65 -0
- data/ext/zxing/zxing-cpp/README.md +50 -0
- data/ext/zxing/zxing-cpp/cli/src/ImageReaderSource.cpp +112 -0
- data/ext/zxing/zxing-cpp/cli/src/ImageReaderSource.h +40 -0
- data/ext/zxing/zxing-cpp/cli/src/jpgd.cpp +3174 -0
- data/ext/zxing/zxing-cpp/cli/src/jpgd.h +319 -0
- data/ext/zxing/zxing-cpp/cli/src/lodepng.cpp +6261 -0
- data/ext/zxing/zxing-cpp/cli/src/lodepng.h +1695 -0
- data/ext/zxing/zxing-cpp/cli/src/main.cpp +297 -0
- data/ext/zxing/zxing-cpp/cmake/FindCPPUNIT.cmake +54 -0
- data/ext/zxing/zxing-cpp/cmake/FindIconv.cmake +57 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/.gitignore +6 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigInteger.cc +405 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigInteger.hh +215 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigIntegerAlgorithms.cc +70 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigIntegerAlgorithms.hh +25 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigIntegerLibrary.hh +8 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigIntegerUtils.cc +50 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigIntegerUtils.hh +72 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigUnsigned.cc +697 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigUnsigned.hh +418 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigUnsignedInABase.cc +125 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/BigUnsignedInABase.hh +122 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/ChangeLog +146 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/Makefile +73 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/NumberlikeArray.hh +177 -0
- data/ext/zxing/zxing-cpp/core/src/bigint/README +71 -0
- data/ext/zxing/zxing-cpp/core/src/win32/zxing/iconv.h +14 -0
- data/ext/zxing/zxing-cpp/core/src/win32/zxing/stdint.h +247 -0
- data/ext/zxing/zxing-cpp/core/src/win32/zxing/win_iconv.c +2035 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/BarcodeFormat.cpp +40 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/BarcodeFormat.h +60 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Binarizer.cpp +45 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Binarizer.h +50 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/BinaryBitmap.cpp +70 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/BinaryBitmap.h +56 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ChecksumException.cpp +28 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ChecksumException.h +34 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/DecodeHints.cpp +142 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/DecodeHints.h +85 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Exception.cpp +43 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Exception.h +51 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/FormatException.cpp +41 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/FormatException.h +37 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/IllegalStateException.h +35 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/InvertedLuminanceSource.cpp +68 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/InvertedLuminanceSource.h +48 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/LuminanceSource.cpp +86 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/LuminanceSource.h +59 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/MultiFormatReader.cpp +124 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/MultiFormatReader.h +48 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/NotFoundException.h +35 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Reader.cpp +31 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Reader.h +40 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ReaderException.h +37 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Result.cpp +61 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/Result.h +55 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ResultIO.cpp +34 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ResultPoint.cpp +108 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ResultPoint.h +55 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ResultPointCallback.cpp +26 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ResultPointCallback.h +39 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/ZXing.h +133 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/AztecDetectorResult.cpp +54 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/AztecDetectorResult.h +48 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/AztecReader.cpp +68 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/AztecReader.h +49 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/decoder/Decoder.cpp +489 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/decoder/Decoder.h +69 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/detector/Detector.cpp +548 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/aztec/detector/Detector.h +92 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/Array.h +170 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/BitArray.cpp +155 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/BitArray.h +81 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/BitArrayIO.cpp +31 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/BitMatrix.cpp +143 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/BitMatrix.h +91 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/BitSource.cpp +76 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/BitSource.h +74 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/CharacterSetECI.cpp +104 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/CharacterSetECI.h +53 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/Counted.h +140 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/DecoderResult.cpp +46 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/DecoderResult.h +51 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/DetectorResult.cpp +39 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/DetectorResult.h +43 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GlobalHistogramBinarizer.cpp +212 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GlobalHistogramBinarizer.h +48 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GreyscaleLuminanceSource.cpp +80 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GreyscaleLuminanceSource.h +53 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GreyscaleRotatedLuminanceSource.cpp +81 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GreyscaleRotatedLuminanceSource.h +46 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GridSampler.cpp +122 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/GridSampler.h +45 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/HybridBinarizer.cpp +226 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/HybridBinarizer.h +67 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/IllegalArgumentException.cpp +27 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/IllegalArgumentException.h +36 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/PerspectiveTransform.cpp +107 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/PerspectiveTransform.h +49 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/Point.h +47 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/Str.cpp +61 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/Str.h +51 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/StringUtils.cpp +198 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/StringUtils.h +52 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/detector/JavaMath.h +43 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/detector/MathUtils.h +57 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/detector/MonochromeRectangleDetector.cpp +174 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/detector/MonochromeRectangleDetector.h +62 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/detector/WhiteRectangleDetector.cpp +330 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/detector/WhiteRectangleDetector.h +59 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/GenericGF.cpp +150 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/GenericGF.h +73 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/GenericGFPoly.cpp +218 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/GenericGFPoly.h +56 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/ReedSolomonDecoder.cpp +174 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/ReedSolomonDecoder.h +49 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/ReedSolomonException.cpp +30 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/common/reedsolomon/ReedSolomonException.h +33 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/DataMatrixReader.cpp +54 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/DataMatrixReader.h +45 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/Version.cpp +199 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/Version.h +87 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/BitMatrixParser.cpp +361 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/BitMatrixParser.h +59 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/DataBlock.cpp +113 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/DataBlock.h +49 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/DecodedBitStreamParser.cpp +416 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/DecodedBitStreamParser.h +104 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/Decoder.cpp +93 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/decoder/Decoder.h +49 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/detector/CornerPoint.cpp +46 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/detector/CornerPoint.h +43 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/detector/Detector.cpp +446 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/detector/Detector.h +94 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/detector/DetectorException.cpp +23 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/datamatrix/detector/DetectorException.h +23 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/ByQuadrantReader.cpp +75 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/ByQuadrantReader.h +42 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/GenericMultipleBarcodeReader.cpp +137 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/GenericMultipleBarcodeReader.h +51 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/MultipleBarcodeReader.cpp +29 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/MultipleBarcodeReader.h +41 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/qrcode/QRCodeMultiReader.cpp +58 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/qrcode/QRCodeMultiReader.h +36 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/qrcode/detector/MultiDetector.cpp +47 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/qrcode/detector/MultiDetector.h +37 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/qrcode/detector/MultiFinderPatternFinder.cpp +236 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/multi/qrcode/detector/MultiFinderPatternFinder.h +47 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/CodaBarReader.cpp +340 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/CodaBarReader.h +57 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/Code128Reader.cpp +496 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/Code128Reader.h +48 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/Code39Reader.cpp +328 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/Code39Reader.h +63 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/Code93Reader.cpp +293 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/Code93Reader.h +58 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/EAN13Reader.cpp +85 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/EAN13Reader.h +49 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/EAN8Reader.cpp +65 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/EAN8Reader.h +47 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/ITFReader.cpp +337 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/ITFReader.h +54 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/MultiFormatOneDReader.cpp +96 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/MultiFormatOneDReader.h +38 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/MultiFormatUPCEANReader.cpp +110 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/MultiFormatUPCEANReader.h +41 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/OneDReader.cpp +227 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/OneDReader.h +81 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/OneDResultPoint.cpp +28 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/OneDResultPoint.h +35 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/UPCAReader.cpp +71 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/UPCAReader.h +50 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/UPCEANReader.cpp +309 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/UPCEANReader.h +88 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/UPCEReader.cpp +146 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/oned/UPCEReader.h +47 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/PDF417Reader.cpp +170 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/PDF417Reader.h +49 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/BitMatrixParser.cpp +997 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/BitMatrixParser.h +84 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/DecodedBitStreamParser.cpp +563 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/DecodedBitStreamParser.h +84 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/Decoder.cpp +118 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/Decoder.h +62 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/ec/ErrorCorrection.cpp +214 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/ec/ErrorCorrection.h +71 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/ec/ModulusGF.cpp +120 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/ec/ModulusGF.h +72 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/ec/ModulusPoly.cpp +284 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/decoder/ec/ModulusPoly.h +68 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/detector/Detector.cpp +664 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/detector/Detector.h +106 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/detector/LinesSampler.cpp +714 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/pdf417/detector/LinesSampler.h +122 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/ErrorCorrectionLevel.cpp +65 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/ErrorCorrectionLevel.h +52 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/FormatInformation.cpp +117 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/FormatInformation.h +54 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/QRCodeReader.cpp +52 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/QRCodeReader.h +48 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/Version.cpp +560 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/Version.h +85 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/BitMatrixParser.cpp +183 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/BitMatrixParser.h +56 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/DataBlock.cpp +118 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/DataBlock.h +50 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/DataMask.cpp +159 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/DataMask.h +50 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/DecodedBitStreamParser.cpp +425 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/DecodedBitStreamParser.h +72 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/Decoder.cpp +107 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/Decoder.h +46 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/Mode.cpp +90 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/decoder/Mode.h +57 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/AlignmentPattern.cpp +47 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/AlignmentPattern.h +45 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/AlignmentPatternFinder.cpp +208 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/AlignmentPatternFinder.h +68 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/Detector.cpp +314 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/Detector.h +69 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/FinderPattern.cpp +69 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/FinderPattern.h +48 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/FinderPatternFinder.cpp +559 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/FinderPatternFinder.h +76 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/FinderPatternInfo.cpp +41 -0
- data/ext/zxing/zxing-cpp/core/src/zxing/qrcode/detector/FinderPatternInfo.h +47 -0
- data/ext/zxing/zxing-cpp/core/tests/src/TestRunner.cpp +30 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/BitArrayTest.cpp +216 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/BitArrayTest.h +61 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/BitMatrixTest.cpp +106 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/BitMatrixTest.h +55 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/BitSourceTest.cpp +49 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/BitSourceTest.h +42 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/CountedTest.cpp +58 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/CountedTest.h +46 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/PerspectiveTransformTest.cpp +69 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/PerspectiveTransformTest.h +47 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/reedsolomon/ReedSolomonTest.cpp +129 -0
- data/ext/zxing/zxing-cpp/core/tests/src/common/reedsolomon/ReedSolomonTest.h +62 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/ErrorCorrectionLevelTest.cpp +47 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/ErrorCorrectionLevelTest.h +45 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/FormatInformationTest.cpp +88 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/FormatInformationTest.h +47 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/VersionTest.cpp +88 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/VersionTest.h +49 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/decoder/DataMaskTest.cpp +132 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/decoder/DataMaskTest.h +91 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/decoder/ModeTest.cpp +52 -0
- data/ext/zxing/zxing-cpp/core/tests/src/qrcode/decoder/ModeTest.h +47 -0
- data/ext/zxing/zxing.cc +224 -0
- data/lib/zxing.rb +50 -0
- data/lib/zxing/.gitignore +2 -0
- data/lib/zxing/aztec.rb +5 -0
- data/lib/zxing/aztec/aztec_reader.rb +14 -0
- data/lib/zxing/bad_image_exception.rb +4 -0
- data/lib/zxing/binarizer.rb +8 -0
- data/lib/zxing/binary_bitmap.rb +15 -0
- data/lib/zxing/checksum_exception.rb +4 -0
- data/lib/zxing/common.rb +7 -0
- data/lib/zxing/common/bit_matrix.rb +9 -0
- data/lib/zxing/common/hybrid_binarizer.rb +17 -0
- data/lib/zxing/common/illegal_argument_exception.rb +4 -0
- data/lib/zxing/datamatrix.rb +5 -0
- data/lib/zxing/datamatrix/data_matrix_reader.rb +14 -0
- data/lib/zxing/decodable.rb +11 -0
- data/lib/zxing/exception.rb +4 -0
- data/lib/zxing/ffi.rb +20 -0
- data/lib/zxing/ffi/aztec.rb +6 -0
- data/lib/zxing/ffi/aztec/aztec_reader.rb +9 -0
- data/lib/zxing/ffi/binarizer.rb +25 -0
- data/lib/zxing/ffi/binary_bitmap.rb +15 -0
- data/lib/zxing/ffi/common.rb +8 -0
- data/lib/zxing/ffi/common/bit_matrix.rb +12 -0
- data/lib/zxing/ffi/common/greyscale_luminance_source.rb +30 -0
- data/lib/zxing/ffi/common/hybrid_binarizer.rb +10 -0
- data/lib/zxing/ffi/datamatrix.rb +6 -0
- data/lib/zxing/ffi/datamatrix/data_matrix_reader.rb +9 -0
- data/lib/zxing/ffi/library.rb +102 -0
- data/lib/zxing/ffi/luminance_source.rb +18 -0
- data/lib/zxing/ffi/multi_format_reader.rb +9 -0
- data/lib/zxing/ffi/oned.rb +6 -0
- data/lib/zxing/ffi/oned/code_39_reader.rb +10 -0
- data/lib/zxing/ffi/qrcode.rb +8 -0
- data/lib/zxing/ffi/qrcode/decoder.rb +10 -0
- data/lib/zxing/ffi/qrcode/detector.rb +10 -0
- data/lib/zxing/ffi/reader.rb +58 -0
- data/lib/zxing/ffi/result.rb +23 -0
- data/lib/zxing/format_exception.rb +4 -0
- data/lib/zxing/illegal_argument_exception.rb +4 -0
- data/lib/zxing/image.rb +15 -0
- data/lib/zxing/luminance_source.rb +18 -0
- data/lib/zxing/multi_format_reader.rb +11 -0
- data/lib/zxing/not_found_exception.rb +4 -0
- data/lib/zxing/oned.rb +5 -0
- data/lib/zxing/oned/code_39_reader.rb +15 -0
- data/lib/zxing/qrcode.rb +8 -0
- data/lib/zxing/qrcode/decoder.rb +14 -0
- data/lib/zxing/qrcode/detector.rb +14 -0
- data/lib/zxing/qrcode/encoder.rb +8 -0
- data/lib/zxing/qrcode/encoder/byte_matrix.rb +18 -0
- data/lib/zxing/qrcode/encoder/encoder.rb +9 -0
- data/lib/zxing/qrcode/encoder/qrcode.rb +18 -0
- data/lib/zxing/reader.rb +8 -0
- data/lib/zxing/reader_exception.rb +4 -0
- data/lib/zxing/reed_solomon_exception.rb +2 -0
- data/lib/zxing/result.rb +18 -0
- data/lib/zxing/rmagick.rb +5 -0
- data/lib/zxing/rmagick/image.rb +104 -0
- data/lib/zxing/version.rb +33 -0
- data/test/qrcode.png +0 -0
- data/test/test_helper.rb +5 -0
- data/test/test_zxing.rb +58 -0
- data/test/vendor.rb +360 -0
- data/test/zxing/test_decodable.rb +38 -0
- data/zxing_cpp.gemspec +48 -0
- metadata +473 -0
|
@@ -0,0 +1,208 @@
|
|
|
1
|
+
// -*- mode:c++; tab-width:2; indent-tabs-mode:nil; c-basic-offset:2 -*-
|
|
2
|
+
/*
|
|
3
|
+
* Copyright 2008 ZXing authors All rights reserved.
|
|
4
|
+
*
|
|
5
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
6
|
+
* you may not use this file except in compliance with the License.
|
|
7
|
+
* You may obtain a copy of the License at
|
|
8
|
+
*
|
|
9
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
+
*
|
|
11
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
12
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
13
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
14
|
+
* See the License for the specific language governing permissions and
|
|
15
|
+
* limitations under the License.
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
#include <zxing/qrcode/detector/AlignmentPatternFinder.h>
|
|
19
|
+
#include <zxing/ReaderException.h>
|
|
20
|
+
#include <zxing/common/BitArray.h>
|
|
21
|
+
#include <vector>
|
|
22
|
+
#include <cmath>
|
|
23
|
+
#include <cstdlib>
|
|
24
|
+
|
|
25
|
+
using std::abs;
|
|
26
|
+
using std::vector;
|
|
27
|
+
using zxing::Ref;
|
|
28
|
+
using zxing::qrcode::AlignmentPatternFinder;
|
|
29
|
+
using zxing::qrcode::AlignmentPattern;
|
|
30
|
+
|
|
31
|
+
// VC++
|
|
32
|
+
|
|
33
|
+
using zxing::BitMatrix;
|
|
34
|
+
using zxing::ResultPointCallback;
|
|
35
|
+
|
|
36
|
+
float AlignmentPatternFinder::centerFromEnd(vector<int>& stateCount, int end) {
|
|
37
|
+
return (float)(end - stateCount[2]) - stateCount[1] / 2.0f;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
bool AlignmentPatternFinder::foundPatternCross(vector<int> &stateCount) {
|
|
41
|
+
float maxVariance = moduleSize_ / 2.0f;
|
|
42
|
+
for (int i = 0; i < 3; i++) {
|
|
43
|
+
if (abs(moduleSize_ - stateCount[i]) >= maxVariance) {
|
|
44
|
+
return false;
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
return true;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
float AlignmentPatternFinder::crossCheckVertical(int startI, int centerJ, int maxCount,
|
|
51
|
+
int originalStateCountTotal) {
|
|
52
|
+
int maxI = image_->getHeight();
|
|
53
|
+
vector<int> stateCount(3, 0);
|
|
54
|
+
|
|
55
|
+
|
|
56
|
+
// Start counting up from center
|
|
57
|
+
int i = startI;
|
|
58
|
+
while (i >= 0 && image_->get(centerJ, i) && stateCount[1] <= maxCount) {
|
|
59
|
+
stateCount[1]++;
|
|
60
|
+
i--;
|
|
61
|
+
}
|
|
62
|
+
// If already too many modules in this state or ran off the edge:
|
|
63
|
+
if (i < 0 || stateCount[1] > maxCount) {
|
|
64
|
+
return nan();
|
|
65
|
+
}
|
|
66
|
+
while (i >= 0 && !image_->get(centerJ, i) && stateCount[0] <= maxCount) {
|
|
67
|
+
stateCount[0]++;
|
|
68
|
+
i--;
|
|
69
|
+
}
|
|
70
|
+
if (stateCount[0] > maxCount) {
|
|
71
|
+
return nan();
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
// Now also count down from center
|
|
75
|
+
i = startI + 1;
|
|
76
|
+
while (i < maxI && image_->get(centerJ, i) && stateCount[1] <= maxCount) {
|
|
77
|
+
stateCount[1]++;
|
|
78
|
+
i++;
|
|
79
|
+
}
|
|
80
|
+
if (i == maxI || stateCount[1] > maxCount) {
|
|
81
|
+
return nan();
|
|
82
|
+
}
|
|
83
|
+
while (i < maxI && !image_->get(centerJ, i) && stateCount[2] <= maxCount) {
|
|
84
|
+
stateCount[2]++;
|
|
85
|
+
i++;
|
|
86
|
+
}
|
|
87
|
+
if (stateCount[2] > maxCount) {
|
|
88
|
+
return nan();
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
int stateCountTotal = stateCount[0] + stateCount[1] + stateCount[2];
|
|
92
|
+
if (5 * abs(stateCountTotal - originalStateCountTotal) >= 2 * originalStateCountTotal) {
|
|
93
|
+
return nan();
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
return foundPatternCross(stateCount) ? centerFromEnd(stateCount, i) : nan();
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
Ref<AlignmentPattern> AlignmentPatternFinder::handlePossibleCenter(vector<int> &stateCount, int i, int j) {
|
|
100
|
+
int stateCountTotal = stateCount[0] + stateCount[1] + stateCount[2];
|
|
101
|
+
float centerJ = centerFromEnd(stateCount, j);
|
|
102
|
+
float centerI = crossCheckVertical(i, (int)centerJ, 2 * stateCount[1], stateCountTotal);
|
|
103
|
+
if (!isnan(centerI)) {
|
|
104
|
+
float estimatedModuleSize = (float)(stateCount[0] + stateCount[1] + stateCount[2]) / 3.0f;
|
|
105
|
+
int max = possibleCenters_->size();
|
|
106
|
+
for (int index = 0; index < max; index++) {
|
|
107
|
+
Ref<AlignmentPattern> center((*possibleCenters_)[index]);
|
|
108
|
+
// Look for about the same center and module size:
|
|
109
|
+
if (center->aboutEquals(estimatedModuleSize, centerI, centerJ)) {
|
|
110
|
+
return center->combineEstimate(centerI, centerJ, estimatedModuleSize);
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
AlignmentPattern *tmp = new AlignmentPattern(centerJ, centerI, estimatedModuleSize);
|
|
114
|
+
// Hadn't found this before; save it
|
|
115
|
+
tmp->retain();
|
|
116
|
+
possibleCenters_->push_back(tmp);
|
|
117
|
+
if (callback_ != 0) {
|
|
118
|
+
callback_->foundPossibleResultPoint(*tmp);
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
Ref<AlignmentPattern> result;
|
|
122
|
+
return result;
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
AlignmentPatternFinder::AlignmentPatternFinder(Ref<BitMatrix> image, int startX, int startY, int width,
|
|
126
|
+
int height, float moduleSize,
|
|
127
|
+
Ref<ResultPointCallback>const& callback) :
|
|
128
|
+
image_(image), possibleCenters_(new vector<AlignmentPattern *> ()), startX_(startX), startY_(startY),
|
|
129
|
+
width_(width), height_(height), moduleSize_(moduleSize), callback_(callback) {
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
AlignmentPatternFinder::~AlignmentPatternFinder() {
|
|
133
|
+
for (int i = 0; i < int(possibleCenters_->size()); i++) {
|
|
134
|
+
(*possibleCenters_)[i]->release();
|
|
135
|
+
(*possibleCenters_)[i] = 0;
|
|
136
|
+
}
|
|
137
|
+
delete possibleCenters_;
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
Ref<AlignmentPattern> AlignmentPatternFinder::find() {
|
|
141
|
+
int maxJ = startX_ + width_;
|
|
142
|
+
int middleI = startY_ + (height_ >> 1);
|
|
143
|
+
// Ref<BitArray> luminanceRow(new BitArray(width_));
|
|
144
|
+
// We are looking for black/white/black modules in 1:1:1 ratio;
|
|
145
|
+
// this tracks the number of black/white/black modules seen so far
|
|
146
|
+
vector<int> stateCount(3, 0);
|
|
147
|
+
for (int iGen = 0; iGen < height_; iGen++) {
|
|
148
|
+
// Search from middle outwards
|
|
149
|
+
int i = middleI + ((iGen & 0x01) == 0 ? ((iGen + 1) >> 1) : -((iGen + 1) >> 1));
|
|
150
|
+
// image_->getBlackRow(i, luminanceRow, startX_, width_);
|
|
151
|
+
stateCount[0] = 0;
|
|
152
|
+
stateCount[1] = 0;
|
|
153
|
+
stateCount[2] = 0;
|
|
154
|
+
int j = startX_;
|
|
155
|
+
// Burn off leading white pixels before anything else; if we start in the middle of
|
|
156
|
+
// a white run, it doesn't make sense to count its length, since we don't know if the
|
|
157
|
+
// white run continued to the left of the start point
|
|
158
|
+
while (j < maxJ && !image_->get(j, i)) {
|
|
159
|
+
j++;
|
|
160
|
+
}
|
|
161
|
+
int currentState = 0;
|
|
162
|
+
while (j < maxJ) {
|
|
163
|
+
if (image_->get(j, i)) {
|
|
164
|
+
// Black pixel
|
|
165
|
+
if (currentState == 1) { // Counting black pixels
|
|
166
|
+
stateCount[currentState]++;
|
|
167
|
+
} else { // Counting white pixels
|
|
168
|
+
if (currentState == 2) { // A winner?
|
|
169
|
+
if (foundPatternCross(stateCount)) { // Yes
|
|
170
|
+
Ref<AlignmentPattern> confirmed(handlePossibleCenter(stateCount, i, j));
|
|
171
|
+
if (confirmed != 0) {
|
|
172
|
+
return confirmed;
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
stateCount[0] = stateCount[2];
|
|
176
|
+
stateCount[1] = 1;
|
|
177
|
+
stateCount[2] = 0;
|
|
178
|
+
currentState = 1;
|
|
179
|
+
} else {
|
|
180
|
+
stateCount[++currentState]++;
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
} else { // White pixel
|
|
184
|
+
if (currentState == 1) { // Counting black pixels
|
|
185
|
+
currentState++;
|
|
186
|
+
}
|
|
187
|
+
stateCount[currentState]++;
|
|
188
|
+
}
|
|
189
|
+
j++;
|
|
190
|
+
}
|
|
191
|
+
if (foundPatternCross(stateCount)) {
|
|
192
|
+
Ref<AlignmentPattern> confirmed(handlePossibleCenter(stateCount, i, maxJ));
|
|
193
|
+
if (confirmed != 0) {
|
|
194
|
+
return confirmed;
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
// Hmm, nothing we saw was observed and confirmed twice. If we had
|
|
201
|
+
// any guess at all, return it.
|
|
202
|
+
if (possibleCenters_->size() > 0) {
|
|
203
|
+
Ref<AlignmentPattern> center((*possibleCenters_)[0]);
|
|
204
|
+
return center;
|
|
205
|
+
}
|
|
206
|
+
|
|
207
|
+
throw zxing::ReaderException("Could not find alignment pattern");
|
|
208
|
+
}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
#ifndef __ALIGNMENT_PATTERN_FINDER_H__
|
|
2
|
+
#define __ALIGNMENT_PATTERN_FINDER_H__
|
|
3
|
+
|
|
4
|
+
/*
|
|
5
|
+
* AlignmentPatternFinder.h
|
|
6
|
+
* zxing
|
|
7
|
+
*
|
|
8
|
+
* Copyright 2010 ZXing authors All rights reserved.
|
|
9
|
+
*
|
|
10
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
11
|
+
* you may not use this file except in compliance with the License.
|
|
12
|
+
* You may obtain a copy of the License at
|
|
13
|
+
*
|
|
14
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
15
|
+
*
|
|
16
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
17
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
18
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
19
|
+
* See the License for the specific language governing permissions and
|
|
20
|
+
* limitations under the License.
|
|
21
|
+
*/
|
|
22
|
+
|
|
23
|
+
#include "AlignmentPattern.h"
|
|
24
|
+
#include <zxing/common/Counted.h>
|
|
25
|
+
#include <zxing/common/BitMatrix.h>
|
|
26
|
+
#include <zxing/ResultPointCallback.h>
|
|
27
|
+
#include <vector>
|
|
28
|
+
|
|
29
|
+
namespace zxing {
|
|
30
|
+
namespace qrcode {
|
|
31
|
+
|
|
32
|
+
class AlignmentPatternFinder : public Counted {
|
|
33
|
+
private:
|
|
34
|
+
static int CENTER_QUORUM;
|
|
35
|
+
static int MIN_SKIP;
|
|
36
|
+
static int MAX_MODULES;
|
|
37
|
+
|
|
38
|
+
Ref<BitMatrix> image_;
|
|
39
|
+
std::vector<AlignmentPattern *> *possibleCenters_;
|
|
40
|
+
int startX_;
|
|
41
|
+
int startY_;
|
|
42
|
+
int width_;
|
|
43
|
+
int height_;
|
|
44
|
+
float moduleSize_;
|
|
45
|
+
|
|
46
|
+
static float centerFromEnd(std::vector<int> &stateCount, int end);
|
|
47
|
+
bool foundPatternCross(std::vector<int> &stateCount);
|
|
48
|
+
|
|
49
|
+
float crossCheckVertical(int startI, int centerJ, int maxCount, int originalStateCountTotal);
|
|
50
|
+
|
|
51
|
+
Ref<AlignmentPattern> handlePossibleCenter(std::vector<int> &stateCount, int i, int j);
|
|
52
|
+
|
|
53
|
+
public:
|
|
54
|
+
AlignmentPatternFinder(Ref<BitMatrix> image, int startX, int startY, int width, int height,
|
|
55
|
+
float moduleSize, Ref<ResultPointCallback>const& callback);
|
|
56
|
+
~AlignmentPatternFinder();
|
|
57
|
+
Ref<AlignmentPattern> find();
|
|
58
|
+
|
|
59
|
+
private:
|
|
60
|
+
AlignmentPatternFinder(const AlignmentPatternFinder&);
|
|
61
|
+
AlignmentPatternFinder& operator =(const AlignmentPatternFinder&);
|
|
62
|
+
|
|
63
|
+
Ref<ResultPointCallback> callback_;
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
#endif // __ALIGNMENT_PATTERN_FINDER_H__
|
|
@@ -0,0 +1,314 @@
|
|
|
1
|
+
// -*- mode:c++; tab-width:2; indent-tabs-mode:nil; c-basic-offset:2 -*-
|
|
2
|
+
/*
|
|
3
|
+
* Detector.cpp
|
|
4
|
+
* zxing
|
|
5
|
+
*
|
|
6
|
+
* Created by Christian Brunschen on 14/05/2008.
|
|
7
|
+
* Copyright 2008 ZXing authors All rights reserved.
|
|
8
|
+
*
|
|
9
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
10
|
+
* you may not use this file except in compliance with the License.
|
|
11
|
+
* You may obtain a copy of the License at
|
|
12
|
+
*
|
|
13
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
14
|
+
*
|
|
15
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
16
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
17
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
18
|
+
* See the License for the specific language governing permissions and
|
|
19
|
+
* limitations under the License.
|
|
20
|
+
*/
|
|
21
|
+
|
|
22
|
+
#include <zxing/qrcode/detector/Detector.h>
|
|
23
|
+
#include <zxing/qrcode/detector/FinderPatternFinder.h>
|
|
24
|
+
#include <zxing/qrcode/detector/FinderPattern.h>
|
|
25
|
+
#include <zxing/qrcode/detector/AlignmentPattern.h>
|
|
26
|
+
#include <zxing/qrcode/detector/AlignmentPatternFinder.h>
|
|
27
|
+
#include <zxing/qrcode/Version.h>
|
|
28
|
+
#include <zxing/common/GridSampler.h>
|
|
29
|
+
#include <zxing/DecodeHints.h>
|
|
30
|
+
#include <zxing/common/detector/MathUtils.h>
|
|
31
|
+
#include <sstream>
|
|
32
|
+
#include <cstdlib>
|
|
33
|
+
|
|
34
|
+
using std::ostringstream;
|
|
35
|
+
using std::abs;
|
|
36
|
+
using std::min;
|
|
37
|
+
using std::max;
|
|
38
|
+
using zxing::qrcode::Detector;
|
|
39
|
+
using zxing::Ref;
|
|
40
|
+
using zxing::BitMatrix;
|
|
41
|
+
using zxing::ResultPointCallback;
|
|
42
|
+
using zxing::DetectorResult;
|
|
43
|
+
using zxing::PerspectiveTransform;
|
|
44
|
+
using zxing::qrcode::AlignmentPattern;
|
|
45
|
+
using zxing::common::detector::MathUtils;
|
|
46
|
+
|
|
47
|
+
// VC++
|
|
48
|
+
using zxing::DecodeHints;
|
|
49
|
+
using zxing::qrcode::FinderPatternFinder;
|
|
50
|
+
using zxing::qrcode::FinderPatternInfo;
|
|
51
|
+
using zxing::ResultPoint;
|
|
52
|
+
|
|
53
|
+
Detector::Detector(Ref<BitMatrix> image) :
|
|
54
|
+
image_(image) {
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
Ref<BitMatrix> Detector::getImage() const {
|
|
58
|
+
return image_;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
Ref<ResultPointCallback> Detector::getResultPointCallback() const {
|
|
62
|
+
return callback_;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
Ref<DetectorResult> Detector::detect(DecodeHints const& hints) {
|
|
66
|
+
callback_ = hints.getResultPointCallback();
|
|
67
|
+
FinderPatternFinder finder(image_, hints.getResultPointCallback());
|
|
68
|
+
Ref<FinderPatternInfo> info(finder.find(hints));
|
|
69
|
+
return processFinderPatternInfo(info);
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
Ref<DetectorResult> Detector::processFinderPatternInfo(Ref<FinderPatternInfo> info){
|
|
73
|
+
Ref<FinderPattern> topLeft(info->getTopLeft());
|
|
74
|
+
Ref<FinderPattern> topRight(info->getTopRight());
|
|
75
|
+
Ref<FinderPattern> bottomLeft(info->getBottomLeft());
|
|
76
|
+
|
|
77
|
+
float moduleSize = calculateModuleSize(topLeft, topRight, bottomLeft);
|
|
78
|
+
if (moduleSize < 1.0f) {
|
|
79
|
+
throw zxing::ReaderException("bad module size");
|
|
80
|
+
}
|
|
81
|
+
int dimension = computeDimension(topLeft, topRight, bottomLeft, moduleSize);
|
|
82
|
+
Version *provisionalVersion = Version::getProvisionalVersionForDimension(dimension);
|
|
83
|
+
int modulesBetweenFPCenters = provisionalVersion->getDimensionForVersion() - 7;
|
|
84
|
+
|
|
85
|
+
Ref<AlignmentPattern> alignmentPattern;
|
|
86
|
+
// Anything above version 1 has an alignment pattern
|
|
87
|
+
if (provisionalVersion->getAlignmentPatternCenters().size() > 0) {
|
|
88
|
+
|
|
89
|
+
|
|
90
|
+
// Guess where a "bottom right" finder pattern would have been
|
|
91
|
+
float bottomRightX = topRight->getX() - topLeft->getX() + bottomLeft->getX();
|
|
92
|
+
float bottomRightY = topRight->getY() - topLeft->getY() + bottomLeft->getY();
|
|
93
|
+
|
|
94
|
+
|
|
95
|
+
// Estimate that alignment pattern is closer by 3 modules
|
|
96
|
+
// from "bottom right" to known top left location
|
|
97
|
+
float correctionToTopLeft = 1.0f - 3.0f / (float)modulesBetweenFPCenters;
|
|
98
|
+
int estAlignmentX = (int)(topLeft->getX() + correctionToTopLeft * (bottomRightX - topLeft->getX()));
|
|
99
|
+
int estAlignmentY = (int)(topLeft->getY() + correctionToTopLeft * (bottomRightY - topLeft->getY()));
|
|
100
|
+
|
|
101
|
+
|
|
102
|
+
// Kind of arbitrary -- expand search radius before giving up
|
|
103
|
+
for (int i = 4; i <= 16; i <<= 1) {
|
|
104
|
+
try {
|
|
105
|
+
alignmentPattern = findAlignmentInRegion(moduleSize, estAlignmentX, estAlignmentY, (float)i);
|
|
106
|
+
break;
|
|
107
|
+
} catch (zxing::ReaderException const& re) {
|
|
108
|
+
(void)re;
|
|
109
|
+
// try next round
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
if (alignmentPattern == 0) {
|
|
113
|
+
// Try anyway
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
Ref<PerspectiveTransform> transform = createTransform(topLeft, topRight, bottomLeft, alignmentPattern, dimension);
|
|
119
|
+
Ref<BitMatrix> bits(sampleGrid(image_, dimension, transform));
|
|
120
|
+
ArrayRef< Ref<ResultPoint> > points(new Array< Ref<ResultPoint> >(alignmentPattern == 0 ? 3 : 4));
|
|
121
|
+
points[0].reset(bottomLeft);
|
|
122
|
+
points[1].reset(topLeft);
|
|
123
|
+
points[2].reset(topRight);
|
|
124
|
+
if (alignmentPattern != 0) {
|
|
125
|
+
points[3].reset(alignmentPattern);
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
Ref<DetectorResult> result(new DetectorResult(bits, points));
|
|
129
|
+
return result;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
Ref<PerspectiveTransform> Detector::createTransform(Ref<ResultPoint> topLeft, Ref<ResultPoint> topRight, Ref <
|
|
133
|
+
ResultPoint > bottomLeft, Ref<ResultPoint> alignmentPattern, int dimension) {
|
|
134
|
+
|
|
135
|
+
float dimMinusThree = (float)dimension - 3.5f;
|
|
136
|
+
float bottomRightX;
|
|
137
|
+
float bottomRightY;
|
|
138
|
+
float sourceBottomRightX;
|
|
139
|
+
float sourceBottomRightY;
|
|
140
|
+
if (alignmentPattern != 0) {
|
|
141
|
+
bottomRightX = alignmentPattern->getX();
|
|
142
|
+
bottomRightY = alignmentPattern->getY();
|
|
143
|
+
sourceBottomRightX = dimMinusThree - 3.0f;
|
|
144
|
+
sourceBottomRightY = sourceBottomRightX;
|
|
145
|
+
} else {
|
|
146
|
+
// Don't have an alignment pattern, just make up the bottom-right point
|
|
147
|
+
bottomRightX = (topRight->getX() - topLeft->getX()) + bottomLeft->getX();
|
|
148
|
+
bottomRightY = (topRight->getY() - topLeft->getY()) + bottomLeft->getY();
|
|
149
|
+
sourceBottomRightX = dimMinusThree;
|
|
150
|
+
sourceBottomRightY = dimMinusThree;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
Ref<PerspectiveTransform> transform(PerspectiveTransform::quadrilateralToQuadrilateral(3.5f, 3.5f, dimMinusThree, 3.5f, sourceBottomRightX,
|
|
154
|
+
sourceBottomRightY, 3.5f, dimMinusThree, topLeft->getX(), topLeft->getY(), topRight->getX(),
|
|
155
|
+
topRight->getY(), bottomRightX, bottomRightY, bottomLeft->getX(), bottomLeft->getY()));
|
|
156
|
+
|
|
157
|
+
return transform;
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
Ref<BitMatrix> Detector::sampleGrid(Ref<BitMatrix> image, int dimension, Ref<PerspectiveTransform> transform) {
|
|
161
|
+
GridSampler &sampler = GridSampler::getInstance();
|
|
162
|
+
return sampler.sampleGrid(image, dimension, transform);
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
int Detector::computeDimension(Ref<ResultPoint> topLeft, Ref<ResultPoint> topRight, Ref<ResultPoint> bottomLeft,
|
|
166
|
+
float moduleSize) {
|
|
167
|
+
int tltrCentersDimension =
|
|
168
|
+
MathUtils::round(ResultPoint::distance(topLeft, topRight) / moduleSize);
|
|
169
|
+
int tlblCentersDimension =
|
|
170
|
+
MathUtils::round(ResultPoint::distance(topLeft, bottomLeft) / moduleSize);
|
|
171
|
+
int dimension = ((tltrCentersDimension + tlblCentersDimension) >> 1) + 7;
|
|
172
|
+
switch (dimension & 0x03) { // mod 4
|
|
173
|
+
case 0:
|
|
174
|
+
dimension++;
|
|
175
|
+
break;
|
|
176
|
+
// 1? do nothing
|
|
177
|
+
case 2:
|
|
178
|
+
dimension--;
|
|
179
|
+
break;
|
|
180
|
+
case 3:
|
|
181
|
+
ostringstream s;
|
|
182
|
+
s << "Bad dimension: " << dimension;
|
|
183
|
+
throw zxing::ReaderException(s.str().c_str());
|
|
184
|
+
}
|
|
185
|
+
return dimension;
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
float Detector::calculateModuleSize(Ref<ResultPoint> topLeft, Ref<ResultPoint> topRight, Ref<ResultPoint> bottomLeft) {
|
|
189
|
+
// Take the average
|
|
190
|
+
return (calculateModuleSizeOneWay(topLeft, topRight) + calculateModuleSizeOneWay(topLeft, bottomLeft)) / 2.0f;
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
float Detector::calculateModuleSizeOneWay(Ref<ResultPoint> pattern, Ref<ResultPoint> otherPattern) {
|
|
194
|
+
float moduleSizeEst1 = sizeOfBlackWhiteBlackRunBothWays((int)pattern->getX(), (int)pattern->getY(),
|
|
195
|
+
(int)otherPattern->getX(), (int)otherPattern->getY());
|
|
196
|
+
float moduleSizeEst2 = sizeOfBlackWhiteBlackRunBothWays((int)otherPattern->getX(), (int)otherPattern->getY(),
|
|
197
|
+
(int)pattern->getX(), (int)pattern->getY());
|
|
198
|
+
if (zxing::isnan(moduleSizeEst1)) {
|
|
199
|
+
return moduleSizeEst2;
|
|
200
|
+
}
|
|
201
|
+
if (zxing::isnan(moduleSizeEst2)) {
|
|
202
|
+
return moduleSizeEst1;
|
|
203
|
+
}
|
|
204
|
+
// Average them, and divide by 7 since we've counted the width of 3 black modules,
|
|
205
|
+
// and 1 white and 1 black module on either side. Ergo, divide sum by 14.
|
|
206
|
+
return (moduleSizeEst1 + moduleSizeEst2) / 14.0f;
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
float Detector::sizeOfBlackWhiteBlackRunBothWays(int fromX, int fromY, int toX, int toY) {
|
|
210
|
+
|
|
211
|
+
float result = sizeOfBlackWhiteBlackRun(fromX, fromY, toX, toY);
|
|
212
|
+
|
|
213
|
+
// Now count other way -- don't run off image though of course
|
|
214
|
+
float scale = 1.0f;
|
|
215
|
+
int otherToX = fromX - (toX - fromX);
|
|
216
|
+
if (otherToX < 0) {
|
|
217
|
+
scale = (float) fromX / (float) (fromX - otherToX);
|
|
218
|
+
otherToX = 0;
|
|
219
|
+
} else if (otherToX >= (int)image_->getWidth()) {
|
|
220
|
+
scale = (float) (image_->getWidth() - 1 - fromX) / (float) (otherToX - fromX);
|
|
221
|
+
otherToX = image_->getWidth() - 1;
|
|
222
|
+
}
|
|
223
|
+
int otherToY = (int) (fromY - (toY - fromY) * scale);
|
|
224
|
+
|
|
225
|
+
scale = 1.0f;
|
|
226
|
+
if (otherToY < 0) {
|
|
227
|
+
scale = (float) fromY / (float) (fromY - otherToY);
|
|
228
|
+
otherToY = 0;
|
|
229
|
+
} else if (otherToY >= (int)image_->getHeight()) {
|
|
230
|
+
scale = (float) (image_->getHeight() - 1 - fromY) / (float) (otherToY - fromY);
|
|
231
|
+
otherToY = image_->getHeight() - 1;
|
|
232
|
+
}
|
|
233
|
+
otherToX = (int) (fromX + (otherToX - fromX) * scale);
|
|
234
|
+
|
|
235
|
+
result += sizeOfBlackWhiteBlackRun(fromX, fromY, otherToX, otherToY);
|
|
236
|
+
|
|
237
|
+
// Middle pixel is double-counted this way; subtract 1
|
|
238
|
+
return result - 1.0f;
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
float Detector::sizeOfBlackWhiteBlackRun(int fromX, int fromY, int toX, int toY) {
|
|
242
|
+
// Mild variant of Bresenham's algorithm;
|
|
243
|
+
// see http://en.wikipedia.org/wiki/Bresenham's_line_algorithm
|
|
244
|
+
bool steep = abs(toY - fromY) > abs(toX - fromX);
|
|
245
|
+
if (steep) {
|
|
246
|
+
int temp = fromX;
|
|
247
|
+
fromX = fromY;
|
|
248
|
+
fromY = temp;
|
|
249
|
+
temp = toX;
|
|
250
|
+
toX = toY;
|
|
251
|
+
toY = temp;
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
int dx = abs(toX - fromX);
|
|
255
|
+
int dy = abs(toY - fromY);
|
|
256
|
+
int error = -dx >> 1;
|
|
257
|
+
int xstep = fromX < toX ? 1 : -1;
|
|
258
|
+
int ystep = fromY < toY ? 1 : -1;
|
|
259
|
+
|
|
260
|
+
// In black pixels, looking for white, first or second time.
|
|
261
|
+
int state = 0;
|
|
262
|
+
// Loop up until x == toX, but not beyond
|
|
263
|
+
int xLimit = toX + xstep;
|
|
264
|
+
for (int x = fromX, y = fromY; x != xLimit; x += xstep) {
|
|
265
|
+
int realX = steep ? y : x;
|
|
266
|
+
int realY = steep ? x : y;
|
|
267
|
+
|
|
268
|
+
// Does current pixel mean we have moved white to black or vice versa?
|
|
269
|
+
if (!((state == 1) ^ image_->get(realX, realY))) {
|
|
270
|
+
if (state == 2) {
|
|
271
|
+
return MathUtils::distance(x, y, fromX, fromY);
|
|
272
|
+
}
|
|
273
|
+
state++;
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
error += dy;
|
|
277
|
+
if (error > 0) {
|
|
278
|
+
if (y == toY) {
|
|
279
|
+
break;
|
|
280
|
+
}
|
|
281
|
+
y += ystep;
|
|
282
|
+
error -= dx;
|
|
283
|
+
}
|
|
284
|
+
}
|
|
285
|
+
// Found black-white-black; give the benefit of the doubt that the next pixel outside the image
|
|
286
|
+
// is "white" so this last point at (toX+xStep,toY) is the right ending. This is really a
|
|
287
|
+
// small approximation; (toX+xStep,toY+yStep) might be really correct. Ignore this.
|
|
288
|
+
if (state == 2) {
|
|
289
|
+
return MathUtils::distance(toX + xstep, toY, fromX, fromY);
|
|
290
|
+
}
|
|
291
|
+
// else we didn't find even black-white-black; no estimate is really possible
|
|
292
|
+
return nan();
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
Ref<AlignmentPattern> Detector::findAlignmentInRegion(float overallEstModuleSize, int estAlignmentX, int estAlignmentY,
|
|
296
|
+
float allowanceFactor) {
|
|
297
|
+
// Look for an alignment pattern (3 modules in size) around where it
|
|
298
|
+
// should be
|
|
299
|
+
int allowance = (int)(allowanceFactor * overallEstModuleSize);
|
|
300
|
+
int alignmentAreaLeftX = max(0, estAlignmentX - allowance);
|
|
301
|
+
int alignmentAreaRightX = min((int)(image_->getWidth() - 1), estAlignmentX + allowance);
|
|
302
|
+
if (alignmentAreaRightX - alignmentAreaLeftX < overallEstModuleSize * 3) {
|
|
303
|
+
throw zxing::ReaderException("region too small to hold alignment pattern");
|
|
304
|
+
}
|
|
305
|
+
int alignmentAreaTopY = max(0, estAlignmentY - allowance);
|
|
306
|
+
int alignmentAreaBottomY = min((int)(image_->getHeight() - 1), estAlignmentY + allowance);
|
|
307
|
+
if (alignmentAreaBottomY - alignmentAreaTopY < overallEstModuleSize * 3) {
|
|
308
|
+
throw zxing::ReaderException("region too small to hold alignment pattern");
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
AlignmentPatternFinder alignmentFinder(image_, alignmentAreaLeftX, alignmentAreaTopY, alignmentAreaRightX
|
|
312
|
+
- alignmentAreaLeftX, alignmentAreaBottomY - alignmentAreaTopY, overallEstModuleSize, callback_);
|
|
313
|
+
return alignmentFinder.find();
|
|
314
|
+
}
|