or run

tessl search
Log in

Version

Workspace
tessl
Visibility
Public
Created
Last updated

docs

index.md
tile.json

tessl/github-zxing-cpp--zxing-cpp

tessl install tessl/github-zxing-cpp--zxing-cpp@2.3.0

Open-source, multi-format linear/matrix barcode image processing library implemented in C++

results.mddocs/reference/

Barcode Results

The Barcode class (alias for Result) encapsulates all information about a decoded barcode, including its content, format, position, error correction level, and metadata.

Barcode Class

class Barcode {
public:
    // Construction (typically created by ReadBarcode/ReadBarcodes)
    Barcode();  // Default invalid barcode

    // Validity and Error Checking
    bool isValid() const;
    const Error& error() const;

    // Format Information
    BarcodeFormat format() const;

    // Content Access
    const ByteArray& bytes() const;          // Raw bytes
    ByteArray bytesECI() const;               // Bytes with ECI protocol
    std::string text(TextMode mode) const;   // Text with specific mode
    std::string text() const;                 // Text with default mode
    std::string ecLevel() const;              // Error correction level
    ContentType contentType() const;          // Content type hint
    bool hasECI() const;                      // Has ECI encoding

    // Position and Orientation
    const Position& position() const;         // Corner positions (Quadrilateral)
    void setPosition(Position pos);
    int orientation() const;                  // Orientation in degrees
    bool isMirrored() const;                  // Is mirrored (QR/DataMatrix)
    bool isInverted() const;                  // Has reversed reflectance

    // Symbology and Metadata
    std::string symbologyIdentifier() const;  // Symbology identifier ("]cm")

    // Structured Append (Multi-Symbol)
    int sequenceSize() const;                 // Total symbols in sequence (-1 if not part)
    int sequenceIndex() const;                // 0-based index in sequence
    std::string sequenceId() const;           // Sequence identifier
    bool isLastInSequence() const;
    bool isPartOfSequence() const;

    // Additional Metadata
    bool readerInit() const;                  // Reader initialization flag
    int lineCount() const;                    // Scan lines detected (linear codes)
    std::string version() const;              // Version/size (QR/DataMatrix/Aztec)

    // Comparison
    bool operator==(const Barcode& other) const;

    // Experimental API (requires ZXING_EXPERIMENTAL_API)
    #ifdef ZXING_EXPERIMENTAL_API
    void symbol(BitMatrix&& bits);
    ImageView symbol() const;
    void zint(unique_zint_symbol&& z);
    zint_symbol* zint() const;
    #endif
};

// Type aliases
using Barcode = Result;
using Barcodes = std::vector<Barcode>;
using Results = std::vector<Result>;
using Position = QuadrilateralI;

Checking Validity

Always check if a barcode is valid before accessing its content:

auto barcode = ZXing::ReadBarcode(image);

if (barcode.isValid()) {
    // Barcode was successfully decoded
    std::cout << "Content: " << barcode.text() << "\n";
} else {
    // No barcode found or decoding failed
    std::cerr << "Error: " << barcode.error().msg() << "\n";
}

Accessing Content

Text Content

// Get text with default text mode (from ReaderOptions)
std::string text = barcode.text();

// Get text with specific text mode
std::string plainText = barcode.text(ZXing::TextMode::Plain);
std::string eciText = barcode.text(ZXing::TextMode::ECI);
std::string hexText = barcode.text(ZXing::TextMode::Hex);
std::string escapedText = barcode.text(ZXing::TextMode::Escaped);

Text modes:

  • Plain: Decoded text using ECI or guessed charset
  • ECI: Standard ECI protocol with all segments
  • HRI: Human Readable Interpretation
  • Hex: Raw bytes as hex string
  • Escaped: Non-graphical characters escaped (e.g., <GS>)

Binary Content

// Get raw bytes
const ZXing::ByteArray& bytes = barcode.bytes();

// Iterate bytes
for (uint8_t byte : bytes) {
    std::cout << std::hex << (int)byte << " ";
}

// Get bytes with ECI encoding
ZXing::ByteArray eciBytes = barcode.bytesECI();

Content Type

ZXing::ContentType type = barcode.contentType();

switch (type) {
    case ZXing::ContentType::Text:
        std::cout << "Text content\n";
        break;
    case ZXing::ContentType::Binary:
        std::cout << "Binary content\n";
        break;
    case ZXing::ContentType::GS1:
        std::cout << "GS1 formatted\n";
        break;
    case ZXing::ContentType::ISO15434:
        std::cout << "ISO 15434 formatted\n";
        break;
    case ZXing::ContentType::Mixed:
        std::cout << "Mixed text/binary\n";
        break;
    case ZXing::ContentType::UnknownECI:
        std::cout << "Unknown ECI\n";
        break;
}

