/** * Unload the given image's data into the given byte stream using the given compression strategy. * Answer the number of bytes written. Method modified to use the passed data if it is not null. */ int unloadData(ImageData image, byte[] data, OutputStream out, int comp) { int totalSize = 0; try { if (comp == 0) return unloadDataNoCompression(image, data, out); int bpl = (image.width * image.depth + 7) / 8; int bmpBpl = (bpl + 3) / 4 * 4; // BMP pads scanlines to multiples of 4 bytes int imageBpl = image.bytesPerLine; // Compression can actually take twice as much space, in worst case byte[] buf = new byte[bmpBpl * 2]; int srcOffset = imageBpl * (image.height - 1); // Start at last line if (data == null) data = image.data; totalSize = 0; byte[] buf2 = new byte[32768]; int buf2Offset = 0; for (int y = image.height - 1; y >= 0; y--) { int lineSize = compress(comp, data, srcOffset, bpl, buf, y == 0); if (buf2Offset + lineSize > buf2.length) { out.write(buf2, 0, buf2Offset); buf2Offset = 0; } System.arraycopy(buf, 0, buf2, buf2Offset, lineSize); buf2Offset += lineSize; totalSize += lineSize; srcOffset -= imageBpl; } if (buf2Offset > 0) out.write(buf2, 0, buf2Offset); } catch (IOException e) { SWT.error(SWT.ERROR_IO, e); } return totalSize; }
/** * Prepare the given image's data for unloading into a byte stream using no compression strategy. * Answer the number of bytes written. Method modified to use the passed data if it is not null. */ int unloadDataNoCompression(ImageData image, byte[] data, OutputStream out) { int bmpBpl = 0; try { int bpl = (image.width * image.depth + 7) / 8; bmpBpl = (bpl + 3) / 4 * 4; // BMP pads scanlines to multiples of 4 bytes int linesPerBuf = 32678 / bmpBpl; byte[] buf = new byte[linesPerBuf * bmpBpl]; if (data == null) data = image.data; int imageBpl = image.bytesPerLine; int dataIndex = imageBpl * (image.height - 1); // Start at last line if (image.depth == 16) { for (int y = 0; y < image.height; y += linesPerBuf) { int count = image.height - y; if (linesPerBuf < count) count = linesPerBuf; int bufOffset = 0; for (int i = 0; i < count; i++) { for (int wIndex = 0; wIndex < bpl; wIndex += 2) { buf[bufOffset + wIndex + 1] = data[dataIndex + wIndex + 1]; buf[bufOffset + wIndex] = data[dataIndex + wIndex]; } bufOffset += bmpBpl; dataIndex -= imageBpl; } out.write(buf, 0, bufOffset); } } else { for (int y = 0; y < image.height; y += linesPerBuf) { int tmp = image.height - y; int count = tmp < linesPerBuf ? tmp : linesPerBuf; int bufOffset = 0; for (int i = 0; i < count; i++) { System.arraycopy(data, dataIndex, buf, bufOffset, bpl); bufOffset += bmpBpl; dataIndex -= imageBpl; } out.write(buf, 0, bufOffset); } } } catch (IOException e) { SWT.error(SWT.ERROR_IO, e); } return bmpBpl * image.height; }