From c9f33e594946c886076c7fd8de424f2f92331f8d Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Sun, 21 Aug 2022 02:53:13 +0800 Subject: [PATCH 01/10] =?UTF-8?q?=E7=BB=99QrCodeUtil=E6=B7=BB=E5=8A=A0?= =?UTF-8?q?=E7=94=9F=E6=88=90SVG=E6=A0=BC=E5=BC=8F=E4=BA=8C=E7=BB=B4?= =?UTF-8?q?=E7=A0=81=E7=9A=84=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/extra/qrcode/QrCodeUtil.java | 79 ++++++++++++++++++- .../hutool/extra/qrcode/QrCodeUtilTest.java | 9 +++ 2 files changed, 86 insertions(+), 2 deletions(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java index 36e048d2b..c5a0f5780 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java @@ -4,6 +4,7 @@ import cn.hutool.core.codec.Base64; import cn.hutool.core.img.Img; import cn.hutool.core.img.ImgUtil; import cn.hutool.core.util.CharsetUtil; +import cn.hutool.core.util.StrUtil; import com.google.zxing.BarcodeFormat; import com.google.zxing.Binarizer; import com.google.zxing.BinaryBitmap; @@ -18,8 +19,7 @@ import com.google.zxing.common.BitMatrix; import com.google.zxing.common.GlobalHistogramBinarizer; import com.google.zxing.common.HybridBinarizer; -import java.awt.Image; -import java.awt.Rectangle; +import java.awt.*; import java.awt.image.BufferedImage; import java.io.ByteArrayOutputStream; import java.io.File; @@ -97,6 +97,17 @@ public class QrCodeUtil { return ImgUtil.toBase64DataUri(img, imageType); } + /** + * @param content 内容 + * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 + * @return SVG矢量图(字符串) + * @since 5.8.6 + */ + public static String generateAsSvg(String content, QrConfig qrConfig) { + BitMatrix bitMatrix = encode(content, qrConfig); + return toSVG(bitMatrix, qrConfig); + } + /** * 生成PNG格式的二维码图片,以byte[]形式表示 * @@ -420,6 +431,70 @@ public class QrCodeUtil { return image; } + /** + * @param matrix BitMatrix + * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 + * @return SVG矢量图(字符串) + * @since 5.8.6 + */ + public static String toSVG(BitMatrix matrix,QrConfig qrConfig) { + return toSVG(matrix, qrConfig.getForeColor(), qrConfig.getBackColor(),qrConfig.img,qrConfig.getRatio()); + } + + /** + * BitMatrix转SVG(字符串) + * + * @param matrix BitMatrix + * @param foreColor 前景色 + * @param backColor 背景色(null表示透明背景) + * @param ratio 二维码中的Logo缩放的比例系数,如5表示长宽最小值的1/5 + * @return SVG矢量图(字符串) + * @since 5.8.6 + */ + public static String toSVG(BitMatrix matrix,int foreColor, Integer backColor,Image logoImg,int ratio) { + StringBuilder sb = new StringBuilder(); + int qrWidth = matrix.getWidth(); + int qrHeight = matrix.getHeight(); + int moduleHeight = (qrHeight == 1) ? qrWidth / 2 : 1; + for (int y = 0; y < qrHeight; y++) { + for (int x = 0; x < qrWidth; x++) { + if (matrix.get(x, y)) { + sb.append(" M" + x + "," + y + "h1v" + moduleHeight + "h-1z"); + } + } + } + qrHeight *= moduleHeight; + String logoBase64 = ""; + int logoWidth = 0; + int logoHeight = 0; + int logoX = 0; + int logoY = 0; + if (logoImg != null) { + logoBase64 = ImgUtil.toBase64DataUri(logoImg, "png"); + // 按照最短的边做比例缩放 + if (qrWidth < qrHeight) { + logoWidth = qrWidth / ratio; + logoHeight = logoImg.getHeight(null) * logoWidth / logoImg.getWidth(null); + } else { + logoHeight = qrHeight / ratio; + logoWidth = logoImg.getWidth(null) * logoHeight / logoImg.getHeight(null); + } + logoX = (qrWidth - logoWidth) / 2; + logoY = (qrHeight - logoHeight) / 2; + + } + Color fore = new Color(foreColor, true); + Color back = new Color(backColor, true); + return "\n" + + " \n" + + (StrUtil.isBlank(logoBase64) ? "" : "\n") + + ""; + } + /** * 创建解码选项 * diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index 735f15db3..04ab35dcf 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -5,6 +5,7 @@ import cn.hutool.core.img.ImgUtil; import cn.hutool.core.io.FileUtil; import cn.hutool.core.lang.Console; import com.google.zxing.BarcodeFormat; +import com.google.zxing.common.BitMatrix; import com.google.zxing.datamatrix.encoder.SymbolShapeHint; import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel; import org.junit.Assert; @@ -14,6 +15,7 @@ import org.junit.Test; import java.awt.Color; import java.awt.image.BufferedImage; import java.io.File; +import java.nio.charset.StandardCharsets; /** * 二维码工具类单元测试 @@ -108,5 +110,12 @@ public class QrCodeUtilTest { Assert.assertNotNull(imageSquare); } + @Test + public void generateSvgTest() { + QrConfig qrConfig = QrConfig.create().setImg("d:/test/logo.png").setForeColor(Color.GREEN).setBackColor(Color.pink); + String svg = QrCodeUtil.generateAsSvg("https://hutool.cn/", qrConfig); + Assert.assertNotNull(svg); + FileUtil.writeString(svg, "d:/test/qr.svg", StandardCharsets.UTF_8); + } } From 7a233005e8738349671d750fe5d7ac4e531ae281 Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Sun, 21 Aug 2022 03:54:33 +0800 Subject: [PATCH 02/10] =?UTF-8?q?=E7=BB=99QrCodeUtil=E6=B7=BB=E5=8A=A0?= =?UTF-8?q?=E7=94=9F=E6=88=90Ascii=20Art=E5=AD=97=E7=AC=A6=E7=94=BB?= =?UTF-8?q?=E6=A0=BC=E5=BC=8F=E4=BA=8C=E7=BB=B4=E7=A0=81=E7=9A=84=E5=8A=9F?= =?UTF-8?q?=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/extra/qrcode/QrCodeUtil.java | 61 +++++++++++++++++++ .../hutool/extra/qrcode/QrCodeUtilTest.java | 8 +++ 2 files changed, 69 insertions(+) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java index c5a0f5780..53da5235f 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java @@ -108,6 +108,38 @@ public class QrCodeUtil { return toSVG(bitMatrix, qrConfig); } + /** + * @param content 内容 + * @return ASCII Art字符画形式的二维码 + * @since 5.8.6 + */ + public static String generateAsAsciiArt(String content) { + return generateAsAsciiArt(content, 0,0,1); + } + /** + * @param content 内容 + * @param qrConfig 二维码配置,仅长、宽、边距配置有效 + * @return ASCII Art字符画形式的二维码 + * @since 5.8.6 + */ + public static String generateAsAsciiArt(String content, QrConfig qrConfig) { + BitMatrix bitMatrix = encode(content, qrConfig); + return toAsciiArt(bitMatrix); + } + + /** + * @param content 内容 + * @param width 宽 + * @param height 长 + * @return ASCII Art字符画形式的二维码 + * @since 5.8.6 + */ + public static String generateAsAsciiArt(String content,int width, int height,int margin) { + QrConfig qrConfig = new QrConfig(width, height).setMargin(margin); + return generateAsAsciiArt( content, qrConfig); + } + + /** * 生成PNG格式的二维码图片,以byte[]形式表示 * @@ -495,6 +527,35 @@ public class QrCodeUtil { ""; } + /** + * @param bitMatrix + * @return ASCII Art字符画形式的二维码 + * @since 5.8.6 + */ + public static String toAsciiArt(BitMatrix bitMatrix) { + int width = bitMatrix.getWidth(); + int height = bitMatrix.getHeight(); + StringBuilder result = new StringBuilder(height * (width + 1)); + for (int i = 0; i <= height; i += 2) { + for (int j = 0; j < width; j++) { + boolean tp = bitMatrix.get(i, j); + boolean bt = i + 1 >= height || bitMatrix.get(i + 1, j); + if (tp && bt) { + result.append(' ');//'\u0020' + } else if (tp) { + result.append('▄');//'\u2584' + } else if (bt) { + result.append('▀');//'\u2580' + } else { + result.append('█');//'\u2588' + } + + } + result.append('\n'); + } + return result.toString(); + } + /** * 创建解码选项 * diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index 04ab35dcf..9a13e58eb 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -118,4 +118,12 @@ public class QrCodeUtilTest { FileUtil.writeString(svg, "d:/test/qr.svg", StandardCharsets.UTF_8); } + @Test + public void generateAsciiArtTest() { + QrConfig qrConfig = QrConfig.create(); + String asciiArt = QrCodeUtil.generateAsAsciiArt("https://hutool.cn/呱呱呱呱呱呱呱呱呱呱呱呱呱呱呱古古怪怪"); + Assert.assertNotNull(asciiArt); + System.out.println(asciiArt); + } + } From b5b1418c3e49ffdea2e23ed1a8952bf42bcc0b4a Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Sun, 21 Aug 2022 21:43:15 +0800 Subject: [PATCH 03/10] =?UTF-8?q?=E4=BC=98=E5=8C=96=E7=94=9F=E6=88=90Ascii?= =?UTF-8?q?Art=E5=AD=97=E7=AC=A6=E7=94=BB=E4=BA=8C=E7=BB=B4=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/extra/qrcode/QrCodeUtil.java | 90 +++++++++++++------ .../hutool/extra/qrcode/QrCodeUtilTest.java | 15 +++- 2 files changed, 77 insertions(+), 28 deletions(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java index 53da5235f..287af4595 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java @@ -3,7 +3,9 @@ package cn.hutool.extra.qrcode; import cn.hutool.core.codec.Base64; import cn.hutool.core.img.Img; import cn.hutool.core.img.ImgUtil; +import cn.hutool.core.lang.ansi.*; import cn.hutool.core.util.CharsetUtil; +import cn.hutool.core.util.NumberUtil; import cn.hutool.core.util.StrUtil; import com.google.zxing.BarcodeFormat; import com.google.zxing.Binarizer; @@ -98,8 +100,8 @@ public class QrCodeUtil { } /** - * @param content 内容 - * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 + * @param content 内容 + * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 * @return SVG矢量图(字符串) * @since 5.8.6 */ @@ -109,34 +111,39 @@ public class QrCodeUtil { } /** + * 生成ASCII Art字符画形式的二维码 + * * @param content 内容 - * @return ASCII Art字符画形式的二维码 + * @return ASCII Art字符画形式的二维码字符串 * @since 5.8.6 */ public static String generateAsAsciiArt(String content) { - return generateAsAsciiArt(content, 0,0,1); + return generateAsAsciiArt(content, 0, 0, 1); } + /** - * @param content 内容 + * 生成ASCII Art字符画形式的二维码 + * + * @param content 内容 * @param qrConfig 二维码配置,仅长、宽、边距配置有效 * @return ASCII Art字符画形式的二维码 * @since 5.8.6 */ public static String generateAsAsciiArt(String content, QrConfig qrConfig) { BitMatrix bitMatrix = encode(content, qrConfig); - return toAsciiArt(bitMatrix); + return toAsciiArt(bitMatrix, qrConfig); } /** * @param content 内容 - * @param width 宽 - * @param height 长 + * @param width 宽 + * @param height 长 * @return ASCII Art字符画形式的二维码 * @since 5.8.6 */ - public static String generateAsAsciiArt(String content,int width, int height,int margin) { + public static String generateAsAsciiArt(String content, int width, int height, int margin) { QrConfig qrConfig = new QrConfig(width, height).setMargin(margin); - return generateAsAsciiArt( content, qrConfig); + return generateAsAsciiArt(content, qrConfig); } @@ -464,13 +471,15 @@ public class QrCodeUtil { } /** - * @param matrix BitMatrix - * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 + * BitMatrix转SVG(字符串) + * + * @param matrix BitMatrix + * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 * @return SVG矢量图(字符串) * @since 5.8.6 */ - public static String toSVG(BitMatrix matrix,QrConfig qrConfig) { - return toSVG(matrix, qrConfig.getForeColor(), qrConfig.getBackColor(),qrConfig.img,qrConfig.getRatio()); + public static String toSVG(BitMatrix matrix, QrConfig qrConfig) { + return toSVG(matrix, qrConfig.getForeColor(), qrConfig.getBackColor(), qrConfig.img, qrConfig.getRatio()); } /** @@ -479,11 +488,11 @@ public class QrCodeUtil { * @param matrix BitMatrix * @param foreColor 前景色 * @param backColor 背景色(null表示透明背景) - * @param ratio 二维码中的Logo缩放的比例系数,如5表示长宽最小值的1/5 + * @param ratio 二维码中的Logo缩放的比例系数,如5表示长宽最小值的1/5 * @return SVG矢量图(字符串) * @since 5.8.6 */ - public static String toSVG(BitMatrix matrix,int foreColor, Integer backColor,Image logoImg,int ratio) { + public static String toSVG(BitMatrix matrix, int foreColor, Integer backColor, Image logoImg, int ratio) { StringBuilder sb = new StringBuilder(); int qrWidth = matrix.getWidth(); int qrHeight = matrix.getHeight(); @@ -528,34 +537,65 @@ public class QrCodeUtil { } /** + * BitMatrix转ASCII Art字符画形式的二维码 + * * @param bitMatrix * @return ASCII Art字符画形式的二维码 * @since 5.8.6 */ - public static String toAsciiArt(BitMatrix bitMatrix) { + public static String toAsciiArt(BitMatrix bitMatrix, QrConfig qrConfig) { int width = bitMatrix.getWidth(); int height = bitMatrix.getHeight(); - StringBuilder result = new StringBuilder(height * (width + 1)); + + AnsiElement foreground = Ansi8BitColor.foreground(rgbToAnsi8BitValue(qrConfig.getForeColor())); + AnsiElement background = Ansi8BitColor.background(rgbToAnsi8BitValue(qrConfig.getBackColor())); + + StringBuilder builder = new StringBuilder(); for (int i = 0; i <= height; i += 2) { + StringBuilder rowBuilder = new StringBuilder(); for (int j = 0; j < width; j++) { boolean tp = bitMatrix.get(i, j); boolean bt = i + 1 >= height || bitMatrix.get(i + 1, j); if (tp && bt) { - result.append(' ');//'\u0020' + rowBuilder.append(' ');//'\u0020' } else if (tp) { - result.append('▄');//'\u2584' + rowBuilder.append('▄');//'\u2584' } else if (bt) { - result.append('▀');//'\u2580' + rowBuilder.append('▀');//'\u2580' } else { - result.append('█');//'\u2588' + rowBuilder.append('█');//'\u2588' } - } - result.append('\n'); + builder.append(AnsiEncoder.encode(foreground, background, rowBuilder)).append('\n'); } - return result.toString(); + return builder.toString(); } + /** + * rgb转Ansi8Bit值 + * + * @param rgb rgb颜色值 + * @return Ansi8bit颜色值 + * @since 5.8.6 + */ + private static int rgbToAnsi8BitValue(int rgb) { + int l; + int r = (rgb >> 16) & 0xff; + int g = (rgb >> 8) & 0xff; + int b = (rgb) & 0xff; + if (r < 0) r += 256; + if (g < 0) g += 256; + if (b < 0) b += 256; + if (r == g && g == b) { + int i = (int) (NumberUtil.div(NumberUtil.mul(r - 10.625, 23), (255 - 10.625), 0)); + l = i >= 0 ? 232 + i : 0; + } else { + l = 16 + (int) (36 * NumberUtil.div(NumberUtil.mul(r, 5), 255, 0)) + (int) (6.0 * (g / 256.0 * 6.0)) + (int) (b / 256.0 * 6.0); + } + return l; + } + + /** * 创建解码选项 * diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index 9a13e58eb..799e23361 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -4,6 +4,8 @@ import cn.hutool.core.codec.Base64; import cn.hutool.core.img.ImgUtil; import cn.hutool.core.io.FileUtil; import cn.hutool.core.lang.Console; +import cn.hutool.core.lang.ansi.Ansi8BitColor; +import cn.hutool.core.lang.ansi.AnsiEncoder; import com.google.zxing.BarcodeFormat; import com.google.zxing.common.BitMatrix; import com.google.zxing.datamatrix.encoder.SymbolShapeHint; @@ -112,7 +114,10 @@ public class QrCodeUtilTest { @Test public void generateSvgTest() { - QrConfig qrConfig = QrConfig.create().setImg("d:/test/logo.png").setForeColor(Color.GREEN).setBackColor(Color.pink); + QrConfig qrConfig = QrConfig.create().setImg("d:/test/logo.png") + .setForeColor(Color.GREEN) + .setBackColor(Color.pink) + .setMargin(1); String svg = QrCodeUtil.generateAsSvg("https://hutool.cn/", qrConfig); Assert.assertNotNull(svg); FileUtil.writeString(svg, "d:/test/qr.svg", StandardCharsets.UTF_8); @@ -120,8 +125,12 @@ public class QrCodeUtilTest { @Test public void generateAsciiArtTest() { - QrConfig qrConfig = QrConfig.create(); - String asciiArt = QrCodeUtil.generateAsAsciiArt("https://hutool.cn/呱呱呱呱呱呱呱呱呱呱呱呱呱呱呱古古怪怪"); + QrConfig qrConfig = QrConfig.create() + .setForeColor(new Color(0,255,0)) + .setBackColor(new Color(0,0,0)) + .setWidth(0) + .setHeight(0).setMargin(1); + String asciiArt = QrCodeUtil.generateAsAsciiArt("https://hutool.cn/",qrConfig); Assert.assertNotNull(asciiArt); System.out.println(asciiArt); } From ea06be85e9d0f2a437475c30c8046d476a6b2f0e Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Sun, 21 Aug 2022 23:31:18 +0800 Subject: [PATCH 04/10] =?UTF-8?q?=E4=BC=98=E5=8C=96=E7=94=9F=E6=88=90Ascii?= =?UTF-8?q?Art=E5=AD=97=E7=AC=A6=E7=94=BB=E4=BA=8C=E7=BB=B4=E7=A0=81?= =?UTF-8?q?=E3=80=81SVG=E4=BA=8C=E7=BB=B4=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/extra/qrcode/QrCodeUtil.java | 137 +++++++++++++----- .../java/cn/hutool/extra/qrcode/QrConfig.java | 2 +- .../hutool/extra/qrcode/QrCodeUtilTest.java | 44 +++++- 3 files changed, 135 insertions(+), 48 deletions(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java index 287af4595..75448c727 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java @@ -3,20 +3,15 @@ package cn.hutool.extra.qrcode; import cn.hutool.core.codec.Base64; import cn.hutool.core.img.Img; import cn.hutool.core.img.ImgUtil; -import cn.hutool.core.lang.ansi.*; +import cn.hutool.core.io.FileUtil; +import cn.hutool.core.io.IoUtil; +import cn.hutool.core.lang.ansi.Ansi8BitColor; +import cn.hutool.core.lang.ansi.AnsiElement; +import cn.hutool.core.lang.ansi.AnsiEncoder; import cn.hutool.core.util.CharsetUtil; import cn.hutool.core.util.NumberUtil; import cn.hutool.core.util.StrUtil; -import com.google.zxing.BarcodeFormat; -import com.google.zxing.Binarizer; -import com.google.zxing.BinaryBitmap; -import com.google.zxing.DecodeHintType; -import com.google.zxing.LuminanceSource; -import com.google.zxing.MultiFormatReader; -import com.google.zxing.MultiFormatWriter; -import com.google.zxing.NotFoundException; -import com.google.zxing.Result; -import com.google.zxing.WriterException; +import com.google.zxing.*; import com.google.zxing.common.BitMatrix; import com.google.zxing.common.GlobalHistogramBinarizer; import com.google.zxing.common.HybridBinarizer; @@ -27,6 +22,7 @@ import java.io.ByteArrayOutputStream; import java.io.File; import java.io.InputStream; import java.io.OutputStream; +import java.nio.charset.StandardCharsets; import java.util.HashMap; import java.util.Map; @@ -42,6 +38,9 @@ import java.util.Map; */ public class QrCodeUtil { + public static final String QR_TYPE_SVG = "svg";// SVG矢量图格式 + public static final String QR_TYPE_TXT = "txt";// Ascii Art字符画文本 + /** * 生成代 logo 图片的 Base64 编码格式的二维码,以 String 形式表示 * @@ -186,8 +185,22 @@ public class QrCodeUtil { * @return 目标文件 */ public static File generate(String content, int width, int height, File targetFile) { - final BufferedImage image = generate(content, width, height); - ImgUtil.write(image, targetFile); + String extName = FileUtil.extName(targetFile); + switch (extName) { + case QR_TYPE_SVG: + String svg = generateAsSvg(content, new QrConfig(width, height)); + FileUtil.writeString(svg, targetFile, StandardCharsets.UTF_8); + break; + case QR_TYPE_TXT: + String txt = generateAsAsciiArt(content, new QrConfig(width, height)); + FileUtil.writeString(txt, targetFile, StandardCharsets.UTF_8); + break; + default: + final BufferedImage image = generate(content, width, height); + ImgUtil.write(image, targetFile); + break; + } + return targetFile; } @@ -201,23 +214,48 @@ public class QrCodeUtil { * @since 4.1.2 */ public static File generate(String content, QrConfig config, File targetFile) { - final BufferedImage image = generate(content, config); - ImgUtil.write(image, targetFile); + String extName = FileUtil.extName(targetFile); + switch (extName) { + case QR_TYPE_SVG: + final String svg = generateAsSvg(content, config); + FileUtil.writeString(svg, targetFile, StandardCharsets.UTF_8); + break; + case QR_TYPE_TXT: + final String txt = generateAsAsciiArt(content, config); + FileUtil.writeString(txt, targetFile, StandardCharsets.UTF_8); + break; + default: + final BufferedImage image = generate(content, config); + ImgUtil.write(image, targetFile); + break; + } return targetFile; } /** * 生成二维码到输出流 * - * @param content 文本内容 - * @param width 宽度 - * @param height 高度 - * @param imageType 图片类型(图片扩展名),见{@link ImgUtil} - * @param out 目标流 + * @param content 文本内容 + * @param width 宽度 + * @param height 高度 + * @param targetType 类型(图片扩展名),见{@link #QR_TYPE_SVG}、 {@link #QR_TYPE_TXT}、{@link ImgUtil} + * @param out 目标流 */ - public static void generate(String content, int width, int height, String imageType, OutputStream out) { - final BufferedImage image = generate(content, width, height); - ImgUtil.write(image, imageType, out); + public static void generate(String content, int width, int height, String targetType, OutputStream out) { + switch (targetType) { + case QR_TYPE_SVG: + final String svg = generateAsSvg(content, new QrConfig(width, height)); + IoUtil.writeUtf8(out, false, svg); + break; + case QR_TYPE_TXT: + final String txt = generateAsAsciiArt(content, new QrConfig(width, height)); + IoUtil.writeUtf8(out, false, txt); + break; + default: + final BufferedImage image = generate(content, width, height); + ImgUtil.write(image, targetType, out); + break; + } } /** @@ -225,13 +263,25 @@ public class QrCodeUtil { * * @param content 文本内容 * @param config 二维码配置,包括长、宽、边距、颜色等 - * @param imageType 图片类型(图片扩展名),见{@link ImgUtil} + * @param targetType 类型(图片扩展名),见{@link #QR_TYPE_SVG}、 {@link #QR_TYPE_TXT}、{@link ImgUtil} * @param out 目标流 * @since 4.1.2 */ - public static void generate(String content, QrConfig config, String imageType, OutputStream out) { - final BufferedImage image = generate(content, config); - ImgUtil.write(image, imageType, out); + public static void generate(String content, QrConfig config, String targetType, OutputStream out) { + switch (targetType) { + case QR_TYPE_SVG: + final String svg = generateAsSvg(content, config); + IoUtil.writeUtf8(out, false, svg); + break; + case QR_TYPE_TXT: + final String txt = generateAsAsciiArt(content, config); + IoUtil.writeUtf8(out, false, txt); + break; + default: + final BufferedImage image = generate(content, config); + ImgUtil.write(image, targetType, out); + break; + } } /** @@ -479,7 +529,7 @@ public class QrCodeUtil { * @since 5.8.6 */ public static String toSVG(BitMatrix matrix, QrConfig qrConfig) { - return toSVG(matrix, qrConfig.getForeColor(), qrConfig.getBackColor(), qrConfig.img, qrConfig.getRatio()); + return toSVG(matrix, qrConfig.foreColor, qrConfig.backColor, qrConfig.img, qrConfig.getRatio()); } /** @@ -524,16 +574,24 @@ public class QrCodeUtil { logoY = (qrHeight - logoHeight) / 2; } + Color fore = new Color(foreColor, true); - Color back = new Color(backColor, true); - return "\n" + - " \n" + - (StrUtil.isBlank(logoBase64) ? "" : "\n") + - ""; + + StringBuilder result = StrUtil.builder(); + result.append("\n"); + result.append(" \n"); + if (StrUtil.isNotBlank(logoBase64)) { + result.append("\n"); + } + result.append(""); + return result.toString(); } /** @@ -547,8 +605,9 @@ public class QrCodeUtil { int width = bitMatrix.getWidth(); int height = bitMatrix.getHeight(); - AnsiElement foreground = Ansi8BitColor.foreground(rgbToAnsi8BitValue(qrConfig.getForeColor())); - AnsiElement background = Ansi8BitColor.background(rgbToAnsi8BitValue(qrConfig.getBackColor())); + + AnsiElement foreground = qrConfig.foreColor == null ? null : Ansi8BitColor.foreground(rgbToAnsi8BitValue(qrConfig.foreColor)); + AnsiElement background = qrConfig.backColor == null ? null : Ansi8BitColor.background(rgbToAnsi8BitValue(qrConfig.backColor)); StringBuilder builder = new StringBuilder(); for (int i = 0; i <= height; i += 2) { diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java index 91675cc16..4d5a388d8 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java @@ -30,7 +30,7 @@ public class QrConfig { /** 长 */ protected int height; /** 前景色(二维码颜色) */ - protected int foreColor = BLACK; + protected Integer foreColor = BLACK; /** 背景色,默认白色,null表示透明 */ protected Integer backColor = WHITE; /** 边距1~4 */ diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index 799e23361..ab07bde11 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -4,19 +4,19 @@ import cn.hutool.core.codec.Base64; import cn.hutool.core.img.ImgUtil; import cn.hutool.core.io.FileUtil; import cn.hutool.core.lang.Console; -import cn.hutool.core.lang.ansi.Ansi8BitColor; -import cn.hutool.core.lang.ansi.AnsiEncoder; import com.google.zxing.BarcodeFormat; -import com.google.zxing.common.BitMatrix; import com.google.zxing.datamatrix.encoder.SymbolShapeHint; import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel; import org.junit.Assert; import org.junit.Ignore; import org.junit.Test; -import java.awt.Color; +import java.awt.*; import java.awt.image.BufferedImage; +import java.io.BufferedOutputStream; +import java.io.BufferedReader; import java.io.File; +import java.io.IOException; import java.nio.charset.StandardCharsets; /** @@ -41,7 +41,7 @@ public class QrCodeUtilTest { // 背景色透明 config.setBackColor(null); config.setErrorCorrection(ErrorCorrectionLevel.H); - String path = FileUtil.isWindows() ? "d:/test/qrcodeCustom.png" : "~/Desktop/hutool/qrcodeCustom.png"; + String path = FileUtil.isWindows() ? "d:/test/qrcodeCustom.txt" : "~/Desktop/hutool/qrcodeCustom.svg"; QrCodeUtil.generate("https://hutool.cn/", config, FileUtil.touch(path)); } @@ -120,14 +120,13 @@ public class QrCodeUtilTest { .setMargin(1); String svg = QrCodeUtil.generateAsSvg("https://hutool.cn/", qrConfig); Assert.assertNotNull(svg); - FileUtil.writeString(svg, "d:/test/qr.svg", StandardCharsets.UTF_8); } @Test public void generateAsciiArtTest() { QrConfig qrConfig = QrConfig.create() - .setForeColor(new Color(0,255,0)) - .setBackColor(new Color(0,0,0)) + .setForeColor(new Color(255,0,255)) + .setBackColor(new Color(0,255,0)) .setWidth(0) .setHeight(0).setMargin(1); String asciiArt = QrCodeUtil.generateAsAsciiArt("https://hutool.cn/",qrConfig); @@ -135,4 +134,33 @@ public class QrCodeUtilTest { System.out.println(asciiArt); } + @Test + public void generateToFileTest() { + QrConfig qrConfig = QrConfig.create() + .setForeColor(Color.BLUE) + .setBackColor(new Color(0,200,255)) + .setWidth(0) + .setHeight(0).setMargin(1); + File qrFile = QrCodeUtil.generate("https://hutool.cn/", qrConfig, FileUtil.touch("d:/test/ascii_art_qr_code.txt")); + BufferedReader reader = FileUtil.getReader(qrFile, StandardCharsets.UTF_8); + reader.lines().forEach(System.out::println); + } + + @Test + public void generateToStreamTest() { + QrConfig qrConfig = QrConfig.create() + .setForeColor(Color.BLUE) + .setBackColor(new Color(0,200,255)) + .setWidth(0) + .setHeight(0).setMargin(1); + String filepath = "d:/test/qr_stream_to_txt.txt"; + try (BufferedOutputStream outputStream = FileUtil.getOutputStream(filepath)) { + QrCodeUtil.generate("https://hutool.cn/", qrConfig,"txt", outputStream); + }catch (IOException e){ + e.printStackTrace(); + } + BufferedReader reader = FileUtil.getReader(filepath, StandardCharsets.UTF_8); + reader.lines().forEach(System.out::println); + } + } From 87319eb73f7f9df0f6cc67fd8df3dfc4b65cf0ce Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Mon, 22 Aug 2022 11:03:17 +0800 Subject: [PATCH 05/10] =?UTF-8?q?=E4=BC=98=E5=8C=96QrCodeUtil=E7=94=9F?= =?UTF-8?q?=E6=88=90base64=E6=96=B9=E6=B3=95=EF=BC=8C=E6=94=AF=E6=8C=81svg?= =?UTF-8?q?=E3=80=81txt?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/extra/qrcode/QrCodeUtil.java | 51 ++++++++++++++----- .../hutool/extra/qrcode/QrCodeUtilTest.java | 9 +++- 2 files changed, 46 insertions(+), 14 deletions(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java index 75448c727..371675624 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java @@ -11,6 +11,7 @@ import cn.hutool.core.lang.ansi.AnsiEncoder; import cn.hutool.core.util.CharsetUtil; import cn.hutool.core.util.NumberUtil; import cn.hutool.core.util.StrUtil; +import cn.hutool.core.util.URLUtil; import com.google.zxing.*; import com.google.zxing.common.BitMatrix; import com.google.zxing.common.GlobalHistogramBinarizer; @@ -46,12 +47,12 @@ public class QrCodeUtil { * * @param content 内容 * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 - * @param imageType 图片类型(图片扩展名),见{@link ImgUtil} + * @param targetType 类型(图片扩展名),见{@link #QR_TYPE_SVG}、 {@link #QR_TYPE_TXT}、{@link ImgUtil} * @param logoBase64 logo 图片的 base64 编码 * @return 图片 Base64 编码字符串 */ - public static String generateAsBase64(String content, QrConfig qrConfig, String imageType, String logoBase64) { - return generateAsBase64(content, qrConfig, imageType, Base64.decode(logoBase64)); + public static String generateAsBase64(String content, QrConfig qrConfig, String targetType, String logoBase64) { + return generateAsBase64(content, qrConfig, targetType, Base64.decode(logoBase64)); } /** @@ -59,12 +60,12 @@ public class QrCodeUtil { * * @param content 内容 * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 - * @param imageType 图片类型(图片扩展名),见{@link ImgUtil} + * @param targetType 类型(图片扩展名),见{@link #QR_TYPE_SVG}、 {@link #QR_TYPE_TXT}、{@link ImgUtil} * @param logo logo 图片的byte[] * @return 图片 Base64 编码字符串 */ - public static String generateAsBase64(String content, QrConfig qrConfig, String imageType, byte[] logo) { - return generateAsBase64(content, qrConfig, imageType, ImgUtil.toImage(logo)); + public static String generateAsBase64(String content, QrConfig qrConfig, String targetType, byte[] logo) { + return generateAsBase64(content, qrConfig, targetType, ImgUtil.toImage(logo)); } /** @@ -72,13 +73,13 @@ public class QrCodeUtil { * * @param content 内容 * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 - * @param imageType 图片类型(图片扩展名),见{@link ImgUtil} + * @param targetType 类型(图片扩展名),见{@link #QR_TYPE_SVG}、 {@link #QR_TYPE_TXT}、{@link ImgUtil} * @param logo logo 图片的byte[] * @return 图片 Base64 编码字符串 */ - public static String generateAsBase64(String content, QrConfig qrConfig, String imageType, Image logo) { + public static String generateAsBase64(String content, QrConfig qrConfig, String targetType, Image logo) { qrConfig.setImg(logo); - return generateAsBase64(content, qrConfig, imageType); + return generateAsBase64(content, qrConfig, targetType); } /** @@ -90,12 +91,36 @@ public class QrCodeUtil { * * @param content 内容 * @param qrConfig 二维码配置,包括长、宽、边距、颜色等 - * @param imageType 图片类型(图片扩展名),见{@link ImgUtil} + * @param targetType 类型(图片扩展名),见{@link #QR_TYPE_SVG}、 {@link #QR_TYPE_TXT}、{@link ImgUtil} * @return 图片 Base64 编码字符串 */ - public static String generateAsBase64(String content, QrConfig qrConfig, String imageType) { - final BufferedImage img = generate(content, qrConfig); - return ImgUtil.toBase64DataUri(img, imageType); + public static String generateAsBase64(String content, QrConfig qrConfig, String targetType) { + String result; + switch (targetType) { + case QR_TYPE_SVG: + String svg = generateAsSvg(content, qrConfig); + result = svgToBase64(svg); + break; + case QR_TYPE_TXT: + String txt = generateAsAsciiArt(content, qrConfig); + result = txtToBase64(txt); + break; + default: + final BufferedImage img = generate(content, qrConfig); + result = ImgUtil.toBase64DataUri(img, targetType); + break; + } + + + return result; + } + + private static String txtToBase64(String txt) { + return URLUtil.getDataUri("text/plain", "base64", Base64.encode(txt)); + } + + private static String svgToBase64(String svg) { + return URLUtil.getDataUri("image/svg+xml", "base64", Base64.encode(svg)); } /** diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index ab07bde11..7ad852c87 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -41,7 +41,7 @@ public class QrCodeUtilTest { // 背景色透明 config.setBackColor(null); config.setErrorCorrection(ErrorCorrectionLevel.H); - String path = FileUtil.isWindows() ? "d:/test/qrcodeCustom.txt" : "~/Desktop/hutool/qrcodeCustom.svg"; + String path = FileUtil.isWindows() ? "d:/test/qrcodeCustom.png" : "~/Desktop/hutool/qrcodeCustom.png"; QrCodeUtil.generate("https://hutool.cn/", config, FileUtil.touch(path)); } @@ -87,6 +87,13 @@ public class QrCodeUtilTest { Assert.assertNotNull(base641); } + @Test + public void generateAsBase64Test3() { + String base64 = QrCodeUtil.generateAsBase64("https://hutool.cn/", new QrConfig(400, 400), "svg"); + Assert.assertNotNull(base64); + System.out.println(base64); + } + @Test @Ignore public void decodeTest3() { From 9543012fecebe376b0d605fd4f2114702cd20d57 Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Mon, 22 Aug 2022 12:38:36 +0800 Subject: [PATCH 06/10] =?UTF-8?q?=E4=BC=98=E5=8C=96QrCodeUtil=E6=B5=8B?= =?UTF-8?q?=E8=AF=95=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index 7ad852c87..ddc964097 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -122,11 +122,14 @@ public class QrCodeUtilTest { @Test public void generateSvgTest() { QrConfig qrConfig = QrConfig.create().setImg("d:/test/logo.png") - .setForeColor(Color.GREEN) + .setForeColor(Color.blue) .setBackColor(Color.pink) + .setRatio(8) + .setErrorCorrection(ErrorCorrectionLevel.M) .setMargin(1); String svg = QrCodeUtil.generateAsSvg("https://hutool.cn/", qrConfig); Assert.assertNotNull(svg); + FileUtil.writeString(svg, FileUtil.touch("d:/test/hutool_qr.svg"),StandardCharsets.UTF_8); } @Test From 62735daa3610ff583ce6c2f6da61ad5a67ff07a0 Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Mon, 22 Aug 2022 13:01:15 +0800 Subject: [PATCH 07/10] =?UTF-8?q?=E4=BC=98=E5=8C=96QrCodeUtil?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/main/java/cn/hutool/extra/qrcode/QrConfig.java | 4 +++- .../src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java | 4 ++-- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java index 4d5a388d8..f4ea8f12a 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrConfig.java @@ -147,7 +147,9 @@ public class QrConfig { * @since 5.1.1 */ public QrConfig setForeColor(Color foreColor) { - if(null != foreColor){ + if(null == foreColor){ + this.foreColor = null; + } else { this.foreColor = foreColor.getRGB(); } return this; diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index ddc964097..8384866b5 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -135,8 +135,8 @@ public class QrCodeUtilTest { @Test public void generateAsciiArtTest() { QrConfig qrConfig = QrConfig.create() - .setForeColor(new Color(255,0,255)) - .setBackColor(new Color(0,255,0)) + .setForeColor(Color.BLUE) + .setBackColor(Color.MAGENTA) .setWidth(0) .setHeight(0).setMargin(1); String asciiArt = QrCodeUtil.generateAsAsciiArt("https://hutool.cn/",qrConfig); From e6fc469e608e27e1e003a7338378bbee94a8850d Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Mon, 22 Aug 2022 13:15:56 +0800 Subject: [PATCH 08/10] =?UTF-8?q?=E4=BC=98=E5=8C=96QrCodeUtil?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/extra/qrcode/QrCodeUtil.java | 2 +- .../hutool/extra/qrcode/QrCodeUtilTest.java | 24 +++++++++++++++++++ 2 files changed, 25 insertions(+), 1 deletion(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java index 371675624..2684c5fcc 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java @@ -358,7 +358,7 @@ public class QrCodeUtil { */ public static BufferedImage generate(String content, BarcodeFormat format, QrConfig config) { final BitMatrix bitMatrix = encode(content, format, config); - final BufferedImage image = toImage(bitMatrix, config.foreColor, config.backColor); + final BufferedImage image = toImage(bitMatrix, config.foreColor != null ? config.foreColor : 0xFF000000, config.backColor); final Image logoImg = config.img; if (null != logoImg && BarcodeFormat.QR_CODE == format) { // 只有二维码可以贴图 diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index 8384866b5..14f67f223 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -44,6 +44,18 @@ public class QrCodeUtilTest { String path = FileUtil.isWindows() ? "d:/test/qrcodeCustom.png" : "~/Desktop/hutool/qrcodeCustom.png"; QrCodeUtil.generate("https://hutool.cn/", config, FileUtil.touch(path)); } + @Test +// @Ignore + public void generateNoCustomColorTest() { + QrConfig config = new QrConfig(); + config.setMargin(0); + config.setForeColor(null); + // 背景色透明 + config.setBackColor(null); + config.setErrorCorrection(ErrorCorrectionLevel.H); + String path = FileUtil.isWindows() ? "d:/test/qrcodeCustom.png" : "~/Desktop/hutool/qrcodeCustom.png"; + QrCodeUtil.generate("https://hutool.cn/", config, FileUtil.touch(path)); + } @Test @Ignore @@ -143,6 +155,18 @@ public class QrCodeUtilTest { Assert.assertNotNull(asciiArt); System.out.println(asciiArt); } + @Test + public void generateAsciiArtNoCustomColorTest() { + QrConfig qrConfig = QrConfig.create() + .setForeColor(null) + .setBackColor(null) + .setWidth(0) + .setHeight(0).setMargin(1); + String asciiArt = QrCodeUtil.generateAsAsciiArt("https://hutool.cn/",qrConfig); + Assert.assertNotNull(asciiArt); + System.out.println(asciiArt); + } + @Test public void generateToFileTest() { From a764477cc07fcd14c2d509befbfab143ac592445 Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Tue, 23 Aug 2022 13:13:21 +0800 Subject: [PATCH 09/10] =?UTF-8?q?=E4=BC=98=E5=8C=96QrCodeUtil?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java index 2684c5fcc..cbe0c6a41 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/qrcode/QrCodeUtil.java @@ -358,7 +358,7 @@ public class QrCodeUtil { */ public static BufferedImage generate(String content, BarcodeFormat format, QrConfig config) { final BitMatrix bitMatrix = encode(content, format, config); - final BufferedImage image = toImage(bitMatrix, config.foreColor != null ? config.foreColor : 0xFF000000, config.backColor); + final BufferedImage image = toImage(bitMatrix, config.foreColor != null ? config.foreColor : Color.BLACK.getRGB(), config.backColor); final Image logoImg = config.img; if (null != logoImg && BarcodeFormat.QR_CODE == format) { // 只有二维码可以贴图 From 45aeefa9f1d301e612f1879ed39a323b56334c46 Mon Sep 17 00:00:00 2001 From: TomXin <766781886@qq.com> Date: Tue, 23 Aug 2022 14:17:42 +0800 Subject: [PATCH 10/10] =?UTF-8?q?=E6=9B=B4=E6=96=B0QrCodeUtilTest?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/cn/hutool/extra/qrcode/QrCodeUtilTest.java | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java index 14f67f223..b6adc03fd 100755 --- a/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java +++ b/hutool-extra/src/test/java/cn/hutool/extra/qrcode/QrCodeUtilTest.java @@ -196,5 +196,16 @@ public class QrCodeUtilTest { BufferedReader reader = FileUtil.getReader(filepath, StandardCharsets.UTF_8); reader.lines().forEach(System.out::println); } + @Test + public void comparePngAndAsciiArtTest() { + QrConfig qrConfig = QrConfig.create() + .setForeColor(null) + .setBackColor(null) + .setWidth(0) + .setHeight(0).setMargin(1); + QrCodeUtil.generate("https://hutool.cn", qrConfig, FileUtil.touch("d:/test/compare/default.jpg")); + QrCodeUtil.generate("https://hutool.cn", qrConfig, FileUtil.touch("d:/test/compare/default.txt")); + QrCodeUtil.generate("https://hutool.cn", qrConfig, FileUtil.touch("d:/test/compare/default.png")); + } }