⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 facecollage.java

📁 此Java代码可以生成一个拼贴组成的数以百计的图
💻 JAVA
字号:
package image.collage;

import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;

import javax.imageio.ImageIO;

public class FaceCollage
{
// ######## CUSTOMIZATION PART ######## - start

// Main image that is formed by collage of images. Must be a bitmap.
private static String mainImagePath = "C:/Image/MainImage.jpg";

// Folder that contains bitmaps which form the collage
private static String sourceFilesPath = "C:/Image/Source/";

// Localtion where result image to be created.
private static String CollageFilePath = "C:/Image/Collage/";

// The number of times, final collage image to be bigger than actual image, so that the small images are clear when zoomed
private static int enlargeSize = 4;

// Number of pixels in each small block of the actual image. Smaller the pixels, better the final collage. Higher the pixels, small images in final collage look clear. Better to keep the same x-y ratio(4:3 generally) as your source images.
private static int XpixelsPerBlock = 12;
private static int YpixelsPerBlock = 9;

// ######## CUSTOMIZATION PART ######## - end

public static void main(String[] args)
{
System.out.println("Running...");
try
{
File sourceFile = new File(mainImagePath);
BufferedImage mainImage = ImageIO.read(sourceFile);
int[][][] blockArray = BlockMainImage(mainImage);

File[] listOfSourceFiles = GetListOfSourcefiles();

int[][] sourceFileRGBs = ClassifySourceImages(listOfSourceFiles);

boolean[] doesSourceContribute = new boolean[listOfSourceFiles.length];
int[][] matchArray = MatchImagesWithBlocks(blockArray, sourceFileRGBs, doesSourceContribute);

CreateResult(mainImage, listOfSourceFiles, matchArray, doesSourceContribute);
System.out.println("Done!!");
}
catch (IOException e)
{
e.printStackTrace();
}
}

public static int[][][] BlockMainImage(BufferedImage imageSource) throws IOException
{
int width = imageSource.getWidth();
int height = imageSource.getHeight();

int[][] rgbArray = new int[width][height];

for (int x = 0; x < width; x++)
for (int y = 0; y < height; y++)
rgbArray[x][y] = imageSource.getRGB(x, y);

int numberOfXBlocks = width / XpixelsPerBlock;
int numberOfYBlocks = height / YpixelsPerBlock;

int[][][] blockArray = new int[numberOfXBlocks][numberOfYBlocks][3];

for (int i = 0; i < numberOfXBlocks; i++)
for (int j = 0; j < numberOfYBlocks; j++)
{
int value, sumR = 0;
int sumG = 0;
int sumB = 0;

for (int x = 0; x < XpixelsPerBlock; x++)
for (int y = 0; y < YpixelsPerBlock; y++)
{
value = rgbArray[i * XpixelsPerBlock + x][j * YpixelsPerBlock + y] + 16777216;
sumB += (value % 256);
value = (value / 256);
sumG += (value % 256);
value = (value / 256);
sumR += (value);
}
int resolutionPerBlock = XpixelsPerBlock * YpixelsPerBlock;
blockArray[i][j][0] = sumR/resolutionPerBlock;
blockArray[i][j][1] = sumG/resolutionPerBlock;
blockArray[i][j][2] = sumB/resolutionPerBlock;
}

return blockArray;
}

public static File[] GetListOfSourcefiles() throws IOException
{
File sourceFolder = new File(sourceFilesPath);
File[] listOfFiles = sourceFolder.listFiles();
int sourceFileCount = 0;
for (int i = 0; i < listOfFiles.length; i++)
{
if (!listOfFiles[i].isFile())
continue;
BufferedImage imageSource = ImageIO.read(listOfFiles[i]);
if (imageSource == null)
continue;
sourceFileCount++;
}

File[] listOfSourceFiles = new File[sourceFileCount];
for (int i = 0, n = 0; i < listOfFiles.length; i++)
{
if (!listOfFiles[i].isFile())
continue;
BufferedImage imageSource = ImageIO.read(listOfFiles[i]);
if (imageSource == null)
continue;
listOfSourceFiles[n++] = listOfFiles[i];
}
return listOfSourceFiles;
}

public static int[][] ClassifySourceImages(File[] listOfSourceFiles) throws IOException
{
int[][] sourceFileRGBs = new int[listOfSourceFiles.length][3];
for (int i = 0; i < listOfSourceFiles.length; i++)
{
if (!listOfSourceFiles[i].isFile())
continue;

BufferedImage imageSource = ImageIO.read(listOfSourceFiles[i]);

if (imageSource == null)
continue;

int width = imageSource.getWidth();
int height = imageSource.getHeight();

int value, sumR = 0;
int sumG = 0;
int sumB = 0;

for (int x = 0; x < width; x++)
for (int y = 0; y < height; y++)
{
value = imageSource.getRGB(x, y) + 16777216;
sumB += (value % 256);
value = (value / 256);
sumG += (value % 256);
value = (value / 256);
sumR += (value);
}
int resolution = width * height;
sourceFileRGBs[i][0] = sumR/resolution;
sourceFileRGBs[i][1] = sumG/resolution;
sourceFileRGBs[i][2] = sumB/resolution;
}
return sourceFileRGBs;
}

public static int[][] MatchImagesWithBlocks(int[][][] blockArray, int[][] sourceFileRGBs, boolean[] doesSourceContribute)
{
int[][] matchArray = new int[blockArray.length][blockArray[0].length];

for (int j = 0; j < blockArray.length; j++)
for (int k = 0; k < blockArray[0].length; k++)
{
int bestDiff = -1;
for (int i = 0; i < sourceFileRGBs.length; i++)
{
int diff = (int)Math.sqrt(Math.pow(blockArray[j][k][0] - sourceFileRGBs[i][0], 2) + Math.pow(blockArray[j][k][1] - sourceFileRGBs[i][1], 2) + Math.pow(blockArray[j][k][2] - sourceFileRGBs[i][2], 2));
if (bestDiff == -1 || (diff < bestDiff))
{
bestDiff = diff;
matchArray[j][k] = i;
}
}
doesSourceContribute[matchArray[j][k]] = true;
}
return matchArray;
}

public static void CreateResult(BufferedImage mainImage, File[] listOfSourceFiles, int[][] matchArray, boolean[] doesSourceContribute) throws IOException
{
int [][][] shortImages = new int[doesSourceContribute.length][XpixelsPerBlock*enlargeSize][YpixelsPerBlock*enlargeSize];
for (int n = 0; n < doesSourceContribute.length; n++)
{
if (!doesSourceContribute[n])
continue;

BufferedImage imageSource = ImageIO.read(listOfSourceFiles[n]);

int width = imageSource.getWidth();
int height = imageSource.getHeight();

int[][] rgbArray = new int[width][height];

for (int x = 0; x < width; x++)
for (int y = 0; y < height; y++)
rgbArray[x][y] = imageSource.getRGB(x, y);

int shortImageXPixel = XpixelsPerBlock * enlargeSize;
int shortImageYPixel = YpixelsPerBlock * enlargeSize;
int XShrinkRatio = width/shortImageXPixel;
int YShrinkRatio = height/shortImageYPixel;
int resolution = XShrinkRatio * YShrinkRatio;

for (int i = 0; i < shortImageXPixel; i++)
for (int j = 0; j < shortImageYPixel; j++)
{
int value, sumR = 0;
int sumG = 0;
int sumB = 0;

for (int x = 0; x < XShrinkRatio; x++)
for (int y = 0; y < YShrinkRatio; y++)
{
value = rgbArray[i * XShrinkRatio + x][j * YShrinkRatio + y] + 1;
sumB += (value % 256);
value = (value / 256);
sumG += (value % 256);
value = (value / 256);
sumR += value;
}

sumR /= resolution;
sumG /= resolution;
sumB /= resolution;
shortImages[n][i][j] = sumR * 65536 + sumG * 256 + sumB - 1;
}
}

int width = mainImage.getWidth() * enlargeSize;
int height = mainImage.getHeight() * enlargeSize;

BufferedImage imageResult = new BufferedImage(width, height, mainImage.getType());

int XpixelPerBlockInResult = XpixelsPerBlock * enlargeSize;
int YpixelPerBlockInResult = YpixelsPerBlock * enlargeSize;
int XBlocks = width/XpixelPerBlockInResult;
int YBlocks = height/YpixelPerBlockInResult;

for (int i = 0; i < XBlocks; i++)
for (int j = 0; j < YBlocks; j++)
{
int match = matchArray[i][j];
for (int x = 0; x < XpixelPerBlockInResult; x++)
for (int y = 0; y < YpixelPerBlockInResult; y++)
imageResult.setRGB((i * XpixelPerBlockInResult + x), (j * YpixelPerBlockInResult + y), shortImages[match][x][y]);
}

File resultFile = new File(CollageFilePath + "Collage.jpg");
ImageIO.write(imageResult, "jpg", resultFile);
}
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -