我正在参加「兔了个兔」创意投稿大赛,详情请看:「兔了个兔」创意投稿大赛
0 引子
我们在启动一些软件时,在启动界面总能看到相关由字符组成的各种软件图案,比如SpringBoot的
那么,如果我们要使用图片来做成字符图案,做为项目启动LOGO,这样看起来会不会更酷呢?
我们的原图是下边这只可爱的小兔子
1 使用自定义字符,打印图像
操作步骤:
- 把这只兔子读取到图像对象中
- 获取图像对象中的像素数据
- 解析像素数据为RGB值
- 将RGB值转为单一灰度值
- 定义我们想要组成图案的字符列表,将单一灰度值替换为我们定义的字符并输出
/**
* 支持 import Java 标准库 (JDK 1.8)
*/
import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
/**
* 注意:目前 Java 代码的入口类名称必须为 Main(大小写敏感)
*/
public class Main {
public static void main(final String[] args) {
//声明图片路径
String path = "/home/faas/abc.png";
String base = "!@#$%^&*()+=<>"; //定义组成图案的字符列表
try {
//读取图片文件
BufferedImage image = ImageIO.read(new File(path));
//遍历纵坐标像素点
for (int y = 0; y < image.getHeight(); y += 2) {
//遍历横坐标像素点
for (int x = 0; x < image.getWidth(); x += 1) {
//获取像素值
int rgb = image.getRGB(x, y);
//分别计算像素值中的RGB数据
int red = (rgb >> 16 ) & 0xff;
int green = (rgb >> 8) & 0xff;
int black = rgb & 0xff;
//将RGB数据转为灰度值
float gray = 0.299f * red + 0.578f * green + 0.114f * black;
int index = Math.round(gray * (base.length() + 1) / 255);
System.out.print(index >= base.length() ? " " : String.valueOf(base.charAt(index)));
}
System.out.println();
}
} catch (final IOException e) {
e.printStackTrace();
}
}
}
打印效果如下
2 水墨图风格的兔子
2.1 首先将彩色图片转为黑白水墨
public static void main(String[] args) {
String path = "d:/data/abc.png";
try {
//读取图片文件
BufferedImage image = ImageIO.read(new File(path));
int width = image.getWidth();
int height = image.getHeight();
//使用灰度模式,创建新的图像对象
BufferedImage grayImage = new BufferedImage(width, height, BufferedImage.TYPE_BYTE_BINARY);
for(int i= 0 ; i < width ; i++){
for(int j = 0 ; j < height; j++){
int rgb = image.getRGB(i, j);
//将像素数据存入缓冲区中
grayImage.setRGB(i, j, rgb);
}
}
File newFile = new File(path + "bak1.png");
ImageIO.write(grayImage, "png", newFile);
} catch (IOException e) {
e.printStackTrace();
}
}
转换后的效果为
2.2 将图片转为字符图案
还是使用 1 中的方法,只是图像文件的名称有变化
public static void main(final String[] args) {
String path = "d:/data/abc.pngbak1.png";
String base = "!@#$%^&*()+=<>"; //定义组成图案的字符列表
try {
//读取图片文件
BufferedImage image = ImageIO.read(new File(path));
//遍历纵坐标像素点
for (int y = 0; y < image.getHeight(); y += 2) {
//遍历横坐标像素点
for (int x = 0; x < image.getWidth(); x += 1) {
//获取像素值
int rgb = image.getRGB(x, y);
//分别计算像素值中的RGB数据
int red = (rgb >> 16 ) & 0xff;
int green = (rgb >> 8) & 0xff;
int black = rgb & 0xff;
//将RGB数据转为灰度值
float gray = 0.299f * red + 0.578f * green + 0.114f * black;
int index = Math.round(gray * (base.length() + 1) / 250);
System.out.print(index >= base.length() ? " " : String.valueOf(base.charAt(index)));
}
System.out.println();
}
} catch (final IOException e) {
e.printStackTrace();
}
}
转换后的效果如下
注意
需要注意的是,用来做字符图案的图片不宜过大,上边转换后的图案都是在notepad++上极限缩小的情况下展示出来的。