当前位置: 首页 > news >正文

Google zxing 生成带logo的二维码图片

环境准备

  • 开发环境

    • JDK 1.8
    • SpringBoot2.2.1
    • Maven 3.2+
  • 开发工具

    • IntelliJ IDEA
    • smartGit
    • Navicat15

添加maven配置

<dependency><groupId>com.google.zxing</groupId><artifactId>core</artifactId><version>3.4.0</version>
</dependency>
<dependency><groupId>com.google.zxing</groupId><artifactId>javase</artifactId><version>3.4.0</version>
</dependency>

创建比特矩阵

先创建比特矩阵,设置默认的宽度、高度、后缀名等等

 private static final String DEFAULT_CHAR_SET = "UTF-8";private static final String DEFAULT_FORMAT_NAME = "JPG";// 二维码宽度
private static final int DEFAULT_QR_CODE_WIDTH = 300;
// 二维码高度
private static final int DEFAULT_QR_CODE_HEIGHT = 300;/*** 创建BitMatrix比特矩阵* @Date 2023/09/24 22:29* @Param contents 二维码里的内容* @Param width 二维码宽度* @param height 二维码高度* @return com.google.zxing.common.BitMatrix*/
public static  BitMatrix createBitMatrix(String contents , int width , int height) throws WriterException, IOException {if (ObjectUtil.isNull(width)) {width = DEFAULT_QR_CODE_WIDTH;}if (ObjectUtil.isNull(height)) {height = DEFAULT_QR_CODE_HEIGHT;}Hashtable<EncodeHintType, Object> hints = new Hashtable<EncodeHintType, Object>();hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H); // 纠错等级L,M,Q,Hhints.put(EncodeHintType.CHARACTER_SET, DEFAULT_CHAR_SET);// 编码utf-8hints.put(EncodeHintType.MARGIN, 1);  // 边距// 创建比特矩阵BitMatrix bitMatrix = new MultiFormatWriter().encode(contents,BarcodeFormat.QR_CODE, width, height, hints);return bitMatrix;}

转换为BufferedImage

创建好比特矩阵后,转换为BufferedImage

 /*** 转换为BufferedImage* @Date 2023/09/24 22:32* @Param [bitMatrix]* @return java.awt.image.BufferedImage*/
public static BufferedImage toBufferedImage(BitMatrix bitMatrix) throws IOException, WriterException {MatrixToImageConfig matrixToImageConfig = new MatrixToImageConfig(0xFF000001, 0xFFFFFFFF);BufferedImage bufferedImage = MatrixToImageWriter.toBufferedImage(bitMatrix, matrixToImageConfig);return bufferedImage;
}

加上二维码logo

