15de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet/* 25de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Copyright (C) 2010 The Android Open Source Project 35de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * 45de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Licensed under the Apache License, Version 2.0 (the "License"); 55de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * you may not use this file except in compliance with the License. 65de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * You may obtain a copy of the License at 75de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * 85de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * http://www.apache.org/licenses/LICENSE-2.0 95de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * 105de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Unless required by applicable law or agreed to in writing, software 115de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * distributed under the License is distributed on an "AS IS" BASIS, 125de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 135de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * See the License for the specific language governing permissions and 145de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * limitations under the License. 155de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet */ 165de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 175de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetpackage android.graphics; 185de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 19918aaa5717fce6081557c82ce1c439b6922737d5Xavier Ducrohetimport com.android.ide.common.rendering.api.LayoutLog; 20b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohetimport com.android.layoutlib.bridge.Bridge; 21c2e9651bf386a1f7bf7fc706cf5424950570470cXavier Ducrohetimport com.android.layoutlib.bridge.impl.DelegateManager; 2216584225125acba18b74920b902c798dfead0328Xavier Ducrohetimport com.android.resources.Density; 239a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohetimport com.android.tools.layoutlib.annotations.LayoutlibDelegate; 245de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 255de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport android.graphics.Bitmap.Config; 265de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport android.os.Parcel; 275de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 285de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport java.awt.Graphics2D; 295de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport java.awt.image.BufferedImage; 305de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport java.io.File; 315de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport java.io.IOException; 325de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport java.io.InputStream; 335de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport java.io.OutputStream; 345de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport java.nio.Buffer; 35b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohetimport java.util.Arrays; 365de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 375de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohetimport javax.imageio.ImageIO; 385de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 395de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet/** 405de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Delegate implementing the native methods of android.graphics.Bitmap 415de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * 425de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Through the layoutlib_create tool, the original native methods of Bitmap have been replaced 435de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * by calls to methods of the same name in this delegate class. 445de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * 455de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * This class behaves like the original native implementation, but in Java, keeping previously 465de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * native data into its own objects and mapping them to int that are sent back and forth between 475de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * it and the original Bitmap class. 485de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * 495de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * @see DelegateManager 505de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * 515de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet */ 52d348b6eaa98e23cb38d90906df109aaa2d20ea7fXavier Ducrohetpublic final class Bitmap_Delegate { 535de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 545de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // ---- delegate manager ---- 555de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet private static final DelegateManager<Bitmap_Delegate> sManager = 56f0a53435f14d23d9555fc46014352ee6a7baa647Xavier Ducrohet new DelegateManager<Bitmap_Delegate>(Bitmap_Delegate.class); 575de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 585de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // ---- delegate helper data ---- 595de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 605de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // ---- delegate data ---- 6163fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet private final Config mConfig; 625de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet private BufferedImage mImage; 635de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet private boolean mHasAlpha = true; 64b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet private int mGenerationId = 0; 655de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 6663fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet 675de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // ---- Public Helper methods ---- 685de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 695de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /** 709f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet * Returns the native delegate associated to a given {@link Bitmap_Delegate} object. 719f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet */ 729f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet public static Bitmap_Delegate getDelegate(Bitmap bitmap) { 739f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet return sManager.getDelegate(bitmap.mNativeBitmap); 749f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet } 759f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet 769f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet /** 779f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet * Returns the native delegate associated to a given an int referencing a {@link Bitmap} object. 789f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet */ 799f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet public static Bitmap_Delegate getDelegate(int native_bitmap) { 809f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet return sManager.getDelegate(native_bitmap); 819f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet } 829f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet 839f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet /** 845de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Creates and returns a {@link Bitmap} initialized with the given file content. 852d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * 862d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param input the file from which to read the bitmap content 872d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param isMutable whether the bitmap is mutable 882d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param density the density associated with the bitmap 892d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * 902d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @see Bitmap#isMutable() 912d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @see Bitmap#getDensity() 925de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet */ 9316584225125acba18b74920b902c798dfead0328Xavier Ducrohet public static Bitmap createBitmap(File input, boolean isMutable, Density density) 942d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet throws IOException { 955de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // create a delegate with the content of the file. 9663fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet Bitmap_Delegate delegate = new Bitmap_Delegate(ImageIO.read(input), Config.ARGB_8888); 975de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 9816584225125acba18b74920b902c798dfead0328Xavier Ducrohet return createBitmap(delegate, isMutable, density.getDpiValue()); 995de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 1005de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1015de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /** 1025de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Creates and returns a {@link Bitmap} initialized with the given stream content. 1032d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * 1042d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param input the stream from which to read the bitmap content 1052d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param isMutable whether the bitmap is mutable 1062d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param density the density associated with the bitmap 1072d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * 1082d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @see Bitmap#isMutable() 1092d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @see Bitmap#getDensity() 1105de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet */ 11116584225125acba18b74920b902c798dfead0328Xavier Ducrohet public static Bitmap createBitmap(InputStream input, boolean isMutable, Density density) 1122d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet throws IOException { 1135de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // create a delegate with the content of the stream. 11463fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet Bitmap_Delegate delegate = new Bitmap_Delegate(ImageIO.read(input), Config.ARGB_8888); 1155de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 11616584225125acba18b74920b902c798dfead0328Xavier Ducrohet return createBitmap(delegate, isMutable, density.getDpiValue()); 1175de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 1185de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1195de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /** 1205de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Creates and returns a {@link Bitmap} initialized with the given {@link BufferedImage} 1212d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * 1222d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param image the bitmap content 1232d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param isMutable whether the bitmap is mutable 1242d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @param density the density associated with the bitmap 1252d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * 1262d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @see Bitmap#isMutable() 1272d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet * @see Bitmap#getDensity() 1285de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet */ 129ffb42f6c5043de226f02318a1311669d35a90711Xavier Ducrohet public static Bitmap createBitmap(BufferedImage image, boolean isMutable, 13016584225125acba18b74920b902c798dfead0328Xavier Ducrohet Density density) throws IOException { 1315de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // create a delegate with the given image. 13263fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet Bitmap_Delegate delegate = new Bitmap_Delegate(image, Config.ARGB_8888); 1335de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 13416584225125acba18b74920b902c798dfead0328Xavier Ducrohet return createBitmap(delegate, isMutable, density.getDpiValue()); 1355de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 1365de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1375de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /** 1385de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet * Returns the {@link BufferedImage} used by the delegate of the given {@link Bitmap}. 1395de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet */ 1405de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet public static BufferedImage getImage(Bitmap bitmap) { 1415de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 1425de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(bitmap.mNativeBitmap); 1435de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 1445de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return null; 1455de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 1465de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1475de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return delegate.mImage; 1485de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 1495de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1505de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet public static int getBufferedImageType(int nativeBitmapConfig) { 1517f9f99ea11051614a7727dfb9f9578b518e76e3cXavier Ducrohet switch (Config.nativeToConfig(nativeBitmapConfig)) { 1525de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet case ALPHA_8: 1535de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return BufferedImage.TYPE_INT_ARGB; 1545de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet case RGB_565: 1555de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return BufferedImage.TYPE_INT_ARGB; 1565de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet case ARGB_4444: 1575de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return BufferedImage.TYPE_INT_ARGB; 1585de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet case ARGB_8888: 1595de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return BufferedImage.TYPE_INT_ARGB; 1605de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 1615de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1625de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return BufferedImage.TYPE_INT_ARGB; 1635de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 1645de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1659f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet /** 1669f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet * Returns the {@link BufferedImage} used by the delegate of the given {@link Bitmap}. 1679f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet */ 1689f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet public BufferedImage getImage() { 1699f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet return mImage; 1709f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet } 1719f63ff263b0a97f0fa63e97136c18f6abccbfc68Xavier Ducrohet 17263fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet /** 17363fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet * Returns the Android bitmap config. Note that this not the config of the underlying 17463fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet * Java2D bitmap. 17563fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet */ 17663fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet public Config getConfig() { 17763fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet return mConfig; 17863fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet } 17963fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet 180b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet /** 181b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * Returns the hasAlpha rendering hint 182b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * @return true if the bitmap alpha should be used at render time 183b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet */ 184b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet public boolean hasAlpha() { 185b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return mHasAlpha && mConfig != Config.RGB_565; 186b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 187b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 188b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet /** 189b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * Update the generationId. 190b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * 191b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * @see Bitmap#getGenerationId() 192b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet */ 193b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet public void change() { 194b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet mGenerationId++; 195b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 19663fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet 1975de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // ---- native methods ---- 1985de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 1999a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2005de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static Bitmap nativeCreate(int[] colors, int offset, int stride, int width, 2015de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet int height, int nativeConfig, boolean mutable) { 2025de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet int imageType = getBufferedImageType(nativeConfig); 2035de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2045de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // create the image 2055de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet BufferedImage image = new BufferedImage(width, height, imageType); 2065de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 207b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (colors != null) { 208b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet image.setRGB(0, 0, width, height, colors, offset, stride); 209b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 2105de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2115de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // create a delegate with the content of the stream. 2127f9f99ea11051614a7727dfb9f9578b518e76e3cXavier Ducrohet Bitmap_Delegate delegate = new Bitmap_Delegate(image, Config.nativeToConfig(nativeConfig)); 2135de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2142d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet return createBitmap(delegate, mutable, Bitmap.getDefaultDensity()); 2155de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2165de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2179a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2185de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static Bitmap nativeCopy(int srcBitmap, int nativeConfig, boolean isMutable) { 219b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate srcBmpDelegate = sManager.getDelegate(srcBitmap); 220b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (srcBmpDelegate == null) { 221b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return null; 222b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 223b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 224b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet BufferedImage srcImage = srcBmpDelegate.getImage(); 225b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 226b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int width = srcImage.getWidth(); 227b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int height = srcImage.getHeight(); 228b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 229b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int imageType = getBufferedImageType(nativeConfig); 230b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 231b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // create the image 232b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet BufferedImage image = new BufferedImage(width, height, imageType); 233b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 234b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // copy the source image into the image. 235b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int[] argb = new int[width * height]; 236b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet srcImage.getRGB(0, 0, width, height, argb, 0, width); 237b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet image.setRGB(0, 0, width, height, argb, 0, width); 238b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 239b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // create a delegate with the content of the stream. 2407f9f99ea11051614a7727dfb9f9578b518e76e3cXavier Ducrohet Bitmap_Delegate delegate = new Bitmap_Delegate(image, Config.nativeToConfig(nativeConfig)); 241b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 242b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return createBitmap(delegate, isMutable, Bitmap.getDefaultDensity()); 2435de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2445de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2459a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2465de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeDestructor(int nativeBitmap) { 247cc4977d0fdaf657907912fd6cc2f9426dc8d2e36Xavier Ducrohet sManager.removeJavaReferenceFor(nativeBitmap); 2485de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2495de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2509a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2515de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeRecycle(int nativeBitmap) { 252cc4977d0fdaf657907912fd6cc2f9426dc8d2e36Xavier Ducrohet sManager.removeJavaReferenceFor(nativeBitmap); 2535de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2545de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2559a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2565de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static boolean nativeCompress(int nativeBitmap, int format, int quality, 2575de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet OutputStream stream, byte[] tempStorage) { 258918aaa5717fce6081557c82ce1c439b6922737d5Xavier Ducrohet Bridge.getLog().error(LayoutLog.TAG_UNSUPPORTED, 25951a7e5447de94791c464cda5cc6ebbf616d73c80Xavier Ducrohet "Bitmap.compress() is not supported", null /*data*/); 260b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return true; 2615de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2625de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2639a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2645de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeErase(int nativeBitmap, int color) { 2655de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 2665de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 2675de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 2685de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return; 2695de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2705de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2715de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet BufferedImage image = delegate.mImage; 2725de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2735de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Graphics2D g = image.createGraphics(); 2745de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet try { 275b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet g.setColor(new java.awt.Color(color, true)); 2765de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2775de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet g.fillRect(0, 0, image.getWidth(), image.getHeight()); 2785de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } finally { 2795de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet g.dispose(); 2805de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2815de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2825de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2839a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2845de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static int nativeWidth(int nativeBitmap) { 2855de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 2865de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 2875de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 2885de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return 0; 2895de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2905de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2915de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return delegate.mImage.getWidth(); 2925de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 2935de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 2949a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 2955de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static int nativeHeight(int nativeBitmap) { 2965de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 2975de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 2985de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 2995de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return 0; 3005de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3015de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3025de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return delegate.mImage.getHeight(); 3035de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3045de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3059a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3065de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static int nativeRowBytes(int nativeBitmap) { 3075de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 3085de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 3095de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 3105de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return 0; 3115de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3125de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3135de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return delegate.mImage.getWidth(); 3145de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3155de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3169a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3175de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static int nativeConfig(int nativeBitmap) { 31863fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet // get the delegate from the native int. 31963fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 32063fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet if (delegate == null) { 32163fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet return 0; 32263fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet } 32363fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet 32463fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet return delegate.mConfig.nativeInt; 3255de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3265de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3279a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3285de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static boolean nativeHasAlpha(int nativeBitmap) { 3295de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 3305de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 3315de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 3325de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return true; 3335de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3345de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3355de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return delegate.mHasAlpha; 3365de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3375de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3389a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3395de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static int nativeGetPixel(int nativeBitmap, int x, int y) { 3405de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 3415de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 3425de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 3435de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return 0; 3445de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3455de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3465de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return delegate.mImage.getRGB(x, y); 3475de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3485de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3499a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3505de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeGetPixels(int nativeBitmap, int[] pixels, int offset, 3515de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet int stride, int x, int y, int width, int height) { 352b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 353b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate == null) { 354b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return; 355b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 356b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 357b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet delegate.getImage().getRGB(x, y, width, height, pixels, offset, stride); 3585de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3595de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3605de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3619a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3625de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeSetPixel(int nativeBitmap, int x, int y, int color) { 363b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 364b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate == null) { 365b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return; 366b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 367b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 368b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet delegate.getImage().setRGB(x, y, color); 3695de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3705de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3719a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3725de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeSetPixels(int nativeBitmap, int[] colors, int offset, 3735de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet int stride, int x, int y, int width, int height) { 374b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 375b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate == null) { 376b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return; 377b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 378b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 379b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet delegate.getImage().setRGB(x, y, width, height, colors, offset, stride); 3805de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3815de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3829a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3835de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeCopyPixelsToBuffer(int nativeBitmap, Buffer dst) { 3845de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // FIXME implement native delegate 3858a80a8555238cc564f445f902aff5231993a8f96Xavier Ducrohet Bridge.getLog().fidelityWarning(LayoutLog.TAG_UNSUPPORTED, 3868a80a8555238cc564f445f902aff5231993a8f96Xavier Ducrohet "Bitmap.copyPixelsToBuffer is not supported.", null, null /*data*/); 3875de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3885de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3899a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3905de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeCopyPixelsFromBuffer(int nb, Buffer src) { 3915de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // FIXME implement native delegate 3928a80a8555238cc564f445f902aff5231993a8f96Xavier Ducrohet Bridge.getLog().fidelityWarning(LayoutLog.TAG_UNSUPPORTED, 3938a80a8555238cc564f445f902aff5231993a8f96Xavier Ducrohet "Bitmap.copyPixelsFromBuffer is not supported.", null, null /*data*/); 3945de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 3955de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 3969a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 3975de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static int nativeGenerationId(int nativeBitmap) { 398b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 399b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate == null) { 400b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return 0; 401b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 402b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 403b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return delegate.mGenerationId; 4045de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 4055de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 4069a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 4075de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static Bitmap nativeCreateFromParcel(Parcel p) { 408b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // This is only called by Bitmap.CREATOR (Parcelable.Creator<Bitmap>), which is only 409b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // used during aidl call so really this should not be called. 410918aaa5717fce6081557c82ce1c439b6922737d5Xavier Ducrohet Bridge.getLog().error(LayoutLog.TAG_UNSUPPORTED, 41151a7e5447de94791c464cda5cc6ebbf616d73c80Xavier Ducrohet "AIDL is not suppored, and therefore Bitmaps cannot be created from parcels.", 41251a7e5447de94791c464cda5cc6ebbf616d73c80Xavier Ducrohet null /*data*/); 413b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return null; 4145de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 4155de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 4169a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 4175de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static boolean nativeWriteToParcel(int nativeBitmap, boolean isMutable, 4185de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet int density, Parcel p) { 419b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // This is only called when sending a bitmap through aidl, so really this should not 420b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // be called. 421918aaa5717fce6081557c82ce1c439b6922737d5Xavier Ducrohet Bridge.getLog().error(LayoutLog.TAG_UNSUPPORTED, 42251a7e5447de94791c464cda5cc6ebbf616d73c80Xavier Ducrohet "AIDL is not suppored, and therefore Bitmaps cannot be written to parcels.", 42351a7e5447de94791c464cda5cc6ebbf616d73c80Xavier Ducrohet null /*data*/); 424b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return false; 4255de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 4265de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 4279a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 4285de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static Bitmap nativeExtractAlpha(int nativeBitmap, int nativePaint, 4295de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet int[] offsetXY) { 430b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate bitmap = sManager.getDelegate(nativeBitmap); 431b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (bitmap == null) { 432b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return null; 433b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 434b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 435d43909c7503e11eb335a452d296a10804bb01fd6Xavier Ducrohet // get the paint which can be null if nativePaint is 0. 436d43909c7503e11eb335a452d296a10804bb01fd6Xavier Ducrohet Paint_Delegate paint = Paint_Delegate.getDelegate(nativePaint); 437b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 438d43909c7503e11eb335a452d296a10804bb01fd6Xavier Ducrohet if (paint != null && paint.getMaskFilter() != null) { 439918aaa5717fce6081557c82ce1c439b6922737d5Xavier Ducrohet Bridge.getLog().fidelityWarning(LayoutLog.TAG_MASKFILTER, 440b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet "MaskFilter not supported in Bitmap.extractAlpha", 44151a7e5447de94791c464cda5cc6ebbf616d73c80Xavier Ducrohet null, null /*data*/); 442b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 4435de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 444b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int alpha = paint != null ? paint.getAlpha() : 0xFF; 445b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet BufferedImage image = createCopy(bitmap.getImage(), BufferedImage.TYPE_INT_ARGB, alpha); 446b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 447b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // create the delegate. The actual Bitmap config is only an alpha channel 448b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate delegate = new Bitmap_Delegate(image, Config.ALPHA_8); 449b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 450b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // the density doesn't matter, it's set by the Java method. 451b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return createBitmap(delegate, false /*isMutable*/, 45216584225125acba18b74920b902c798dfead0328Xavier Ducrohet Density.DEFAULT_DENSITY /*density*/); 453b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 4545de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 4559a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 4565de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativePrepareToDraw(int nativeBitmap) { 457b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // nothing to be done here. 4585de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 4595de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 4609a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 4615de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static void nativeSetHasAlpha(int nativeBitmap, boolean hasAlpha) { 4625de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get the delegate from the native int. 4635de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet Bitmap_Delegate delegate = sManager.getDelegate(nativeBitmap); 4645de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet if (delegate == null) { 4655de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet return; 4665de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 4675de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 4685de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet delegate.mHasAlpha = hasAlpha; 4695de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 4705de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 4719a4fe29c8d92014d2d9a848e9116b8cc9d0842f9Xavier Ducrohet @LayoutlibDelegate 4725de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet /*package*/ static boolean nativeSameAs(int nb0, int nb1) { 473b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate delegate1 = sManager.getDelegate(nb0); 474b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate1 == null) { 475b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return false; 476b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 477b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 478b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet Bitmap_Delegate delegate2 = sManager.getDelegate(nb1); 479b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate2 == null) { 480b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return false; 481b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 482b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 483b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet BufferedImage image1 = delegate1.getImage(); 484b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet BufferedImage image2 = delegate2.getImage(); 485b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate1.mConfig != delegate2.mConfig || 486b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet image1.getWidth() != image2.getWidth() || 487b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet image1.getHeight() != image2.getHeight()) { 488b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return false; 489b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 490b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 491b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // get the internal data 492b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int w = image1.getWidth(); 493b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int h = image2.getHeight(); 494b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int[] argb1 = new int[w*h]; 495b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int[] argb2 = new int[w*h]; 496b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 497b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet image1.getRGB(0, 0, w, h, argb1, 0, w); 498b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet image2.getRGB(0, 0, w, h, argb2, 0, w); 499b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 500b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // compares 501b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (delegate1.mConfig == Config.ALPHA_8) { 502b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet // in this case we have to manually compare the alpha channel as the rest is garbage. 503b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet final int length = w*h; 504b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet for (int i = 0 ; i < length ; i++) { 505b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if ((argb1[i] & 0xFF000000) != (argb2[i] & 0xFF000000)) { 506b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return false; 507b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 508b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 509b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return true; 510b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 511b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 512b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return Arrays.equals(argb1, argb2); 5135de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 5145de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 5155de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // ---- Private delegate/helper methods ---- 5165de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 51763fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet private Bitmap_Delegate(BufferedImage image, Config config) { 5185de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet mImage = image; 51963fd87113cea6abec97a6cd966e090e9b590fc3bXavier Ducrohet mConfig = config; 5205de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 5215de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 5222d56b273ef6e2984a4e8914fb67772b173d0a154Xavier Ducrohet private static Bitmap createBitmap(Bitmap_Delegate delegate, boolean isMutable, int density) { 5235de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // get its native_int 524cc4977d0fdaf657907912fd6cc2f9426dc8d2e36Xavier Ducrohet int nativeInt = sManager.addNewDelegate(delegate); 5255de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet 5265de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet // and create/return a new Bitmap with it 527ec4a50428d5f26a22df3edaf7e5b08f41d5cb54bAmith Yamasani return new Bitmap(nativeInt, null /* buffer */, isMutable, null /*ninePatchChunk*/, 528ec4a50428d5f26a22df3edaf7e5b08f41d5cb54bAmith Yamasani density); 5295de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet } 530b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 531b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet /** 532b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * Creates and returns a copy of a given BufferedImage. 533b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * <p/> 534b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * if alpha is different than 255, then it is applied to the alpha channel of each pixel. 535b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * 536b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * @param image the image to copy 537b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * @param imageType the type of the new image 538b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * @param alpha an optional alpha modifier 539b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet * @return a new BufferedImage 540b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet */ 541b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet /*package*/ static BufferedImage createCopy(BufferedImage image, int imageType, int alpha) { 542b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int w = image.getWidth(); 543b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int h = image.getHeight(); 544b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 545b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet BufferedImage result = new BufferedImage(w, h, imageType); 546b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 547b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int[] argb = new int[w * h]; 548b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet image.getRGB(0, 0, image.getWidth(), image.getHeight(), argb, 0, image.getWidth()); 549b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 550b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet if (alpha != 255) { 551b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet final int length = argb.length; 552b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet for (int i = 0 ; i < length; i++) { 553b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet int a = (argb[i] >>> 24 * alpha) / 255; 554b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet argb[i] = (a << 24) | (argb[i] & 0x00FFFFFF); 555b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 556b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 557b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 558b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet result.setRGB(0, 0, w, h, argb, 0, w); 559b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 560b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet return result; 561b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet } 562b1da1afa7418960b650780250bbd34c81af61aa3Xavier Ducrohet 5635de11a18e9151e6bc9b3e81cf31fc43dc63dffbfXavier Ducrohet} 564