Hola! Estoy teniendo un problema el resizear imágenes en Java, y sobre el stack que me dá no hay ninguna información en internet, y ya hace 2 días que no lo puedo solucionar. El stack es el siguiente:
Código :
Ver originalcensere.framework.commons.exception.DataAccessException: Se produjo un error al crear el item <18>
bla bla bla bla
Caused by: com.sun.image.codec.jpeg.ImageFormatException: Initializing CInfo for encoding.
at sun.awt.image.codec.JPEGImageEncoderImpl.writeJPEGStream(Native Method)
at sun.awt.image.codec.JPEGImageEncoderImpl.encode(Unknown Source)
at sun.awt.image.codec.JPEGImageEncoderImpl.encode(Unknown Source)
at sun.awt.image.codec.JPEGImageEncoderImpl.encode(Unknown Source)
at censere.framework.utils.images.ImgScaler.convertToJpg(ImgScaler.java:220)
at censere.framework.utils.images.ImgScaler.convertToJpg(ImgScaler.java:230)
at censere.framework.utils.images.ImgScaler.convertToJpg(ImgScaler.java:230)
Esa última línea del stack, se repite cientos de veces hasta que debe hacer stack overflow. El código que resizea es el siguiente:
Código :
Ver original//Función principal a la que llamo
public byte[] getScaled(String fullPath, int size, int maxWeight, boolean forceSquare) throws Exception {
BufferedImage img = ImageIO.read(new File(fullPath));
return getScaled(img, size, maxWeight, forceSquare);
}
/**
* Hace todo el proceso
*/
public byte[] getScaled(BufferedImage img, int size, int maxWeight, boolean forceSquare) throws Exception {
BufferedImage out = getScaledBI(img, size, forceSquare);
return getBytes(out, size, maxWeight);
}
/**
* Reduce una BufferedImage
*/
public BufferedImage getScaledBI(BufferedImage img, int size, boolean forceSquare) throws Exception {
int scaleStep;
if ( size <= 200 )
scaleStep = scaleSmallStep;
else
scaleStep = scaleBigStep;
BufferedImage out = scaleSteps(img, size, scaleStep, forceSquare);
return out;
}
public BufferedImage scaleSteps(BufferedImage img, int max, int maxStep, boolean forceSquare) throws IOException {
resizeSteps = (Math.max(img.getWidth(), img.getHeight()) / maxStep) + 1;
debug("resizeSteps=" + resizeSteps);
return scaleByRemainingSteps(img, max, resizeSteps, forceSquare);
}
public BufferedImage scaleByRemainingSteps(BufferedImage img, int max, int remainingSteps, boolean forceSquare)
throws IOException {
// Determine the scale.
double scale = (double) max / (double) img.getHeight();
if (img.getWidth() > img.getHeight()) {
scale = (double) max / (double) img.getWidth();
}
if (remainingSteps > 1) {
double step = (1d - scale) / remainingSteps;
scale += step;
}
// No agranda por ningún motivo
if (scale > 1d)
scale = 1d;
debug("scale=" + scale);
int scaledW = (int) (scale * img.getWidth());
int scaledH = (int) (scale * img.getHeight());
int newMax = Math.max(scaledW, scaledH);
// Si el maximo calculado es mas chico que el objetivo, va el obj
// esto puede pasar si la imagen es mas chica que el obj
if (newMax < max)
newMax = max;
HashMap<Object, Object> hints = new HashMap<Object, Object>();
// hints.put(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
// hints.put(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
// hints.put(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
// hints.put(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
hints.put(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
BufferedImage out = null;
if (forceSquare) {
out = new BufferedImage(newMax, newMax, BufferedImage.TYPE_INT_RGB);
} else {
out = new BufferedImage(scaledW, scaledH, BufferedImage.TYPE_INT_RGB);
}
Graphics2D g2d = out.createGraphics();
g2d.setBackground(new Color(255, 255, 255));
g2d.clearRect(0, 0, newMax, newMax);
g2d.setRenderingHints(hints);
if (forceSquare) {
g2d.drawImage(img, (newMax - scaledW) / 2, (newMax - scaledH) / 2, scaledW, scaledH, null);
} else {
g2d.drawImage(img, 0, 0, scaledW, scaledH, null);
}
g2d.dispose();
if (remainingSteps > 1)
return scaleByRemainingSteps(out, max, remainingSteps - 1, forceSquare);
return out;
}
/**
* Convierte a JPG y devuelve los bytes
*
* @throws Exception
*/
public byte[] getBytes(BufferedImage img, int size, int maxWeight) throws Exception {
int step;
int startQuality;
if (size < 100) {
step = jpgSmallStep;
startQuality = jpgStartSmall;
} else {
step = jpgBigStep;
startQuality = jpgStartBig;
}
byte[] bytes = convertToJpg(img, startQuality, maxWeight, step);
return bytes;
}
public byte[] convertToJpg(BufferedImage img, int quality, int maxSize, int step) throws Exception {
ByteArrayOutputStream out = new ByteArrayOutputStream();
JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
JPEGEncodeParam param = encoder.getDefaultJPEGEncodeParam(img);
float q = quality / 100f;
param.setQuality(q, true);
encoder.encode(img, param);
byte[] imageBytes = out.toByteArray();
out.close();
finalQuality = (int) (q * 100);
qualitySteps++;
debug("q=" + q + ", s=" + imageBytes.length);
if (imageBytes.length > maxSize)
return convertToJpg(img, quality - step, maxSize, step);
return imageBytes;
}
Esta última función es la que falla, pero la verdad que ya no tengo idea de cual puede ser el problema.
Espero me puedan ayudar POR FAVOR!!!