二维码内容过多,生成的二维码太复杂,导致扫码的时候,过慢或者扫不出来解决方案。附二维码生成、解析工具类

总所周知,二维码的内容越多,二维码越复杂,越是复杂的二维码扫码效率越慢,有时候导致直接扫码的时候直接扫不出来。

解决方法:
在生成二维码的时候,对二维码文本进行压缩,压缩内容生成二维码,在扫码的时候,把扫码获取的压缩内容传给后台,然后进行二维码解压即可获取解压内容。

具体实现方法如下:
1. 引入pom文件

		<!--二维码解析-->
        <dependency>
            <groupId>com.google.zxing</groupId>
            <artifactId>core</artifactId>
            <version>3.3.3</version>
        </dependency>
        <dependency>
            <groupId>com.google.zxing</groupId>
            <artifactId>javase</artifactId>
            <version>3.3.3</version>
        </dependency>

2. 写测试类

 public static void main(String[] args) throws IOException, NotFoundException {
        String content="假设这个文本的内容超级长";
        //压缩
        String zipContent=zipBase64(content);
        System.out.println("压缩内容"+zipContent);
        //生成二维码
        QRCodeUtil.getQRCode(zipContent,"jpg","G:/img/testQr2.jpg","UTF-8");
        //获取二维码路径
        String format="G:/img/testQr2.jpg";
        //获取压缩内容
        String analysis = QRCodeUtil.analysis(format, "UTF-8");
        //解压已压缩内容
        String unzipBase64 = unzipBase64(analysis);
        System.out.println(unzipBase64);
    }

3. 结果:
生成的图片如下:
在这里插入图片描述
控制台输出:
在这里插入图片描述
4.工具类

压缩解压文本:

/**
     * 压缩文本
     * @param text
     * @return
     */
    public static String zipBase64(String text) {
        //创建一个新的字节数组输出流。缓冲区容量最初为 32 字节
        try (ByteArrayOutputStream out = new ByteArrayOutputStream()) {
            //使用默认压缩器和缓冲区大小创建新的输出流
            try (DeflaterOutputStream deflaterOutputStream = new DeflaterOutputStream(out)) {
                deflaterOutputStream.write(text.getBytes(Charset.forName("UTF-8")));
            }
            return Base64.getEncoder().encodeToString(out.toByteArray());
        } catch (IOException e) {
        }
        return "";
    }

    /**
     * 解压文本
     * @param text
     * @return
     */
    public static String unzipBase64(String text) {
        try (ByteArrayOutputStream os = new ByteArrayOutputStream()) {
            //使用默认解压缩器和缓冲区创建新的输出流
            try (OutputStream outputStream = new InflaterOutputStream(os)) {
                outputStream.write(Base64.getDecoder().decode(text.getBytes()));
            }
            return new String(os.toByteArray(), Charset.forName("UTF-8"));
        } catch (IOException e) {

        }
        return "";
    }

生成二维码,解析二维码工具:

package com.excel.util;

import cn.hutool.extra.qrcode.BufferedImageLuminanceSource;
import com.google.zxing.*;
import com.google.zxing.client.j2se.MatrixToImageWriter;
import com.google.zxing.common.BitMatrix;
import com.google.zxing.common.HybridBinarizer;
import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel;

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.nio.file.Path;
import java.util.HashMap;
import java.util.Map;

/**
 * 二维码的解析,生成
 * @author lenovo
 */
public class QRCodeUtil {

