Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Generated QR not scan-able #46

Closed
YohannesTz opened this issue Oct 11, 2023 · 6 comments
Closed

Generated QR not scan-able #46

YohannesTz opened this issue Oct 11, 2023 · 6 comments
Assignees
Labels
question Further information is requested

Comments

@YohannesTz
Copy link

YohannesTz commented Oct 11, 2023

I asked for Java sample and I got some code that works and generates the QR I want but the generated Qr is not scannable. I am not sure what I missed. I tried it on multiple devices.

here is my code

import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;

import androidx.core.content.ContextCompat;

import com.github.alexzhirkevich.customqrgenerator.HighlightingType;
import com.github.alexzhirkevich.customqrgenerator.QrData;
import com.github.alexzhirkevich.customqrgenerator.QrErrorCorrectionLevel;
import com.github.alexzhirkevich.customqrgenerator.QrHighlighting;
import com.github.alexzhirkevich.customqrgenerator.QrHighlightingKt;
import com.github.alexzhirkevich.customqrgenerator.vector.QrCodeDrawableKt;
import com.github.alexzhirkevich.customqrgenerator.vector.QrVectorOptions;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QVectorShapeUtilsKt;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorBackground;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorBallShape;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorColor;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorColors;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorFrameShape;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorLogo;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorLogoPadding;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorLogoShape;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorPixelShape;
import com.github.alexzhirkevich.customqrgenerator.vector.style.QrVectorShapes;
import com.github.yohannestz.cberemix.R;
import com.google.android.material.elevation.SurfaceColors;

import java.nio.charset.StandardCharsets;

public class QRCodeGenerator {
    private final Context context;

    public QRCodeGenerator(Context context) {
        this.context = context;
    }

    public Drawable drawableFromText(String data) {
        if (Utils.isHex(data)) {
            data = data.toUpperCase();
        }
        QrData qrData = new QrData.Text(data);
        return QrCodeDrawableKt.QrCodeDrawable(qrData, getQrVectorOptions(data), StandardCharsets.UTF_8);
    }

    private QrVectorOptions getQrVectorOptions(String data) {
        if (data.length() < 140)
            return getDesignQrVectorOptions(data);
        else
            return getCompatibilityQrVectorOptions();
    }

    private QrVectorOptions getDesignQrVectorOptions(String data) {
        QrVectorLogo.Builder qrVectorLogoBuilder = new QrVectorLogo.Builder();
        qrVectorLogoBuilder.setDrawable(ContextCompat.getDrawable(context, R.drawable.cbe_vector));
        qrVectorLogoBuilder.setShape(new QrVectorLogoShape.RoundCorners(0.5f));
        qrVectorLogoBuilder.setPadding(new QrVectorLogoPadding.Natural(.5f));
        qrVectorLogoBuilder.setSize(0.1f);
        QrVectorLogo qrVectorLogo = qrVectorLogoBuilder.build();

        QrVectorOptions.Builder optionsBuilder = getDefaultOptionsBuilder()
                .setShapes(
                        new QrVectorShapes(
                                new QrVectorPixelShape.Rect(.75f),
                                new QrVectorPixelShape.Rect(.75f),
                                new QrVectorBallShape.RoundCorners(.15f, true, true, true, true),
                                new QrVectorFrameShape.RoundCorners(.15f, 1f, true, true, true, true, 7),
                                true
                        )
                )
                .setColors(
                        new QrVectorColors(
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context)),
                                new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary)),
                                new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary)),
                                new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary))
                        )
                )
                .setBackground(
                        new QrVectorBackground(
                                ContextCompat.getDrawable(context, R.drawable.bg_box),
                                (drawable, i, i1) -> Bitmap.createBitmap(i, i1, Bitmap.Config.ARGB_8888),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context))
                        )
                )
                .setLogo(qrVectorLogo)
                .setAnchorsHighlighting(new QrHighlighting(
                        new HighlightingType.Styled(
                                QrHighlightingKt.QrVersionEyeShape(
                                        new QrVectorFrameShape.AsPixelShape(new QrVectorPixelShape.Rect(.75f), 5),
                                        QVectorShapeUtilsKt.asBallShape(new QrVectorPixelShape.Rect(.75f))),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context)),
                                new QrVectorPixelShape.Rect(.0f),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context))
                        ),
                        new HighlightingType.Styled(
                                QrHighlightingKt.QrVersionEyeShape(
                                        new QrVectorFrameShape.AsPixelShape(new QrVectorPixelShape.Rect(.75f), 5),
                                        QVectorShapeUtilsKt.asBallShape(new QrVectorPixelShape.Rect(.75f))),
                                new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary)),
                                new QrVectorPixelShape.Rect(.0f),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context))
                        ),
                        new HighlightingType.Styled(
                                new QrVectorPixelShape.Rect(.75f), new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context)),
                                new QrVectorPixelShape.Rect(.75f), new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary))),
                        1.0f
                ));


        if (data.length() > 60) {
            optionsBuilder.setErrorCorrectionLevel(QrErrorCorrectionLevel.Low);
        } else {
            optionsBuilder.setErrorCorrectionLevel(QrErrorCorrectionLevel.Medium);
        }

        new HighlightingType.Styled(new QrVectorFrameShape.RoundCorners(.15f, 1f, true, true, true, true, 7), new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context)), new QrVectorFrameShape.RoundCorners(.15f, 1f, true, true, true, true, 7), new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary)));
        QrHighlightingKt.QrVersionEyeShape(
                new QrVectorFrameShape.AsPixelShape(
                        new QrVectorPixelShape.Rect(.75f), 5
                ),
                QVectorShapeUtilsKt.asBallShape(new QrVectorPixelShape.Rect(.75f))
        );

        return optionsBuilder.build();
    }

    private QrVectorOptions getCompatibilityQrVectorOptions() {
        return getDefaultOptionsBuilder()
                .setShapes(
                        new QrVectorShapes(
                                new QrVectorPixelShape.RoundCorners(.0f),
                                new QrVectorPixelShape.RoundCorners(.35f),
                                new QrVectorBallShape.RoundCorners(.15f, true, true, true, true),
                                new QrVectorFrameShape.RoundCorners(.15f, 1f, true, true, true, true, 7),
                                true
                        )
                )
                .build();
    }

    private QrVectorOptions.Builder getDefaultOptionsBuilder() {
        return new QrVectorOptions.Builder()
                .setPadding(.15f)
                .setBackground(
                        new QrVectorBackground(
                                ContextCompat.getDrawable(context, R.drawable.bg_box),
                                (drawable, i, i1) -> Bitmap.createBitmap(i, i1, Bitmap.Config.ARGB_8888),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context))
                        )
                )
                .setErrorCorrectionLevel(QrErrorCorrectionLevel.Low);
    }

    //for future
    private static Bitmap drawableToBitmap(Drawable drawable, int size) {
        if (drawable instanceof BitmapDrawable) {
            BitmapDrawable bitmapDrawable = (BitmapDrawable) drawable;
            if (bitmapDrawable.getBitmap() != null) {
                return bitmapDrawable.getBitmap();
            }
        }
        Bitmap bitmap = Bitmap.createBitmap(size, size, Bitmap.Config.ARGB_8888);
        Canvas canvas = new Canvas(bitmap);
        drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
        drawable.draw(canvas);
        return bitmap;
    }
}