Format Information

// Get format
ZXing::BarcodeFormat format = barcode.format();

// Convert to string
std::string formatName = ZXing::ToString(format);
std::cout << "Format: " << formatName << "\n";

// Check specific format
if (format == ZXing::BarcodeFormat::QRCode) {
    std::cout << "This is a QR code\n";
}

Position and Geometry

Corner Positions

// Get position (quadrilateral with 4 corners)
const ZXing::Position& pos = barcode.position();

// Access corners
ZXing::PointI topLeft = pos.topLeft();
ZXing::PointI topRight = pos.topRight();
ZXing::PointI bottomRight = pos.bottomRight();
ZXing::PointI bottomLeft = pos.bottomLeft();

std::cout << "Corners: "
          << "TL(" << topLeft.x << "," << topLeft.y << ") "
          << "TR(" << topRight.x << "," << topRight.y << ") "
          << "BR(" << bottomRight.x << "," << bottomRight.y << ") "
          << "BL(" << bottomLeft.x << "," << bottomLeft.y << ")\n";

// Get orientation
double orient = pos.orientation();  // Radians

Orientation

// Get orientation in degrees
int degrees = barcode.orientation();

std::cout << "Barcode is rotated " << degrees << " degrees\n";

Mirroring and Inversion

// Check if mirrored (horizontally flipped)
// Supported for QR Code and Data Matrix
if (barcode.isMirrored()) {
    std::cout << "Barcode is mirrored\n";
}

// Check if inverted (dark background, light barcode)
if (barcode.isInverted()) {
    std::cout << "Barcode is inverted\n";
}

Error Correction Level

std::string ecLevel = barcode.ecLevel();

if (!ecLevel.empty()) {
    std::cout << "Error correction: " << ecLevel << "\n";
}

// QR Code: "L", "M", "Q", "H"
// Aztec: Percentage (e.g., "23")
// PDF417: Level 0-8
// Empty string if not applicable

Symbology Identifier

The symbology identifier follows the AIM standard ("]cm" format):

std::string symId = barcode.symbologyIdentifier();

if (!symId.empty()) {
    std::cout << "Symbology ID: " << symId << "\n";
    // Examples:
    // "]Q1" - QR Code
    // "]d2" - Data Matrix
    // "]e0" - EAN-13
    // "]C1" - Code 128
}

Format: ]cm where:

  • c = symbology code character
  • m = modifier

Structured Append (Multi-Symbol Barcodes)

Some formats support structured append, where data is split across multiple barcodes:

if (barcode.isPartOfSequence()) {
    int index = barcode.sequenceIndex();  // 0-based position
    int size = barcode.sequenceSize();     // Total number of symbols
    std::string id = barcode.sequenceId(); // Sequence identifier

    std::cout << "Symbol " << (index + 1) << " of " << size
              << " (ID: " << id << ")\n";

    if (barcode.isLastInSequence()) {
        std::cout << "This is the last symbol\n";
    }
}

Merging Structured Append Sequences

// Read all barcodes
auto barcodes = ZXing::ReadBarcodes(image);

// Merge all structured append sequences automatically
auto merged = ZXing::MergeStructuredAppendSequences(barcodes);

// Or merge a specific sequence manually
ZXing::Barcodes sequence = /* collect related barcodes */;
auto combined = ZXing::MergeStructuredAppendSequence(sequence);

std::cout << "Complete data: " << combined.text() << "\n";

Supported formats for structured append:

  • QR Code
  • PDF417
  • Data Matrix
  • Aztec

Additional Metadata

Reader Initialization

if (barcode.readerInit()) {
    std::cout << "Reader Initialization/Programming symbol\n";
}

Line Count (Linear Barcodes)

For linear (1D) barcodes, the number of scan lines that matched:

int lines = barcode.lineCount();

if (lines > 0) {
    std::cout << "Detected on " << lines << " scan lines\n";
}

Version (2D Codes)

For QR Code, Data Matrix, and Aztec:

std::string version = barcode.version();

if (!version.empty()) {
    std::cout << "Version/Size: " << version << "\n";
}

// QR Code: "1" to "40" (or "M1"-"M4" for Micro QR)
// Data Matrix: e.g., "12x12", "16x16"
// Aztec: e.g., "1" to "32"

Error Handling

