BufferedImage 是处理图片的缓冲器,用于处理图片的长度,修改图片的大小,颜色转换以及对图片的其他修改。
public class Test {
static BufferedImage image = null;
public static void main(String[] args)
{
try {
File input_file = new File("C:\\Users\\Administrator\\Desktop\\beautiful.jpg");
image = new BufferedImage(600,600,BufferedImage.TYPE_INT_RGB);
image = ImageIO.read(input_file);
System.out.println("图片已读取");
File out_file = new File("C:\\Users\\Administrator\\Desktop\\out_beautiful4.jpg");
ImageIO.write(image,"jpg",out_file);
System.out.println("图片已输出");
} catch (IOException e) {
e.printStackTrace();
}
}
}
像素是图像的最小单位,由四个分量Alpha(透明度度量),红色,绿色,蓝色和简称(ARGB)组成。
所有组件的值都在0到255之间(包括0和255)。零表示该组件不存在,而255表示该组件已完全存在。
由于 2 8 = 256 2^{8} = 256 28=256并且像素分量的值在0到255之间,因此我们只需要8位即可存储这些值。
因此,存储ARGB值所需的总位数为8 * 4 = 32位或4个字节。
当顺序表示Alpha获取最左边的8位时,Blue获取最右边的8位。
因此位的位置:
蓝色分量为7-0,
绿色分量为15-8,
红色分量为23-16,
alpha分量为31-24,
在灰度图像中,图像的Alpha分量将与原始图像相同,但是RGB将被更改,即,所有三个RGB分量对于每个像素将具有相同的值。
算法:
public class Test {
static BufferedImage image = null;
static File input_file = null;
public static void main(String[] args)
{
try {
input_file = new File("C:\\Users\\Administrator\\Desktop\\beautiful.jpg");
image = ImageIO.read(input_file);
} catch (IOException e) {
e.printStackTrace();
}
// 获取图片的长度和宽度
int width = image.getWidth();
int height = image.getHeight();
for (int y = 0; y < height; y++)
{
for (int x = 0; x < width; x++)
{
// (x,y)表示图像的坐标
int p = image.getRGB(x,y);
int a = (p>>24)&0xff;
int r = (p>>16)&0xff;
int g = (p>>8)&0xff;
int b = p&0xff;
// 计算平均值
int avg = (r+g+b)/3;
// 替换 RGB 值
p = (a<<24) | (avg<<16) | (avg<<8) | avg;
image.setRGB(x, y, p);
}
}
// 输出图片
try
{
input_file = new File("C:\\Users\\Administrator\\Desktop\\out.jpg");
ImageIO.write(image, "jpg", input_file);
} catch (IOException e) {
e.printStackTrace();
}
}
}
在负片图像中,图像的Alpha分量将与原始图像相同,但是RGB将被更改,即所有三个RGB分量的值将均为255-原始分量值。
算法:
public class Test {
static BufferedImage image = null;
static File input_file = null;
public static void main(String[] args)
{
try {
input_file = new File("C:\\Users\\Administrator\\Desktop\\beautiful.jpg");
image = ImageIO.read(input_file);
} catch (IOException e) {
e.printStackTrace();
}
// 获取图片的长度和宽度
int width = image.getWidth();
int height = image.getHeight();
for (int y = 0; y < height; y++)
{
for (int x = 0; x < width; x++)
{
// (x,y)表示图像的坐标
int p = image.getRGB(x,y);
int a = (p>>24)&0xff;
int r = (p>>16)&0xff;
int g = (p>>8)&0xff;
int b = p&0xff;
// 从255减去RGB
r = 255 - r;
g = 255 - g;
b = 255 - b;
// 替换 RGB 值
p = (a<<24) | (r<<16) | (g<<8) | b;
image.setRGB(x, y, p);
}
}
// 输出图片
try
{
input_file = new File("C:\\Users\\Administrator\\Desktop\\out.jpg");
ImageIO.write(image, "jpg", input_file);
} catch (IOException e) {
e.printStackTrace();
}
}
}
获取每个坐标的像素值,然后保持所需的结果彩色像素值相同,并将其他两个像素值设置为零。
转换成红色:
public class Test {
static BufferedImage image = null;
static File input_file = null;
public static void main(String[] args)
{
try {
input_file = new File("C:\\Users\\Administrator\\Desktop\\beautiful.jpg");
image = ImageIO.read(input_file);
} catch (IOException e) {
e.printStackTrace();
}
// 获取图片的长度和宽度
int width = image.getWidth();
int height = image.getHeight();
for (int y = 0; y < height; y++)
{
for (int x = 0; x < width; x++)
{
// (x,y)表示图像的坐标
int p = image.getRGB(x,y);
int a = (p>>24)&0xff;
int r = (p>>16)&0xff;
int g = (p>>8)&0xff;
int b = p&0xff;
// G:设为 0
// B:设为 0
g = 0;
b = 0;
// 替换 RGB 值
p = (a<<24) | (r<<16) | (g<<8) | b;
image.setRGB(x, y, p);
}
}
// 输出图片
try
{
input_file = new File("C:\\Users\\Administrator\\Desktop\\out.jpg");
ImageIO.write(image, "jpg", input_file);
} catch (IOException e) {
e.printStackTrace();
}
}
}
比如设为蓝色
在棕褐色图像中,图像的Alpha分量将与原始图像相同(因为Alpha分量表示透明度),但是RGB将更改。
棕褐色计算公式(微软推荐):
newRed = 0.393 * R + 0.769 * G + 0.189 * B
newGreen = 0.349 * R + 0.686 * G + 0.168 * B
newBlue = 0.272 * R + 0.534 * G + 0.131 * B
注意:如果这些输出值中的任何一个大于255, 只需将其设置为255。
public class Test {
static BufferedImage image = null;
static File input_file = null;
public static void main(String[] args)
{
try {
input_file = new File("C:\\Users\\Administrator\\Desktop\\beautiful.jpg");
image = ImageIO.read(input_file);
} catch (IOException e) {
e.printStackTrace();
}
// 获取图片的长度和宽度
int width = image.getWidth();
int height = image.getHeight();
for (int y = 0; y < height; y++)
{
for (int x = 0; x < width; x++)
{
// (x,y)表示图像的坐标
int p = image.getRGB(x,y);
int a = (p>>24)&0xff;
int r = (p>>16)&0xff;
int g = (p>>8)&0xff;
int b = p&0xff;
// 计算 红色,绿色,蓝色
int newRed = (int)(0.393*r + 0.769*g + 0.189*b);
int newGreen = (int)(0.349*r + 0.686*g + 0.168*b);
int newBlue = (int)(0.272*r + 0.534*g + 0.131*b);
//check condition
if (newRed > 255)
r = 255;
else
r = newRed;
if (newGreen > 255)
g = 255;
else
g = newGreen;
if (newBlue > 255)
b = 255;
else
b = newBlue;
// 替换 RGB 值
p = (a<<24) | (r<<16) | (g<<8) | b;
image.setRGB(x, y, p);
}
}
// 输出图片
try
{
input_file = new File("C:\\Users\\Administrator\\Desktop\\out.jpg");
ImageIO.write(image, "jpg", input_file);
} catch (IOException e) {
e.printStackTrace();
}
}
}
将左侧的颜色值放到右侧,将右侧的颜色值放到左侧。
算法:
public class Test {
static BufferedImage image = null;
static File input_file = null;
public static void main(String[] args)
{
try {
input_file = new File("C:\\Users\\Administrator\\Desktop\\beautiful.jpg");
image = ImageIO.read(input_file);
} catch (IOException e) {
e.printStackTrace();
}
// 获取图片的长度和宽度
int width = image.getWidth();
int height = image.getHeight();
for (int y = 0; y < height; y++)
{
for (int x = 0, rx = (width - 1); x < width/2; x++, rx--)
{
// (x,y)表示图像的坐标
int p = image.getRGB(x,y);
int p2 = image.getRGB(rx,y);
image.setRGB(rx, y, p);
image.setRGB(x, y, p2);
}
}
// 输出图片
try
{
input_file = new File("C:\\Users\\Administrator\\Desktop\\out.jpg");
ImageIO.write(image, "jpg", input_file);
} catch (IOException e) {
e.printStackTrace();
}
}
}
您可以在此基础上下旋转。
另外,您可以创建另一个BufferedImage对象并添加颜色值以实现镜像。
首先,我们需要为Java设置OpenCV。
OpenCV在线安装教程太多了,我们只介绍一个很容易在这里出现的问题,NO opencv_java300 in java.library.path [duplicate]
,这是因为缺少opencv_java430.dll,请将其从opencv / build / java / x64目录复制到jdk安装目录的 bin 目录中。
public class Test {
// 加载Core.NATIVE_LIBRARY_NAME
static{ System.loadLibrary(Core.NATIVE_LIBRARY_NAME); }
public static void main(String[] args)
{
//通过加载源级联xml文件来创建人脸检测器
CascadeClassifier faceDetector = new CascadeClassifier();
File directory = new File("");//设定为当前文件夹
String path = directory.getAbsolutePath()+"\\src\\haarcascade_frontalface_alt.xml";
faceDetector.load(path);
Mat image = Imgcodecs.imread("C:\\Users\\Administrator\\Desktop\\aobama.jpg");
// 侦测人脸
MatOfRect faceDetections = new MatOfRect();
faceDetector.detectMultiScale(image, faceDetections);
// 创建一个显示检测到的面部的矩形框
for (Rect rect : faceDetections.toArray())
{
Imgproc.rectangle(image, new Point(rect.x, rect.y),
new Point(rect.x + rect.width, rect.y + rect.height),
new Scalar(0, 255, 0));
}
// 输出图像
Imgcodecs.imwrite("C:\\Users\\Administrator\\Desktop\\out2.jpg", image);
}
}
这里使用三个包:
使用的一些方法:
public class Test {
static BufferedImage img = null;
static File f = null;
public static void main(String[] args)
{
try {
// 读取图片
f = new File("C:\\Users\\Administrator\\Desktop\\beautiful.jpg");
img = ImageIO.read(f);
} catch (IOException e) {
e.printStackTrace();
}
// 创建相同宽度的BufferedImage对象,并从输入图片开始的高度
BufferedImage temp = new BufferedImage(img.getWidth(),
img.getHeight(), BufferedImage.TYPE_INT_RGB);
//创建图形对象并添加原始图片
Graphics graphics = temp.getGraphics();
graphics.drawImage(img, 0, 0, null);
// 设置水印文本的字体和颜色
graphics.setFont(new Font("Arial", Font.PLAIN, 20));
graphics.setColor(new Color(0, 122, 255, 40));
// 设置水印文本内容
String watermark = "hello world";
// 设置水印位置
graphics.drawString(watermark, 30, 30);
// 释放该方法正在使用的所有系统资源
graphics.dispose();
try {
// 输出图像
ImageIO.write(temp, "png", new File("C:\\Users\\Administrator\\Desktop\\out.jpg"));
} catch (IOException e) {
e.printStackTrace();
}
}
}