aboutsummaryrefslogtreecommitdiffstats
path: root/ddms
diff options
context:
space:
mode:
authorXavier Ducrohet <xav@android.com>2009-11-12 13:25:09 -0800
committerXavier Ducrohet <xav@android.com>2009-11-12 13:30:02 -0800
commit4112b0c98f2debc972b14c791aff29603f0a23b7 (patch)
tree1ba6e36a56d66f5a66d1a13e8a9ae6beb2b1da40 /ddms
parent132b77d91171a9a773fa6fe221f10c52ac996a75 (diff)
downloadsdk-4112b0c98f2debc972b14c791aff29603f0a23b7.zip
sdk-4112b0c98f2debc972b14c791aff29603f0a23b7.tar.gz
sdk-4112b0c98f2debc972b14c791aff29603f0a23b7.tar.bz2
Use SWT to write PNG screenshot now that we moved to SWT 3.3+
BUG 2256562 Change-Id: I9a181cb799b1eadc027d6357c100fc4dfb0db012
Diffstat (limited to 'ddms')
-rw-r--r--ddms/libs/ddmuilib/src/com/android/ddmuilib/ScreenShotDialog.java10
-rw-r--r--ddms/libs/ddmuilib/src/com/android/ddmuilib/WritePng.java258
2 files changed, 7 insertions, 261 deletions
diff --git a/ddms/libs/ddmuilib/src/com/android/ddmuilib/ScreenShotDialog.java b/ddms/libs/ddmuilib/src/com/android/ddmuilib/ScreenShotDialog.java
index 0f04a60..3a108f6 100644
--- a/ddms/libs/ddmuilib/src/com/android/ddmuilib/ScreenShotDialog.java
+++ b/ddms/libs/ddmuilib/src/com/android/ddmuilib/ScreenShotDialog.java
@@ -21,6 +21,7 @@ import com.android.ddmlib.Log;
import com.android.ddmlib.RawImage;
import org.eclipse.swt.SWT;
+import org.eclipse.swt.SWTException;
import org.eclipse.swt.dnd.Clipboard;
import org.eclipse.swt.dnd.ImageTransfer;
import org.eclipse.swt.dnd.Transfer;
@@ -28,6 +29,7 @@ import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.graphics.ImageData;
+import org.eclipse.swt.graphics.ImageLoader;
import org.eclipse.swt.graphics.PaletteData;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
@@ -292,10 +294,12 @@ public class ScreenShotDialog extends Dialog {
ImageData imageData = mImageLabel.getImage().getImageData();
try {
- WritePng.savePng(fileName, imageData);
+ ImageLoader loader = new ImageLoader();
+ loader.data = new ImageData[] { imageData };
+ loader.save(fileName, SWT.IMAGE_PNG);
}
- catch (IOException ioe) {
- Log.w("ddms", "Unable to save " + fileName + ": " + ioe);
+ catch (SWTException e) {
+ Log.w("ddms", "Unable to save " + fileName + ": " + e.getMessage());
}
}
}
diff --git a/ddms/libs/ddmuilib/src/com/android/ddmuilib/WritePng.java b/ddms/libs/ddmuilib/src/com/android/ddmuilib/WritePng.java
deleted file mode 100644
index 804b416..0000000
--- a/ddms/libs/ddmuilib/src/com/android/ddmuilib/WritePng.java
+++ /dev/null
@@ -1,258 +0,0 @@
-/*
- * Copyright (C) 2007 The Android Open Source Project
- *
- * 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 com.android.ddmuilib;
-
-import com.android.ddmlib.Log;
-
-import org.eclipse.swt.graphics.ImageData;
-
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.OutputStream;
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-import java.util.zip.CRC32;
-import java.util.zip.Deflater;
-
-/**
- * Compensate for SWT issues by writing our own PNGs from ImageData.
- */
-public class WritePng {
- private WritePng() {}
-
- private static final byte[] PNG_MAGIC =
- new byte[] { -119, 80, 78, 71, 13, 10, 26, 10 };
-
- public static void savePng(String fileName, ImageData imageData)
- throws IOException {
-
- try {
- FileOutputStream out = new FileOutputStream(fileName);
-
- Log.d("ddms", "Saving to PNG, width=" + imageData.width
- + ", height=" + imageData.height
- + ", depth=" + imageData.depth
- + ", bpl=" + imageData.bytesPerLine);
-
- savePng(out, imageData);
-
- // need to do that on, or the file is empty on windows!
- out.flush();
- out.close();
- } catch (Exception e) {
- Log.e("writepng", e);
- }
- }
-
- /*
- * Supply functionality missing from our version of SWT.
- */
- private static void savePng(OutputStream out, ImageData imageData)
- throws IOException {
-
- int width = imageData.width;
- int height = imageData.height;
- byte[] out24;
-
- Log.d("ddms-png", "Convert to 24bit from " + imageData.depth);
-
- if (imageData.depth == 24 || imageData.depth == 32) {
- out24 = convertTo24ForPng(imageData.data, width, height,
- imageData.depth, imageData.bytesPerLine);
- } else if (imageData.depth == 16) {
- out24 = convert16to24(imageData);
- } else {
- return;
- }
-
- // Create the compressed form. I'm taking the low road here and
- // just creating a large buffer, which should always be enough to
- // hold the compressed output.
- byte[] compPixels = new byte[out24.length + 16384];
- Deflater compressor = new Deflater();
- compressor.setLevel(Deflater.BEST_COMPRESSION);
- compressor.setInput(out24);
- compressor.finish();
- int compLen;
- do { // must do this in a loop to satisfy java.util.Zip
- compLen = compressor.deflate(compPixels);
- assert compLen != 0 || !compressor.needsInput();
- } while (compLen == 0);
- Log.d("ddms", "Compressed image data from " + out24.length
- + " to " + compLen);
-
- // Write the PNG magic
- out.write(PNG_MAGIC);
-
- ByteBuffer buf;
- CRC32 crc;
-
- // Write the IHDR chunk (13 bytes)
- byte[] header = new byte[8 + 13 + 4];
- buf = ByteBuffer.wrap(header);
- buf.order(ByteOrder.BIG_ENDIAN);
-
- putChunkHeader(buf, 13, "IHDR");
- buf.putInt(width);
- buf.putInt(height);
- buf.put((byte) 8); // 8pp
- buf.put((byte) 2); // direct color used
- buf.put((byte) 0); // compression method == deflate
- buf.put((byte) 0); // filter method (none)
- buf.put((byte) 0); // interlace method (none)
-
- crc = new CRC32();
- crc.update(header, 4, 4+13);
- buf.putInt((int)crc.getValue());
-
- out.write(header);
-
- // Write the IDAT chunk
- byte[] datHdr = new byte[8 + 0 + 4];
- buf = ByteBuffer.wrap(datHdr);
- buf.order(ByteOrder.BIG_ENDIAN);
-
- putChunkHeader(buf, compLen, "IDAT");
- crc = new CRC32();
- crc.update(datHdr, 4, 4+0);
- crc.update(compPixels, 0, compLen);
- buf.putInt((int) crc.getValue());
-
- out.write(datHdr, 0, 8);
- out.write(compPixels, 0, compLen);
- out.write(datHdr, 8, 4);
-
- // Write the IEND chunk (0 bytes)
- byte[] trailer = new byte[8 + 0 + 4];
-
- buf = ByteBuffer.wrap(trailer);
- buf.order(ByteOrder.BIG_ENDIAN);
- putChunkHeader(buf, 0, "IEND");
-
- crc = new CRC32();
- crc.update(trailer, 4, 4+0);
- buf.putInt((int)crc.getValue());
-
- out.write(trailer);
- }
-
- /*
- * Output a chunk header.
- */
- private static void putChunkHeader(ByteBuffer buf, int length,
- String typeStr) {
-
- int type = 0;
-
- if (typeStr.length() != 4)
- throw new RuntimeException();
-
- for (int i = 0; i < 4; i++) {
- type <<= 8;
- type |= (byte) typeStr.charAt(i);
- }
-
- buf.putInt(length);
- buf.putInt(type);
- }
-
- /*
- * Convert raw pixels to 24-bit RGB with a "filter" byte at the start
- * of each row.
- */
- private static byte[] convertTo24ForPng(byte[] in, int width, int height,
- int depth, int stride) {
-
- assert depth == 24 || depth == 32;
- assert stride == width * (depth/8);
-
- // 24 bit pixels plus one byte per line for "filter"
- byte[] out24 = new byte[width * height * 3 + height];
- int y;
-
- int inOff = 0;
- int outOff = 0;
- for (y = 0; y < height; y++) {
- out24[outOff++] = 0; // filter flag
-
- if (depth == 24) {
- System.arraycopy(in, inOff, out24, outOff, width * 3);
- outOff += width * 3;
- } else if (depth == 32) {
- int tmpOff = inOff;
- for (int x = 0; x < width; x++) {
- tmpOff++; // ignore alpha
- out24[outOff++] = in[tmpOff++];
- out24[outOff++] = in[tmpOff++];
- out24[outOff++] = in[tmpOff++];
- }
- }
-
- inOff += stride;
- }
-
- assert outOff == out24.length;
-
- return out24;
- }
-
- private static byte[] convert16to24(ImageData imageData) {
- int width = imageData.width;
- int height = imageData.height;
-
- int redShift = imageData.palette.redShift;
- int greenShift = imageData.palette.greenShift;
- int blueShift = imageData.palette.blueShift;
-
- int redMask = imageData.palette.redMask;
- int greenMask = imageData.palette.greenMask;
- int blueMask = imageData.palette.blueMask;
-
- // 24 bit pixels plus one byte per line for "filter"
- byte[] out24 = new byte[width * height * 3 + height];
- int outOff = 0;
-
-
- int[] line = new int[width];
- for (int y = 0; y < height; y++) {
- imageData.getPixels(0, y, width, line, 0);
-
- out24[outOff++] = 0; // filter flag
- for (int x = 0; x < width; x++) {
- int pixelValue = line[x];
- out24[outOff++] = byteChannelValue(pixelValue, redMask, redShift);
- out24[outOff++] = byteChannelValue(pixelValue, greenMask, greenShift);
- out24[outOff++] = byteChannelValue(pixelValue, blueMask, blueShift);
- }
- }
-
- return out24;
- }
-
- private static byte byteChannelValue(int value, int mask, int shift) {
- int bValue = value & mask;
- if (shift < 0) {
- bValue = bValue >>> -shift;
- } else {
- bValue = bValue << shift;
- }
-
- return (byte)bValue;
-
- }
-
-}