B4A Library [B4X] QRGenerator - Cross platform QR code generator

Discussion in 'Additional libraries, classes and official updates' started by Erel, May 16, 2018.

Thread Status:
Not open for further replies.
  1. Erel

    Erel Administrator Staff Member Licensed User

    QRGenerator is a class that generates QR codes.
    It is written in B4X and it is compatible with B4A, B4i and B4J.

    iPhone default camera app recognizing the QR code displayed in a B4A app:

    [​IMG]

    Supports the following formats: 4-L, 4-H and 9-L. Bytes mode only.
    Can create codes made of up to 230 bytes.

    It depends on XUI library.
    It uses the very useful BytesBuilder class.
    If you get a compilation error related to Bit.ArrayCopy method then you should add ByteConverter library and use it instead. Bit.ArrayCopy is a relatively new method.

    I wasn't familiar with the qr code format before. It was more complicated than I expected.
    Very good resource about the format: https://www.thonky.com/qr-code-tutorial/introduction
    The Reed-Solomon error correction calculation is based on zxing open source project.

    A B4J example is attached with QRGenerator and BytesBuilder classes.

    Versions

    V1.20 - Adds support for 9-L codes. Also renamed the local Block variable as it is a reserved word in B4i.
    v1.11 - Fixes an issue with messages 35 or 36 bytes long.
     

    Attached Files:

    Last edited: Aug 30, 2018
  2. Alexander Stolte

    Alexander Stolte Well-Known Member Licensed User

    on qrcode monkey you can create qr-codes with a logo, they even work.
    would that be possible in the future with B4X?
    qr-code (5).png
     
  3. Erel

    Erel Administrator Staff Member Licensed User

    Why wait for the future?

    [​IMG]

    v1.10 of QRGenerator adds support for 4-H codes. In this format 30% of the data can be restored from the error codes.
    This makes it possible to add a logo at the center and keep the data complete.
    It will use 4-h format if the data <= 34 bytes. See the logs.

    The larger the image the larger the chances that the code will be broken.
     
  4. Cableguy

    Cableguy Expert Licensed User

    Can transarent images be used?
     
  5. Erel

    Erel Administrator Staff Member Licensed User

    Sure.
     
    Cableguy likes this.
  6. DonManfred

    DonManfred Expert Licensed User

    :D
    Nice addition! :)
     
    Alexander Stolte and Erel like this.
  7. Erel

    Erel Administrator Staff Member Licensed User

    A slightly modified version that adds some colors and changes the blocks to circles:

    [​IMG]

    The change is in DrawMatrix sub.

    The colors can be used with the square blocks as well (with the QRGenerator from the first post):

    [​IMG]
     

    Attached Files:

    MarcoRome, Levit, lemonisdead and 3 others like this.
  8. Cableguy

    Cableguy Expert Licensed User

    Hmmm .... I wonder if it is possible to create invisible QRCodes.... (pun intended)
     
  9. Alexander Stolte

    Alexander Stolte Well-Known Member Licensed User

    This is why i love B4X :D:D:D

    EDIT: Thanks!!
     
  10. Erel

    Erel Administrator Staff Member Licensed User

    Last example for today:

    [​IMG]

    You can play with the factors to make it more detectable.

    Code:
    Sub AddSomeColors(QRBmp As B4XBitmap, logo As B4XBitmap) As B4XBitmap
       
    Dim bc As BitmapCreator
       bc.Initialize(QRBmp.Width, QRBmp.Height)
       bc.CopyPixelsFromBitmap(QRBmp)
       
    Dim LogoBC As BitmapCreator
       LogoBC.Initialize(QRBmp.Width, QRBmp.Height)
       LogoBC.CopyPixelsFromBitmap(logo)
       
    Dim LightFactor As Float = 2
       
    Dim DarkFactor As Float = 0.8
       
    Dim argb, largb As ARGBColor
       
    For x = 0 To bc.mWidth - 1
           
    For y = 0 To bc.mHeight - 1
               bc.GetARGB(x, y, argb)
               LogoBC.GetARGB(x, y, largb)
               
    If largb.a > 0 Then
                   
    Dim factor As Float
                   
    If argb.r = 0 Then factor = DarkFactor Else factor = LightFactor
                   largb.r = 
    Min(255, largb.r * factor)
                   largb.g =  
    Min(255, largb.g * factor)
                   largb.b =  
    Min(255, largb.b * factor)
                   bc.SetARGB(x, y, largb)
               
    End If
           
    Next
       
    Next
       
    Return bc.Bitmap
    End Sub
     
  11. Erel

    Erel Administrator Staff Member Licensed User

    Better implementation:

    [​IMG]

    Code:
    Sub AddSomeColors(QRBmp As B4XBitmap, logo As B4XBitmap) As B4XBitmap
       
    Dim bc As BitmapCreator
       bc.Initialize(QRBmp.Width, QRBmp.Height)
       bc.CopyPixelsFromBitmap(QRBmp)
       
    Dim LogoBC As BitmapCreator
       LogoBC.Initialize(QRBmp.Width, QRBmp.Height)
       LogoBC.CopyPixelsFromBitmap(logo)
       
    Dim argb, largb As ARGBColor
       
    For x = 0 To bc.mWidth - 1
           
    For y = 0 To bc.mHeight - 1
               bc.GetARGB(x, y, argb)
               LogoBC.GetARGB(x, y, largb)
               
    If largb.a > 0 Then
                   largb.a = 
    200
                   LogoBC.SetARGB(x, y, largb)
                   bc.BlendPixel(LogoBC, x, y, x, y)
               
    End If
           
    Next
       
    Next
       
    Return bc.Bitmap
    End Sub
     
    Last edited: May 17, 2018
  12. Johan Schoeman

    Johan Schoeman Expert Licensed User

    I have done something similar here before (for B4A) and understand the complexity of generating 2D codes (have done it for QR codes version 1 to 40 with all 4 error levels and any masking pattern. Included is PDF 417 codes and Aztec codes (level 1 to 11). Also some 1D barcodes. Calculating error correction words is a whole excercise on its own. Creating generator polynomials are also complex.

    Have also done a posting for B4J with same code converted from B4A to B4J somewhere in the forum.

    b4a:

    https://www.b4x.com/android/forum/threads/qr-code-library.41408/#post-322509
    b4j:

    https://www.b4x.com/android/forum/t...e93-ean8-ean13-and-code128.57248/#post-361917

    Not simple at all when it comes to packing out the bits into the correct pattern that is required. Aztec codes get more complex and packing out Data Matrix is a nightmare.
    But agree with Erel - far more complicated than what it seems to be. Once I "mastered" PDF417 I could make my own airline tickets - and tested them at numerous airports. It was great fun...:)

    Qr codes with error correction H is quite tolerable and can recover data from a damaged QR code. As long as all three finding patters are there. Break one and the QR code is failing a scan more often than not
     
    Last edited: Jun 6, 2018
  13. prajinpraveen

    prajinpraveen Member Licensed User

    Thank you for this . works like a charm
    is it possible to use this on B4J web App?
     
  14. DonManfred

    DonManfred Expert Licensed User

    the [B4X] suggests it is working with B4a, b4i and b4j
     
  15. Erel

    Erel Administrator Staff Member Licensed User

    That's almost true. It works in B4J UI apps.

    It will not work in non-ui apps as it is based on XUI and B4XCanvas. You can make a small helper app that receives the data to encode and creates an image file. Use jShell to call it.
     
  16. prajinpraveen

    prajinpraveen Member Licensed User

    Thank you. The error was on b4xcanvas when using on ABMaterial . I will create a helper app.
     
  17. Serway

    Serway Member Licensed User

    Hello,

    How to insert an image into a QRCode ?
    The QRCode in the sample attached project is broken.
    Thanks community for help.

    Thierry
     

    Attached Files:

  18. Erel

    Erel Administrator Staff Member Licensed User

    Several mistakes in your code.

    1. Why are you using BitmapDrawable?
    2. B4XView.SetBitmap sets the gravity to center. In this case the returned bitmap is large due to the device scale. You can either set the gravity to FILL or resize the bitmap yourself:
    Code:
    ImvQR.SetBitmap(QR.AddBitmap(BmpQR, logo, 255 * Value / 100).Resize(ImvQR.Width, ImvQR.Height, True))
    3. The image itself is not a very good fit for this masking as its contrast is very large.
    4. I modified your code and added a seekbar that helps with finding a good alpha value.

    It is about 140 when I test it with the default iPhone camera app.

    [​IMG]
     

    Attached Files:

  19. Serway

    Serway Member Licensed User

    Hi Erel,

    How fast of response !
    Thank you very much Erel for your assistance.
    It works perfectly.

    Thierry
    (ישראלי מצרפת)
     
    Erel likes this.
  20. Gabino A. de la Gala

    Gabino A. de la Gala Active Member Licensed User

    What would be the best way to print the generated code to a network printer?

    My idea is to generate the QR using a B4A application and once generated, print it on a network printer.

    My idea is to put the same QR13 EAN13, the batch and the expiration date of the products as they are received. Then generate the corresponding label so that, at the time of sale, with reading the QR and automatically we obtain all the "important" data.
     
Thread Status:
Not open for further replies.
Loading...
  1. This site uses cookies to help personalise content, tailor your experience and to keep you logged in if you register.
    By continuing to use this site, you are consenting to our use of cookies.
    Dismiss Notice