if (!barcode.isValid()) {
    const ZXing::Error& error = barcode.error();

    std::cerr << "Error type: " << (int)error.type() << "\n";
    std::cerr << "Error message: " << error.msg() << "\n";

    switch (error.type()) {
        case ZXing::Error::Type::Format:
            std::cerr << "Format/decoding error\n";
            break;
        case ZXing::Error::Type::Checksum:
            std::cerr << "Checksum validation failed\n";
            break;
        case ZXing::Error::Type::Unsupported:
            std::cerr << "Unsupported feature\n";
            break;
        case ZXing::Error::Type::None:
            std::cerr << "No error (barcode is valid)\n";
            break;
    }
}

Working with Multiple Results

auto barcodes = ZXing::ReadBarcodes(image, options);

std::cout << "Found " << barcodes.size() << " barcodes:\n";

for (size_t i = 0; i < barcodes.size(); ++i) {
    const auto& bc = barcodes[i];

    std::cout << i + 1 << ". ";

    if (bc.isValid()) {
        std::cout << ZXing::ToString(bc.format()) << ": " << bc.text() << "\n";

        // Access position
        auto pos = bc.position();
        std::cout << "   Position: " << ZXing::ToString(pos) << "\n";

        // Access metadata
        if (!bc.ecLevel().empty()) {
            std::cout << "   EC Level: " << bc.ecLevel() << "\n";
        }
    } else {
        std::cout << "Invalid - " << bc.error().msg() << "\n";
    }
}

Filtering and Sorting Results

auto barcodes = ZXing::ReadBarcodes(image);

// Filter by format
ZXing::Barcodes qrCodes;
std::copy_if(barcodes.begin(), barcodes.end(), std::back_inserter(qrCodes),
    [](const ZXing::Barcode& bc) {
        return bc.format() == ZXing::BarcodeFormat::QRCode;
    });

// Sort by position (top to bottom)
std::sort(barcodes.begin(), barcodes.end(),
    [](const ZXing::Barcode& a, const ZXing::Barcode& b) {
        return a.position().topLeft().y < b.position().topLeft().y;
    });

// Find barcode at specific position
auto it = std::find_if(barcodes.begin(), barcodes.end(),
    [&](const ZXing::Barcode& bc) {
        return ZXing::IsInside(ZXing::PointI{x, y}, bc.position());
    });

Comparison

ZXing::Barcode bc1 = /* ... */;
ZXing::Barcode bc2 = /* ... */;

if (bc1 == bc2) {
    std::cout << "Barcodes are identical\n";
}

// Compares all properties: content, format, position, metadata, etc.

Character Encoding

// Check if barcode uses ECI
if (barcode.hasECI()) {
    std::cout << "Uses Extended Channel Interpretation\n";

    // Get content with ECI preservation
    auto eciBytes = barcode.bytesECI();

    // Get text with ECI mode
    std::string eciText = barcode.text(ZXing::TextMode::ECI);
}

// Content type helps determine encoding
if (barcode.contentType() == ZXing::ContentType::Text) {
    // Likely UTF-8 or other text encoding
    std::string text = barcode.text();
}

ByteArray Type

The ByteArray class is used for raw binary content:

class ByteArray : public std::vector<uint8_t> {
public:
    ByteArray();  // Default empty
    ByteArray(std::initializer_list<uint8_t> list);
    explicit ByteArray(int len);  // Pre-allocate with zeros
    explicit ByteArray(const std::string& str);  // From string

    void append(const ByteArray& other);
    std::string_view asString(size_t pos = 0, size_t len = std::string_view::npos) const;
};

// Utility function for hex representation
std::string ToHex(const ByteArray& bytes);

Usage:

auto barcode = ZXing::ReadBarcode(image);

// Get raw bytes
const ZXing::ByteArray& bytes = barcode.bytes();

// Convert to hex string for display
std::string hex = ZXing::ToHex(bytes);
std::cout << "Hex: " << hex << "\n";  // Output: "48 65 6C 6C 6F"

// Access as string view
std::string_view sv = bytes.asString();

// ByteArray is a std::vector<uint8_t>, so use standard vector operations
for (uint8_t byte : bytes) {
    std::cout << static_cast<int>(byte) << " ";
}

Type Aliases

// These types are equivalent
ZXing::Barcode bc = /* ... */;
ZXing::Result res = /* ... */;  // Same type

// Vectors
ZXing::Barcodes barcodes = /* ... */;  // std::vector<Barcode>
ZXing::Results results = /* ... */;     // std::vector<Result>

// Position
ZXing::Position pos = bc.position();    // QuadrilateralI
ZXing::QuadrilateralI quad = pos;       // Same type

Related

  • Barcode Reading - Reading barcodes to get Barcode objects
  • Barcode Writing - Creating Barcode objects for writing
  • Error Handling - Error class details
  • Geometry and Position - Position and Quadrilateral types
  • Character Encodings - Character set and ECI handling
  • Structured Append - Multi-symbol barcode support