给创建的二维码BufferedImage加上logo

 /*** 给二维码添加logo* @Date 2023/09/24 22:33* @Param [bufferedImage, logoFile]* @return java.awt.image.BufferedImage*/public static BufferedImage addQrCodeLogo(BufferedImage bufferedImage, File logoFile) throws IOException {Graphics2D graphics = bufferedImage.createGraphics();int matrixWidth = bufferedImage.getWidth();int matrixHeigh = bufferedImage.getHeight();// 读取logo图片文件BufferedImage logo = ImageIO.read(logoFile);int logoWidth = logo.getWidth();int logoHeight = logo.getHeight();//  计算logo放置位置int x = bufferedImage.getWidth()  / 5*2;int y = bufferedImage.getHeight() / 5*2;int width = matrixWidth / 5;int height = matrixHeigh / 5;// 开始绘制图片graphics.drawImage(logo, x, y, width, height, null);graphics.drawRoundRect(x, y, logoWidth, logoHeight, 15, 15);graphics.setStroke(new BasicStroke(5.0F, 1, 1));graphics.setColor(Color.white);graphics.drawRect(x, y, logoWidth, logoHeight);graphics.dispose();bufferedImage.flush();return bufferedImage;}

测试

public static void main(String[] args) throws Exception {BufferedImage bufferedImage = toBufferedImage(createBitMatrix("https://blog.csdn.net", 300, 300));ImageIO.write(bufferedImage, "png", new File("D:/qrcode.jpg"));System.out.println(decodeQrCode(bufferedImage));BufferedImage logoQrCode = addQrCodeLogo(bufferedImage, new File("D://logo.png"));ImageIO.write(logoQrCode, "png", new File("D:/logoQrcode.jpg"));}

创建不带logo的二维码图片
在这里插入图片描述
创建带logo的二维码图片
在这里插入图片描述

附录

package com.example.common.util.qrcode;import cn.hutool.core.codec.Base64;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.google.zxing.*;
import com.google.zxing.client.j2se.BufferedImageLuminanceSource;
import com.google.zxing.client.j2se.MatrixToImageConfig;
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.*;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.util.Hashtable;public class QrCodeGenerator {private static final String DEFAULT_CHAR_SET = "UTF-8";private static final String DEFAULT_FORMAT_NAME = "JPG";// 二维码宽度private static final int DEFAULT_QR_CODE_WIDTH = 300;// 二维码高度private static final int DEFAULT_QR_CODE_HEIGHT = 300;/*** 创建BitMatrix比特矩阵* @Date 2023/09/24 22:29* @Param contents 二维码里的内容* @Param width 二维码宽度* @param height 二维码高度* @return com.google.zxing.common.BitMatrix*/public static  BitMatrix createBitMatrix(String contents , int width , int height) throws WriterException, IOException {if (ObjectUtil.isNull(width)) {width = DEFAULT_QR_CODE_WIDTH;}if (ObjectUtil.isNull(height)) {height = DEFAULT_QR_CODE_HEIGHT;}Hashtable<EncodeHintType, Object> hints = new Hashtable<EncodeHintType, Object>();hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H); // 纠错等级L,M,Q,Hhints.put(EncodeHintType.CHARACTER_SET, DEFAULT_CHAR_SET);// 编码utf-8hints.put(EncodeHintType.MARGIN, 1);  // 边距// 创建比特矩阵BitMatrix bitMatrix = new MultiFormatWriter().encode(contents,BarcodeFormat.QR_CODE, width, height, hints);return bitMatrix;}/*** 创建二维码,返回字节数组* @Date 2023/09/24 22:30* @Param contents 二维码里的内容* @Param imageFormat 图片后缀名* @Param width 二维码宽度* @param height 二维码高度* @return byte[]*/public static byte[] createQrCode(String contents , String imageFormat , int width , int height) throws WriterException, IOException {if (StrUtil.isBlank(imageFormat)){imageFormat = DEFAULT_FORMAT_NAME;}BitMatrix bitMatrix = createBitMatrix(contents , width, height);ByteArrayOutputStream os = new ByteArrayOutputStream();MatrixToImageWriter.writeToStream(bitMatrix, imageFormat, os);return os.toByteArray();}/*** 创建二维码,返回base64字符串* @Date 2023/09/24 22:30* @Param contents 二维码里的内容* @Param imageFormat 图片后缀名* @Param width 二维码宽度* @param height 二维码高度* @return byte[]*/public static String createQrCodeBase64(String contents , String imageFormat , int width , int height) throws WriterException, IOException {byte[] bytes =createQrCode(contents , imageFormat , width, height);return Base64.encode(bytes);}/*** 解码二维码* @Date 2023/09/24 22:32* @Param [image]* @return java.lang.String*/public static String decodeQrCode(BufferedImage image) throws Exception {if (image == null) return StrUtil.EMPTY;BufferedImageLuminanceSource source = new BufferedImageLuminanceSource(image);BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));Hashtable<DecodeHintType, Object> hints = new Hashtable<DecodeHintType, Object>();hints.put(DecodeHintType.CHARACTER_SET, DEFAULT_CHAR_SET);Result result = new MultiFormatReader().decode(bitmap, hints);return result.getText();}/*** 转换为BufferedImage* @Date 2023/09/24 22:32* @Param [bitMatrix]* @return java.awt.image.BufferedImage*/public static BufferedImage toBufferedImage(BitMatrix bitMatrix) throws IOException, WriterException {MatrixToImageConfig matrixToImageConfig = new MatrixToImageConfig(0xFF000001, 0xFFFFFFFF);BufferedImage bufferedImage = MatrixToImageWriter.toBufferedImage(bitMatrix, matrixToImageConfig);return bufferedImage;}/*** 给二维码添加logo* @Date 2023/09/24 22:33* @Param [bufferedImage, logoFile]* @return java.awt.image.BufferedImage*/public static BufferedImage addQrCodeLogo(BufferedImage bufferedImage, File logoFile) throws IOException {Graphics2D graphics = bufferedImage.createGraphics();int matrixWidth = bufferedImage.getWidth();int matrixHeigh = bufferedImage.getHeight();// 读取logo图片文件BufferedImage logo = ImageIO.read(logoFile);int logoWidth = logo.getWidth();int logoHeight = logo.getHeight();//  计算logo放置位置int x = bufferedImage.getWidth()  / 5*2;int y = bufferedImage.getHeight() / 5*2;int width = matrixWidth / 5;int height = matrixHeigh / 5;// 开始绘制图片graphics.drawImage(logo, x, y, width, height, null);graphics.drawRoundRect(x, y, logoWidth, logoHeight, 15, 15);graphics.setStroke(new BasicStroke(5.0F, 1, 1));graphics.setColor(Color.white);graphics.drawRect(x, y, logoWidth, logoHeight);graphics.dispose();bufferedImage.flush();return bufferedImage;}public static void main(String[] args) throws Exception {BufferedImage bufferedImage = toBufferedImage(createBitMatrix("https://blog.csdn.net", 300, 300));ImageIO.write(bufferedImage, "png", new File("D:/qrcode.jpg"));System.out.println(decodeQrCode(bufferedImage));BufferedImage logoQrCode = addQrCodeLogo(bufferedImage, new File("D://logo.png"));ImageIO.write(logoQrCode, "png", new File("D:/logoQrcode.jpg"));}}

相关文章:

Google zxing 生成带logo的二维码图片

环境准备 开发环境 JDK 1.8SpringBoot2.2.1Maven 3.2 开发工具 IntelliJ IDEAsmartGitNavicat15 添加maven配置 <dependency><groupId>com.google.zxing</groupId><artifactId>core</artifactId><version>3.4.0</version> </…...

使用Python计算平面多边形间最短距离

要计算平面多边形间的最短距离&#xff0c;首先需要导入Excel表格中的多边形数据&#xff0c;然后使用GJK&#xff08;Gilbert-Johnson-Keerthi&#xff09;算法来判断两个多边形是否重叠。如果两个多边形不重叠&#xff0c;可以计算它们之间的最短距离。 以下是一个基本的Pyt…...

【Python】Python语言基础(中)

第十章 Python的数据类型 基本数据类型 数字 整数 整数就是整数 浮点数 在编程中&#xff0c;小数都称之为浮点数 浮点数的精度问题 print(0.1 0.2) --------------- 0.30000000000000004 ​​1.可以通过round()函数来控制小数点后位数 round(a b)&#xff0c;则表示…...

观察者模式、订阅者发布者模式、vtk中的观察者模式

文章目录 什么是观察者模式vtk是如何实现的观察者模式.AddObserver什么时候使用观察者模式&#xff1f;什么使用订阅发布者模式?观察者模式的实现订阅发布者的实现总结知识补充: 什么是观察者模式 用于在对象之间建立一对多的依赖关系&#xff0c;当一个对象的状态发生变化时…...

关于element-ui中,页面上有多个el-table并通过v-if、v-else等控制是否显示时,type=selection勾选框失效或不显示的问题

刚开始是勾选框那一列直接空了什么都不显示&#xff0c;搜索了一下说是给el-table标签增加id&#xff0c;加了之后是显示了&#xff0c;但是点击任何选框都会直接取消全部选中效果&#xff0c;翻了半天源码也没发现到底是哪里事件冲突了还是怎么回事&#xff0c;烦了&#xff0…...

Stewart六自由度正解、逆解计算-C#和Matlab程序

目录 一、Stewart并联六自由度正解计算 &#xff08;一&#xff09;概况 &#xff08;二&#xff09;Matlab正解计算 1、参考程序一 2、参考程序二 &#xff08;三&#xff09;C#程序正解计算 1、工程下载链接 2、正解运行计算 &#xff08;四&#xff09;正程…...

C语言 驼峰命名法和下划线命名法

在C语言中&#xff0c;变量命名遵循以下规则&#xff1a; 变量名只能由字母、数字和下划线组成。变量名必须以字母或下划线开头。变量名不能使用C语言中的关键字。变量名中不能出现连续的两个下划线。变量名区分大小写&#xff0c;例如&#xff0c;count和Count被视为两个不同…...

大数据学习(8)-hive压缩

&&大数据学习&& &#x1f525;系列专栏&#xff1a; &#x1f451;哲学语录: 承认自己的无知&#xff0c;乃是开启智慧的大门 &#x1f496;如果觉得博主的文章还不错的话&#xff0c;请点赞&#x1f44d;收藏⭐️留言&#x1f4dd;支持一下博>主哦&#x…...

[sqoop]hive导入mysql,其中mysql的列存在默认值列

一、思路 直接在hive表中去掉有默认值的了列&#xff0c;在sqoop导入时,指定非默认值列即可&#xff0c; 二、具体 mysql的表 hive的表 create table dwd.dwd_hk_rcp_literature(id string,literature_no string,authors string,article_title string,source_title string…...

Stream流中的常用方法(forEach,filter,map,count,limit,skip,concat)和Stream流的特点

1、forEach方法 该方法接收一个Consumer接口是一个 消费型 的函数式接口&#xff0c;可以传递Lambda表达式&#xff0c;消费数据用来遍历流中的数据&#xff0c;是一个 终结 方法&#xff0c;遍历 之后就不能继续调用Stream流中的其他方法 package com.csdn.stream; import jav…...

2023大联盟2比赛总结

比赛链接 反思 T1 奇怪的贪心和构造题一直是我的软肋部分 T2 简单题 T3 也不难 T4 套路没学过&#xff0c;感觉还是太菜了 题解 A 考虑先给图随便染色&#xff0c;然后调整 因为每个点的度数为 3 3 3&#xff0c;所以如果有 x → u → v x\to u\to v x→u→v 的颜…...

Flutter笔记:电商中文货币显示插件Money Display

Flutter笔记 电商中文货币显示插件 Money Display 作者&#xff1a;李俊才 &#xff08;jcLee95&#xff09;&#xff1a;https://blog.csdn.net/qq_28550263 邮箱 &#xff1a;291148484163.com 本文地址&#xff1a;https://blog.csdn.net/qq_28550263/article/details/1338…...

腾讯云上创建 对象存储cos

1. 登录腾讯云, 找到对象存储cos 2. 创建存储桶 3. 获取4个配置参数 桶名称 / 地域secretId / secretKey...

微信小程序生成海报

效果: js1: const cloudHelper = require(../../../helper/cloud_helper.js);async function config1({cover,title,desc,qr,bg = }) {var qr1 ="images/qr.png"var qr2 ="https://636c-cloud1-0gu29f2j63906b7e-1319556650.tcb.qcloud.la/activitycomm/setu…...

stm32学习笔记:EXIT中断

1、中断系统 中断系统是管理和执行中断的逻辑结构&#xff0c;外部中断是众多能产生中断的外设之一。 1.中断&#xff1a; 在主程序运行过程中&#xff0c;出现了特定的中断触发条件 (中断源&#xff0c;如对于外部中断来说可以是引脚发生了电平跳变&#xff0c;对于定时器来…...

css 块元素、行内元素、行内块元素相互转换

在HTML和CSS中&#xff0c;元素可以分为三类&#xff1a;块级元素&#xff08;Block-level Elements&#xff09;、内联元素&#xff08;Inline Elements&#xff09;和内联块级元素&#xff08;Inline-block Elements&#xff09;。 块级元素&#xff08;Block-level Elements…...

【JUC】多线程基础概述

文章目录 1. 一锁二并三程2. 用户线程和守护线程 1. 一锁二并三程 一锁&#xff1a;synchronized 二并: 并发&#xff1a;一台处理器“同时”处理多个任务&#xff0c;同一时刻只有一个事件发生并行&#xff1a;多台处理器同时处理多个任务&#xff0c;同一时刻多个处理器分…...

Git 回退代码的两种方法对比

Git 回退代码版本 在项目的开发中&#xff0c;有时候还是会出现&#xff0c;一些误提交了一些代码&#xff0c;这时候就会想撤回提交的代码&#xff0c;在Git中有两种方法可以使用&#xff0c;现在通过对比方法比较这两种方法的区别&#xff0c;分别适用于哪些情况&#xff1f…...

Avalonia常用小控件Charts

1.项目下载地址&#xff1a;https://gitee.com/confusedkitten/avalonia-demo 2.UI库Semi.Avalonia&#xff0c;项目地址 https://github.com/irihitech/Semi.Avalonia 3.Charts库&#xff0c;LiveChartsCore.SkiaSharpView.Avalonia&#xff0c;Nuget获取只有预览库&#x…...

【Hugging Face】管理 huggingface_hub 缓存系统

摘要 这篇文档介绍了Hugging Face Hub的缓存系统。该系统旨在提供一个中央缓存,以便不同版本的文件可以被下载和缓存。缓存系统将文件组织成模型、数据集和空间等不同的目录,每个目录包含特定类型的文件。系统确保如果文件已经下载并更新,除非明确要求,否则不会再次下载。…...

反向工程与模型迁移:打造未来商品详情API的可持续创新体系

在电商行业蓬勃发展的当下&#xff0c;商品详情API作为连接电商平台与开发者、商家及用户的关键纽带&#xff0c;其重要性日益凸显。传统商品详情API主要聚焦于商品基本信息&#xff08;如名称、价格、库存等&#xff09;的获取与展示&#xff0c;已难以满足市场对个性化、智能…...

R语言AI模型部署方案:精准离线运行详解

R语言AI模型部署方案:精准离线运行详解 一、项目概述 本文将构建一个完整的R语言AI部署解决方案,实现鸢尾花分类模型的训练、保存、离线部署和预测功能。核心特点: 100%离线运行能力自包含环境依赖生产级错误处理跨平台兼容性模型版本管理# 文件结构说明 Iris_AI_Deployme…...

为什么需要建设工程项目管理?工程项目管理有哪些亮点功能?

在建筑行业&#xff0c;项目管理的重要性不言而喻。随着工程规模的扩大、技术复杂度的提升&#xff0c;传统的管理模式已经难以满足现代工程的需求。过去&#xff0c;许多企业依赖手工记录、口头沟通和分散的信息管理&#xff0c;导致效率低下、成本失控、风险频发。例如&#…...

Linux简单的操作

ls ls 查看当前目录 ll 查看详细内容 ls -a 查看所有的内容 ls --help 查看方法文档 pwd pwd 查看当前路径 cd cd 转路径 cd .. 转上一级路径 cd 名 转换路径 …...

剑指offer20_链表中环的入口节点

链表中环的入口节点 给定一个链表&#xff0c;若其中包含环&#xff0c;则输出环的入口节点。 若其中不包含环&#xff0c;则输出null。 数据范围 节点 val 值取值范围 [ 1 , 1000 ] [1,1000] [1,1000]。 节点 val 值各不相同。 链表长度 [ 0 , 500 ] [0,500] [0,500]。 …...

如何将联系人从 iPhone 转移到 Android

从 iPhone 换到 Android 手机时&#xff0c;你可能需要保留重要的数据&#xff0c;例如通讯录。好在&#xff0c;将通讯录从 iPhone 转移到 Android 手机非常简单&#xff0c;你可以从本文中学习 6 种可靠的方法&#xff0c;确保随时保持连接&#xff0c;不错过任何信息。 第 1…...

如何更改默认 Crontab 编辑器 ?

在 Linux 领域中&#xff0c;crontab 是您可能经常遇到的一个术语。这个实用程序在类 unix 操作系统上可用&#xff0c;用于调度在预定义时间和间隔自动执行的任务。这对管理员和高级用户非常有益&#xff0c;允许他们自动执行各种系统任务。 编辑 Crontab 文件通常使用文本编…...

Webpack性能优化:构建速度与体积优化策略

一、构建速度优化 1、​​升级Webpack和Node.js​​ ​​优化效果​​&#xff1a;Webpack 4比Webpack 3构建时间降低60%-98%。​​原因​​&#xff1a; V8引擎优化&#xff08;for of替代forEach、Map/Set替代Object&#xff09;。默认使用更快的md4哈希算法。AST直接从Loa…...

从 GreenPlum 到镜舟数据库:杭银消费金融湖仓一体转型实践

作者&#xff1a;吴岐诗&#xff0c;杭银消费金融大数据应用开发工程师 本文整理自杭银消费金融大数据应用开发工程师在StarRocks Summit Asia 2024的分享 引言&#xff1a;融合数据湖与数仓的创新之路 在数字金融时代&#xff0c;数据已成为金融机构的核心竞争力。杭银消费金…...

python爬虫——气象数据爬取

一、导入库与全局配置 python 运行 import json import datetime import time import requests from sqlalchemy import create_engine import csv import pandas as pd作用&#xff1a; 引入数据解析、网络请求、时间处理、数据库操作等所需库。requests&#xff1a;发送 …...