Java tutorial
/* * Copyright 1998-2010 Linux.org.ru * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package ru.org.linux.util; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; /** * Gets image dimensions by parsing file headers. * <p/> * currently supported file types: Jpeg Gif Png */ public class ImageInfo { private static final Log logger = LogFactory.getLog(ImageInfo.class); private int height = -1; private int width = -1; private int size = 0; private final String filename; @SuppressWarnings("UseOfSystemOutOrSystemErr") public static void main(String[] args) throws Exception { ImageInfo info = new ImageInfo(args[0]); if (info.width > info.height) { System.out.print("horizontal "); } else { System.out.print("vertical "); } System.out.println(info.width + " " + info.height); } public static String detectImageType(File file) throws BadImageException, IOException { logger.debug("Detecting image type for: " + file + " (" + file.length() + " bytes)"); ImageInfo2 ii = new ImageInfo2(); FileInputStream is = null; try { is = new FileInputStream(file); ii.setInput(is); ii.check(); int format = ii.getFormat(); switch (format) { case ImageInfo2.FORMAT_GIF: return "gif"; case ImageInfo2.FORMAT_JPEG: return "jpg"; case ImageInfo2.FORMAT_PNG: return "png"; default: throw new BadImageException("Unsupported format: " + ii.getMimeType()); } } finally { if (is != null) { is.close(); } } } /** * constructs image from filename * <p/> * file type is determined from file's extension */ public ImageInfo(String filename) throws BadImageException, IOException { this.filename = filename; FileInputStream fileStream = null; try { fileStream = new FileInputStream(filename); size = (int) new File(filename).length(); String lowname = filename.toLowerCase(); if (lowname.endsWith("gif")) { getGifInfo(fileStream); } else if (lowname.endsWith("jpg") || lowname.endsWith("jpeg")) { getJpgInfo(fileStream); } else if (lowname.endsWith("png")) { getPngInfo(fileStream); } else { throw new BadImageException("Invalid image extension"); } if (height == -1 || width == -1) { throw new BadImageException(); } } finally { if (fileStream != null) { fileStream.close(); } } } public ImageInfo(String filename, String extension) throws BadImageException, IOException { this(new File(filename), extension); } public ImageInfo(File file, String extension) throws BadImageException, IOException { filename = file.getName(); FileInputStream fileStream = null; try { fileStream = new FileInputStream(file); size = fileStream.available(); if ("gif".equals(extension)) { getGifInfo(fileStream); } else if ("jpg".equals(extension) || "jpeg".equals(extension)) { getJpgInfo(fileStream); } else if ("png".equals(extension)) { getPngInfo(fileStream); } else { throw new BadImageException("Invalid image extension"); } if (height == -1 || width == -1) { throw new BadImageException(); } } finally { if (fileStream != null) { fileStream.close(); } } } private void getGifInfo(FileInputStream fileStream) throws IOException, BadImageException { byte[] bytes = new byte[13]; int bytesread = fileStream.read(bytes); if (bytesread == 13) { String header = new String(bytes); if ("GIF".equals(header.substring(0, 3))) //It's a gif, continue processing { width = shortLittleEndian(bytes[6], bytes[7]); height = shortLittleEndian(bytes[8], bytes[9]); } else { throw new BadImageException("Bad GIF image: " + filename); } } } private void getPngInfo(FileInputStream fileStream) throws IOException, BadImageException { byte[] bytes = new byte[24]; int bytesread = fileStream.read(bytes); if (bytesread == 24) { String header = new String(bytes); if ("PNG".equals(header.substring(1, 4))) { width = intBigEndian(bytes[16], bytes[17], bytes[18], bytes[19]); height = intBigEndian(bytes[20], bytes[21], bytes[22], bytes[23]); } else { throw new BadImageException("Bad PNG image: " + filename); } } } private void getJpgInfo(FileInputStream fileStream) throws IOException, BadImageException { if (fileStream.read() == 0xFF && fileStream.read() == 0xD8) { while (true) { int marker; do { marker = fileStream.read(); } while (marker != 0xFF); do { marker = fileStream.read(); } while (marker == 0xFF); if (((marker >= 0xC0) && (marker <= 0xC3)) || ((marker >= 0xC5) && (marker <= 0xCB)) || ((marker >= 0xCD) && (marker <= 0xCF))) { fileStream.skip(3); height = shortBigEndian((byte) fileStream.read(), (byte) fileStream.read()); width = shortBigEndian((byte) fileStream.read(), (byte) fileStream.read()); break; } else { fileStream.skip(shortBigEndian((byte) fileStream.read(), (byte) fileStream.read()) - 2); } } } else { throw new BadImageException("Bad JPG image: " + filename); } } private static short shortBigEndian(byte firstRead, byte lastRead) { return (short) (((firstRead & 0xFF) << 8) | lastRead & 0xFF); } private static short shortLittleEndian(byte firstRead, byte lastRead) { return shortBigEndian(lastRead, firstRead); } private static int intBigEndian(byte a1, byte a2, byte a3, byte a4) { return ((a1 & 0xFF) << 24) | ((a2 & 0xFF) << 16) | ((a3 & 0xFF) << 8) | a4 & 0xFF; } public int getHeight() { return height; } public int getWidth() { return width; } /** * get file size */ public int getSize() { return size; } /** * get file size in user-printable form */ public String getSizeString() { return size / 1024 + " Kb"; } /** * get HTML code for inclusion into IMG tag */ public String getCode() { return "width=" + width + " height=" + height; } public static void resizeImage(String filename, String iconname, int size) throws IOException, UtilException, InterruptedException { String[] cmd = { "/usr/bin/convert", "-scale", Integer.toString(size), filename, iconname }; Process proc = Runtime.getRuntime().exec(cmd); int exitStatus = proc.waitFor(); if (exitStatus != 0) { logger.warn("Failed to convert from " + filename + " to " + iconname); throw new UtilException("Can't convert image: convert failed"); } } }