and in my fragment I have:

   //onStart
   binding.qrImageView.setImageDrawable(generateQr(qrDataText));
   private Drawable generateQr(String payload) {
        QRCodeGenerator qrCodeGenerator = new QRCodeGenerator(getContext());
        qrDataText = "https://cbe.com/receive?account=100003450&amount=" + payload;
        return qrCodeGenerator.drawableFromText(qrDataText);
    }

Result:
image preview

@YohannesTz YohannesTz added the question Further information is requested label Oct 11, 2023
@alexzhirkevich
Copy link
Owner

Read this

@YohannesTz
Copy link
Author

hi, sorry for the late reply. I tried what the docs recommended but I am still was not able to make it scannable in other apps.

@alexzhirkevich
Copy link
Owner

Then try to remove highlighting. Its experimental and is not needed in your case

@hardikbhalodi
Copy link

hardikbhalodi commented Oct 14, 2023

@YohannesTz remove this part and it will work

  setAnchorsHighlighting(new QrHighlighting(
                        new HighlightingType.Styled(
                                QrHighlightingKt.QrVersionEyeShape(
                                        new QrVectorFrameShape.AsPixelShape(new QrVectorPixelShape.Rect(.75f), 5),
                                        QVectorShapeUtilsKt.asBallShape(new QrVectorPixelShape.Rect(.75f))),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context)),
                                new QrVectorPixelShape.Rect(.0f),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context))
                        ),
                        new HighlightingType.Styled(
                                QrHighlightingKt.QrVersionEyeShape(
                                        new QrVectorFrameShape.AsPixelShape(new QrVectorPixelShape.Rect(.75f), 5),
                                        QVectorShapeUtilsKt.asBallShape(new QrVectorPixelShape.Rect(.75f))),
                                new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary)),
                                new QrVectorPixelShape.Rect(.0f),
                                new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context))
                        ),
                        new HighlightingType.Styled(
                                new QrVectorPixelShape.Rect(.75f), new QrVectorColor.Solid(SurfaceColors.SURFACE_1.getColor(context)),
                                new QrVectorPixelShape.Rect(.75f), new QrVectorColor.Solid(ContextCompat.getColor(context, R.color.md_theme_light_primary))),
                        1.0f
                ));

also do not use padding at all if not needed or decrease padding to 0.1f
qrVectorLogoBuilder.setPadding(new QrVectorLogoPadding.Natural(.1f));

@YohannesTz
Copy link
Author

Hi, I removed the part specified. was still unscannable. changing the color to black did the trick. didn't know contrast really affected the results. so what do you guys recommend me when it comes to branding?

@alexzhirkevich
Copy link
Owner

Always test it and search for the most suitable working variant. QR codes aren't magic and not all styles are possible

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested
Projects
None yet
Development

No branches or pull requests

3 participants