VintaSoft Barcode .NET SDK 14.3: Documentation for .NET developer
In This Topic
    How to use Structure Append feature for distributing data message across several 2D barcodes?
    In This Topic
    Structure Append feature allows to distribute data message across several 2D barcodes
    (up to 16 DataMatrix barcodes, up to 16 QR barcodes, up to 26 Aztec barcodes, up to 99999 PDF417 barcodes, up to 9 Code16K barcodes, up to 35 DotCode barcodes) if data message cannot be stored in a single 2D barcode.

    Example: Here is an example that shows how to use Structure Append feature for distributing data message across several 2D barcodes.
    using System;
    using System.Text;
    
    using Vintasoft.Barcode;
    using Vintasoft.Barcode.BarcodeInfo;
    using Vintasoft.Imaging;
    
    /// <summary>
    /// Test that shows how to use Structured Append feature for distributing data message across
    /// several 2D barcodes.
    /// </summary>
    class StructureAppendExample
    {
    
        /// <summary>
        /// Runs the test.
        /// </summary>
        public static void Test()
        {
            BarcodeType barcodeType = BarcodeType.DataMatrix;
    
            int symbolsCount = 5;
    
            string symbolsValue =
                "In order to fit a non-square area or to handle larger messages than are practical " +
                "in a single symbol, a data message can be distributed across several symbols. " +
                "Aztec, Code 16K, DataMatrix, DotCode, MaxiCode, QR Code, PDF417, Micro PDF417 "+
                "symbols may be appended in a structured format.";
    
            // split data and generate barcodes
            VintasoftBitmap[] barcodeImages = GenerateBarcodes(barcodeType, symbolsValue, symbolsCount);
    
            // resort barcode images
            Array.Reverse(barcodeImages);
            Array.Reverse(barcodeImages, 0, barcodeImages.Length / 2);
    
            // read barcodes and merge data value
            string readValue = ReadBarcodeValue(barcodeImages, barcodeType);
    
            if (readValue == symbolsValue)
                Console.WriteLine("Success");
            else
                throw new ApplicationException();
        }
    
        /// <summary>
        /// Splits value and generates symbolCount barcodes using Structured Append.
        /// </summary>
        public static VintasoftBitmap[] GenerateBarcodes(BarcodeType barcodeType, string value, int symbolCount)
        {
            // create an image array
            VintasoftBitmap[] result = new VintasoftBitmap[symbolCount];
    
            // create the barcode writer
            using (BarcodeWriter writer = new BarcodeWriter())
            {
                // specify that writer must generate barcode of specified type
                writer.Settings.Barcode = barcodeType;
                writer.Settings.MinWidth = 5;
    
                // create parity data for a QR barcode value
                byte parityData = 0;
                if (barcodeType == BarcodeType.QR)
                    parityData = QRStructuredAppendCharacter.CaluculateParityData(value);
    
                // generate symbols(barcodes)
                int fragmentLength = value.Length / symbolCount;
                for (int i = 0; i < symbolCount; i++)
                {
                    // create Structured Append character
    
                    StructuredAppendCharacter structureAppendCharacter;
                    switch (barcodeType)
                    {
                        case BarcodeType.Aztec:
                            structureAppendCharacter =
                                new AztecStructuredAppendCharacter(i + 1, symbolCount, "");
                            break;
    
                        case BarcodeType.DataMatrix:
                            structureAppendCharacter =
                                new DataMatrixStructuredAppendCharacter(i + 1, symbolCount, 0);
                            break;
    
                        case BarcodeType.DotCode:
                            structureAppendCharacter =
                                NonDataFlags.CreateDotCodeStructuredAppendCharacter(i + 1, symbolCount);
                            break;
    
                        case BarcodeType.QR:
                            structureAppendCharacter =
                                new QRStructuredAppendCharacter(i + 1, symbolCount, parityData);
                            break;
    
                        case BarcodeType.Code16K:
                            structureAppendCharacter =
                                new StructuredAppendCharacter(i + 1, symbolCount);
                            writer.Settings.Height = 200;
                            break;
    
                        case BarcodeType.MaxiCode:
                            structureAppendCharacter =
                                new StructuredAppendCharacter(i + 1, symbolCount);
                            break;
    
                        case BarcodeType.MicroPDF417:
                            structureAppendCharacter =
                                new PDF417StructuredAppendCharacter(i + 1, symbolCount, "123");
                            break;
    
                        case BarcodeType.PDF417:
                            structureAppendCharacter =
                                new PDF417StructuredAppendCharacter(i + 1, symbolCount, "123");
                            break;
    
                        default:
                            throw new NotSupportedException();
                    }
    
                    // create symbol data
    
                    string symbolTextData;
                    if (i == symbolCount - 1)
                        symbolTextData = value.Substring(i * fragmentLength);
                    else
                        symbolTextData = value.Substring(i * fragmentLength, fragmentLength);
    
                    TextValueItem symbolData = new TextValueItem(symbolTextData);
    
                    // set the barcode value items
                    writer.Settings.ValueItems = new ValueItemBase[] { structureAppendCharacter, symbolData };
    
                    // create image with barcode
                    result[i] = writer.GetBarcodeAsVintasoftBitmap();
                }
    
                return result;
            }
        }
    
        /// <summary>
        /// Reads barcodes and merges the results into a single value.
        /// </summary>
        private static string ReadBarcodeValue(VintasoftBitmap[] barcodeImages, BarcodeType barcodeType)
        {
            // create the barcode reader
            using (BarcodeReader reader = new BarcodeReader())
            {
                // specify that reader must search for barcodes of specified type
                reader.Settings.ScanBarcodeTypes = barcodeType;            
    
                // barcode reading results
                IBarcodeInfo[] readingResults = new IBarcodeInfo[barcodeImages.Length];
                // read barcodes
                for (int i = 0; i < barcodeImages.Length; i++)
                {
                    // read barcode from image
                    readingResults[i] = reader.ReadBarcodes(barcodeImages[i])[0];
    
                    // dispose image
                    barcodeImages[i].Dispose();
                }
    
                // determine symbol count
                int symbolsCount = 0;
                for (int i = 0; i < readingResults.Length; i++)
                {
                    if (readingResults[i].ValueItems[0] is StructuredAppendCharacter)
                    {
                        symbolsCount = ((StructuredAppendCharacter)readingResults[i].ValueItems[0]).SymbolCount;
                        break;
                    }
                }
                if (symbolsCount == 0)
                    throw new ApplicationException("No Structured Append symbols.");
    
                // create array of string
                string[] resultValues = new string[symbolsCount];
                // fill resultValues
                for (int i = 0; i < readingResults.Length; i++)
                {
                    if (readingResults[i].ValueItems[0] is StructuredAppendCharacter)
                    {
                        StructuredAppendCharacter structureAppendCharacter =
                            (StructuredAppendCharacter)readingResults[i].ValueItems[0];
                        if (structureAppendCharacter.SymbolCount == symbolsCount)
                        {
                            readingResults[i].ShowNonDataFlagsInValue = false;
                            resultValues[structureAppendCharacter.SymbolPosition - 1] = readingResults[i].Value;
                        }
                    }
                }
    
                // build result string
                StringBuilder result = new StringBuilder();
                for (int i = 0; i < resultValues.Length; i++)
                {
                    if (resultValues[i] != null)
                    {
                        result.Append(resultValues[i]);
                    }
                    else
                    {
                        throw new ApplicationException(string.Format("missing symbol at position {0}", i + 1));
                    }
                }
    
                return result.ToString();
            }
        }
    
    }
    
    
    Imports System.Text
    
    Imports Vintasoft.Barcode
    Imports Vintasoft.Barcode.BarcodeInfo
    Imports Vintasoft.Imaging
    
    ''' <summary>
    ''' Test that shows how to use Structured Append feature for distributing data message across
    ''' several 2D barcodes.
    ''' </summary>
    Class StructureAppendExample
    
        ''' <summary>
        ''' Runs the test.
        ''' </summary>
        Public Shared Sub Test()
            Dim barcodeType__1 As BarcodeType = BarcodeType.DataMatrix
    
            Dim symbolsCount As Integer = 5
    
            Dim symbolsValue As String = "In order to fit a non-square area or to handle larger messages than are practical " & "in a single symbol, a data message can be distributed across several symbols. " & "Aztec, Code 16K, DataMatrix, DotCode, MaxiCode, QR Code, PDF417, Micro PDF417 " & "symbols may be appended in a structured format."
    
            ' split data and generate barcodes
            Dim barcodeImages As VintasoftBitmap() = GenerateBarcodes(barcodeType__1, symbolsValue, symbolsCount)
    
            ' resort barcode images
            Array.Reverse(barcodeImages)
            Array.Reverse(barcodeImages, 0, barcodeImages.Length \ 2)
    
            ' read barcodes and merge data value
            Dim readValue As String = ReadBarcodeValue(barcodeImages, barcodeType__1)
    
            If readValue = symbolsValue Then
                Console.WriteLine("Success")
            Else
                Throw New ApplicationException()
            End If
        End Sub
    
        ''' <summary>
        ''' Splits value and generates symbolCount barcodes using Structured Append.
        ''' </summary>
        Public Shared Function GenerateBarcodes(barcodeType__1 As BarcodeType, value As String, symbolCount As Integer) As VintasoftBitmap()
            ' create an image array
            Dim result As VintasoftBitmap() = New VintasoftBitmap(symbolCount - 1) {}
    
            ' create the barcode writer
            Using writer As New BarcodeWriter()
                ' specify that writer must generate barcode of specified type
                writer.Settings.Barcode = barcodeType__1
                writer.Settings.MinWidth = 5
    
                ' create parity data for a QR barcode value
                Dim parityData As Byte = 0
                If barcodeType__1 = BarcodeType.QR Then
                    parityData = QRStructuredAppendCharacter.CaluculateParityData(value)
                End If
    
                ' generate symbols(barcodes)
                Dim fragmentLength As Integer = value.Length \ symbolCount
                For i As Integer = 0 To symbolCount - 1
                    ' create Structured Append character
    
                    Dim structureAppendCharacter As StructuredAppendCharacter
                    Select Case barcodeType__1
                        Case BarcodeType.Aztec
                            structureAppendCharacter = New AztecStructuredAppendCharacter(i + 1, symbolCount, "")
                            Exit Select
    
                        Case BarcodeType.DataMatrix
                            structureAppendCharacter = New DataMatrixStructuredAppendCharacter(i + 1, symbolCount, 0)
                            Exit Select
    
                        Case BarcodeType.DotCode
                            structureAppendCharacter = NonDataFlags.CreateDotCodeStructuredAppendCharacter(i + 1, symbolCount)
                            Exit Select
    
                        Case BarcodeType.QR
                            structureAppendCharacter = New QRStructuredAppendCharacter(i + 1, symbolCount, parityData)
                            Exit Select
    
                        Case BarcodeType.Code16K
                            structureAppendCharacter = New StructuredAppendCharacter(i + 1, symbolCount)
                            writer.Settings.Height = 200
                            Exit Select
    
                        Case BarcodeType.MaxiCode
                            structureAppendCharacter = New StructuredAppendCharacter(i + 1, symbolCount)
                            Exit Select
    
                        Case BarcodeType.MicroPDF417
                            structureAppendCharacter = New PDF417StructuredAppendCharacter(i + 1, symbolCount, "123")
                            Exit Select
    
                        Case BarcodeType.PDF417
                            structureAppendCharacter = New PDF417StructuredAppendCharacter(i + 1, symbolCount, "123")
                            Exit Select
                        Case Else
    
                            Throw New NotSupportedException()
                    End Select
    
                    ' create symbol data
    
                    Dim symbolTextData As String
                    If i = symbolCount - 1 Then
                        symbolTextData = value.Substring(i * fragmentLength)
                    Else
                        symbolTextData = value.Substring(i * fragmentLength, fragmentLength)
                    End If
    
                    Dim symbolData As New TextValueItem(symbolTextData)
    
                    ' set the barcode value items
                    writer.Settings.ValueItems = New ValueItemBase() {structureAppendCharacter, symbolData}
    
                    ' create image with barcode
                    result(i) = writer.GetBarcodeAsVintasoftBitmap()
                Next
    
                Return result
            End Using
        End Function
    
        ''' <summary>
        ''' Reads barcodes and merges the results into a single value.
        ''' </summary>
        Private Shared Function ReadBarcodeValue(barcodeImages As VintasoftBitmap(), barcodeType As BarcodeType) As String
            ' create the barcode reader
            Using reader As New BarcodeReader()
                ' specify that reader must search for barcodes of specified type
                reader.Settings.ScanBarcodeTypes = barcodeType
    
                ' barcode reading results
                Dim readingResults As IBarcodeInfo() = New IBarcodeInfo(barcodeImages.Length - 1) {}
                ' read barcodes
                For i As Integer = 0 To barcodeImages.Length - 1
                    ' read barcode from image
                    readingResults(i) = reader.ReadBarcodes(barcodeImages(i))(0)
    
                    ' dispose image
                    barcodeImages(i).Dispose()
                Next
    
                ' determine symbol count
                Dim symbolsCount As Integer = 0
                For i As Integer = 0 To readingResults.Length - 1
                    If TypeOf readingResults(i).ValueItems(0) Is StructuredAppendCharacter Then
                        symbolsCount = DirectCast(readingResults(i).ValueItems(0), StructuredAppendCharacter).SymbolCount
                        Exit For
                    End If
                Next
                If symbolsCount = 0 Then
                    Throw New ApplicationException("No Structured Append symbols.")
                End If
    
                ' create array of string
                Dim resultValues As String() = New String(symbolsCount - 1) {}
                ' fill resultValues
                For i As Integer = 0 To readingResults.Length - 1
                    If TypeOf readingResults(i).ValueItems(0) Is StructuredAppendCharacter Then
                        Dim structureAppendCharacter As StructuredAppendCharacter = DirectCast(readingResults(i).ValueItems(0), StructuredAppendCharacter)
                        If structureAppendCharacter.SymbolCount = symbolsCount Then
                            readingResults(i).ShowNonDataFlagsInValue = False
                            resultValues(structureAppendCharacter.SymbolPosition - 1) = readingResults(i).Value
                        End If
                    End If
                Next
    
                ' build result string
                Dim result As New StringBuilder()
                For i As Integer = 0 To resultValues.Length - 1
                    If resultValues(i) IsNot Nothing Then
                        result.Append(resultValues(i))
                    Else
                        Throw New ApplicationException(String.Format("missing symbol at position {0}", i + 1))
                    End If
                Next
    
                Return result.ToString()
            End Using
        End Function
    
    End Class