    /**
     * 生成二维码
     * @param contents 内容
     * @param format 二维码图片后缀
     * @param filepath //生成二维码路径(当包含二维码名称和后缀,忽略format)
     * @throws IOException
     * @throws NotFoundException
     */
    public static void getQRCode(String contents,String format,String filepath) throws IOException, NotFoundException {
        getQRCode(contents, format, filepath,"utf-8");
    }
    /**
     * 生成二维码
     * @param contents 内容
     * @param format 二维码图片后缀
     * @param filepath //生成二维码路径(当包含二维码名称和后缀,忽略format)
     * @param character 二维码内容编码方式
     * @throws IOException
     * @throws NotFoundException
     */
    public static void getQRCode(String contents,String format,String filepath,String character) throws IOException, NotFoundException {
       getQRCode(300,300,contents,format,filepath,character);
    }
    /**
     * 生成二维码
     * @param width 宽
     * @param height 高
     * @param contents 内容
     * @param format 二维码图片后缀
     * @param filepath //生成二维码路径(当包含二维码名称和后缀,忽略format)
     * @param character 二维码内容编码方式
     * @throws IOException
     * @throws NotFoundException
     */
    public static void getQRCode(int width,int height,String contents,String format,String filepath,String character) throws IOException, NotFoundException {
        HashMap map = new HashMap();
        map.put(EncodeHintType.CHARACTER_SET,character);
        map.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.M);
        map.put(EncodeHintType.MARGIN, 0);
        try {
            BitMatrix bm = new MultiFormatWriter().encode(contents, BarcodeFormat.QR_CODE, width, height,map);
            Path file = new File(filepath).toPath();
            MatrixToImageWriter.writeToPath(bm, format, file);
        } catch (WriterException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    /**
     * 解析上传二维码内容(直解析utf-8和GBK编码的二维码)
     * @param QRImg 二维码图片内容
     * @throws IOException
     * @throws NotFoundException
     */
    public static String analysis(File QRImg) throws IOException, NotFoundException {
        BufferedImage image = ImageIO.read(QRImg);
        BinaryBitmap bb = new BinaryBitmap(new HybridBinarizer(new BufferedImageLuminanceSource(image)));
        HashMap map = new HashMap();
        map.put(DecodeHintType.CHARACTER_SET, "utf-8");
        Result result = new MultiFormatReader().decode(bb, map);
        String QRContents=result.getText();
        if (result.getText().contains("�")){
            //乱码了,更换编码方式
            System.out.println("乱码了,更换编码格式(GBK)");
            map.put(DecodeHintType.CHARACTER_SET, "GBK");
            result = new MultiFormatReader().decode(bb, map);
            QRContents=result.getText();
        }
        System.out.println("二维码文本内容:"+QRContents);
        return QRContents;
    }
    /**
     * 解析本地二维码内容(直解析utf-8和GBK编码的二维码)
     * @param filePath 二维码图片地址
     * @throws IOException
     * @throws NotFoundException
     */
    public static String analysis(String filePath) throws IOException, NotFoundException {
        BufferedImage image = ImageIO.read(new File(filePath));
        BinaryBitmap bb = new BinaryBitmap(new HybridBinarizer(new BufferedImageLuminanceSource(image)));
        HashMap map = new HashMap();
        map.put(DecodeHintType.CHARACTER_SET, "utf-8");
        Result result = new MultiFormatReader().decode(bb, map);
        String QRContents=result.getText();
        if (result.getText().contains("�")){
            //乱码了,更换编码方式
            System.out.println("乱码了,更换编码格式(GBK)");
            map.put(DecodeHintType.CHARACTER_SET, "GBK");
            result = new MultiFormatReader().decode(bb, map);
            QRContents=result.getText();
        }
        System.out.println("二维码文本内容:"+QRContents);
        return QRContents;
    }
    /**
     * 解析本地二维码内容,自定义编码格式
     * @param filePath 二维码图片地址
     * @param character 二维码内容编码格式
     * @throws IOException
     * @throws NotFoundException
     */
    public static String analysis(String filePath,String character) throws IOException, NotFoundException {
        BufferedImage image = ImageIO.read(new File(filePath));
        BinaryBitmap bb = new BinaryBitmap(new HybridBinarizer(new BufferedImageLuminanceSource(image)));
        HashMap map = new HashMap();
        map.put(DecodeHintType.CHARACTER_SET,character);
        map.put(DecodeHintType.TRY_HARDER, Boolean.TRUE);
        //复杂模式
        map.put(DecodeHintType.PURE_BARCODE, Boolean.TRUE);
        Result result = new MultiFormatReader().decode(bb, map);
        String QRContents=result.getText();
        return QRContents;
    }
    /**
     * 解析二维码,此方法解析一个路径的二维码图片(带logo)
     * path:二维码图片路径
     */
    public static String deEncodeByPath(String path) {
        String content = null;
        BufferedImage image;
        try {
            image = ImageIO.read(new File(path));
            LuminanceSource source = new BufferedImageLuminanceSource(image);
            Binarizer binarizer = new HybridBinarizer(source);
            BinaryBitmap binaryBitmap = new BinaryBitmap(binarizer);
            Map<DecodeHintType, Object> hints = new HashMap<DecodeHintType, Object>();
            hints.put(DecodeHintType.CHARACTER_SET, "GBK");
            hints.put(DecodeHintType.TRY_HARDER, Boolean.TRUE);
            Result result = new MultiFormatReader().decode(binaryBitmap, hints);//解码
            System.out.println("图片中内容:  ");
            System.out.println("content: " + result.getText());
            content = result.getText();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (NotFoundException e) {
            //这里判断如果识别不了带LOGO的图片,重新添加上一个属性
            try {
                image = ImageIO.read(new File(path));
                LuminanceSource source = new BufferedImageLuminanceSource(image);
                Binarizer binarizer = new HybridBinarizer(source);
                BinaryBitmap binaryBitmap = new BinaryBitmap(binarizer);
                Map<DecodeHintType, Object> hints = new HashMap<DecodeHintType, Object>();
                //设置编码格式
                hints.put(DecodeHintType.CHARACTER_SET, "GBK");
                //设置优化精度
                hints.put(DecodeHintType.TRY_HARDER, Boolean.TRUE);
                //设置复杂模式开启(我使用这种方式就可以识别微信的二维码了)
                hints.put(DecodeHintType.PURE_BARCODE,Boolean.TYPE);
                Result result = new MultiFormatReader().decode(binaryBitmap, hints);//解码
                System.out.println("图片中内容:  ");
                System.out.println("content: " + result.getText());
                content = result.getText();
            } catch (IOException e1) {
                e1.printStackTrace();
            } catch (NotFoundException e2) {
                e2.printStackTrace();
            }
        }
        return content;
    }
}

  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

XuDream

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值