BitmapDrawable.java revision 9066cfe9886ac131c34d59ed0e2d287b0e3c0087
19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/*
29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Copyright (C) 2006 The Android Open Source Project
39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
49066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
59066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * you may not use this file except in compliance with the License.
69066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * You may obtain a copy of the License at
79066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
89066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
99066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * See the License for the specific language governing permissions and
149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * limitations under the License.
159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */
169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectpackage android.graphics.drawable;
189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.content.res.Resources;
209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.content.res.TypedArray;
219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.Bitmap;
229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.BitmapFactory;
239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.Canvas;
249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.ColorFilter;
259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.Paint;
269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.PixelFormat;
279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.Rect;
289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.Shader;
299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.graphics.BitmapShader;
309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.util.AttributeSet;
319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.util.DisplayMetrics;
329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.view.Gravity;
339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport org.xmlpull.v1.XmlPullParser;
359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport org.xmlpull.v1.XmlPullParserException;
369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport java.io.IOException;
389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/**
409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * A Drawable that wraps a bitmap and can be tiled, stretched, or aligned. You can create a
419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * BitmapDrawable from a file path, an input stream, through XML inflation, or from
429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * a {@link android.graphics.Bitmap} object.
439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>It can be defined in an XML file with the <code>&lt;bitmap></code> element.</p>
449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>
459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Also see the {@link android.graphics.Bitmap} class, which handles the management and
469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * transformation of raw bitmap graphics, and should be used when drawing to a
479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * {@link android.graphics.Canvas}.
489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * </p>
499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * @attr ref android.R.styleable#BitmapDrawable_src
519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * @attr ref android.R.styleable#BitmapDrawable_antialias
529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * @attr ref android.R.styleable#BitmapDrawable_filter
539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * @attr ref android.R.styleable#BitmapDrawable_dither
549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * @attr ref android.R.styleable#BitmapDrawable_gravity
559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * @attr ref android.R.styleable#BitmapDrawable_tileMode
569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */
579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectpublic class BitmapDrawable extends Drawable {
589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static final int DEFAULT_PAINT_FLAGS = Paint.FILTER_BITMAP_FLAG;
609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private BitmapState mBitmapState;
619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private Bitmap mBitmap;
629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private final Rect mDstRect = new Rect();   // Gravity.apply() sets this
639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private boolean mApplyGravity;
659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private boolean mRebuildShader;
669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private int mBitmapWidth;
679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private int mBitmapHeight;
689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private boolean mMutated;
699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public BitmapDrawable() {
719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState = new BitmapState((Bitmap) null);
729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public BitmapDrawable(Bitmap bitmap) {
759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        this(new BitmapState(bitmap));
769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public BitmapDrawable(String filepath) {
799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        this(new BitmapState(BitmapFactory.decodeFile(filepath)));
809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (mBitmap == null) {
819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            android.util.Log.w("BitmapDrawable", "BitmapDrawable cannot decode " + filepath);
829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public BitmapDrawable(java.io.InputStream is) {
869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        this(new BitmapState(BitmapFactory.decodeStream(is)));
879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (mBitmap == null) {
889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            android.util.Log.w("BitmapDrawable", "BitmapDrawable cannot decode " + is);
899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final Paint getPaint() {
939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mBitmapState.mPaint;
949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final Bitmap getBitmap() {
979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mBitmap;
989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private void setBitmap(Bitmap bitmap) {
1019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmap = bitmap;
1029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (bitmap != null) {
1039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mBitmapWidth = bitmap.getWidth();
1049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mBitmapHeight = bitmap.getHeight();
1059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        } else {
1069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mBitmapWidth = mBitmapHeight = -1;
1079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
1089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
1119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Set the density scale at which this drawable will be rendered. This
1129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * method assumes the drawable will be rendered at the same density as the
1139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * specified canvas.
1149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param canvas The Canvas from which the density scale must be obtained.
1169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see android.graphics.Bitmap#setDensityScale(float)
1189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see android.graphics.Bitmap#getDensityScale()
1199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @hide pending API council approval
1219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
1229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setDensityScale(Canvas canvas) {
1239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setDensityScale(canvas.getDensityScale());
1249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
1279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Set the density scale at which this drawable will be rendered.
1289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param metrics The DisplayMetrics indicating the density scale for this drawable.
1309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see android.graphics.Bitmap#setDensityScale(float)
1329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see android.graphics.Bitmap#getDensityScale()
1339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @hide pending API council approval
1359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
1369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setDensityScale(DisplayMetrics metrics) {
1379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setDensityScale(metrics.density);
1389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
1419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Set the density scale at which this drawable will be rendered.
1429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param density The density scale for this drawable.
1449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see android.graphics.Bitmap#setDensityScale(float)
1469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see android.graphics.Bitmap#getDensityScale()
1479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
1489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @hide pending API council approval
1499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
1509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setDensityScale(float density) {
1519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        density = (density == Bitmap.DENSITY_SCALE_UNKNOWN ? 1.0f : density);
1529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mTargetDensityScale = density;
1539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /** Get the gravity used to position/stretch the bitmap within its bounds.
1569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        See android.view.Gravity
1579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return the gravity applied to the bitmap
1589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
1599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public int getGravity() {
1609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mBitmapState.mGravity;
1619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /** Set the gravity used to position/stretch the bitmap within its bounds.
1649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        See android.view.Gravity
1659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param gravity the gravity
1669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
1679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setGravity(int gravity) {
1689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mGravity = gravity;
1699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mApplyGravity = true;
1709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setAntiAlias(boolean aa) {
1739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mPaint.setAntiAlias(aa);
1749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
1779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setFilterBitmap(boolean filter) {
1789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mPaint.setFilterBitmap(filter);
1799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
1829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setDither(boolean dither) {
1839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mPaint.setDither(dither);
1849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public Shader.TileMode getTileModeX() {
1879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mBitmapState.mTileModeX;
1889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public Shader.TileMode getTileModeY() {
1919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mBitmapState.mTileModeY;
1929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setTileModeX(Shader.TileMode mode) {
1959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setTileModeXY(mode, mBitmapState.mTileModeY);
1969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final void setTileModeY(Shader.TileMode mode) {
1999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setTileModeXY(mBitmapState.mTileModeX, mode);
2009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setTileModeXY(Shader.TileMode xmode, Shader.TileMode ymode) {
2039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final BitmapState state = mBitmapState;
2049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (state.mTileModeX != xmode || state.mTileModeY != ymode) {
2059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            state.mTileModeX = xmode;
2069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            state.mTileModeY = ymode;
2079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mRebuildShader = true;
2089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
2129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public int getChangingConfigurations() {
2139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return super.getChangingConfigurations() | mBitmapState.mChangingConfigurations;
2149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
2179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    protected void onBoundsChange(Rect bounds) {
2189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        super.onBoundsChange(bounds);
2199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mApplyGravity = true;
2209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
2239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void draw(Canvas canvas) {
2249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Bitmap bitmap = mBitmap;
2259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (bitmap != null) {
2269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            final BitmapState state = mBitmapState;
2279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (mRebuildShader) {
2289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                Shader.TileMode tmx = state.mTileModeX;
2299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                Shader.TileMode tmy = state.mTileModeY;
2309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                if (tmx == null && tmy == null) {
2329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    state.mPaint.setShader(null);
2339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                } else {
2349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    Shader s = new BitmapShader(bitmap,
2359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            tmx == null ? Shader.TileMode.CLAMP : tmx,
2369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            tmy == null ? Shader.TileMode.CLAMP : tmy);
2379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    state.mPaint.setShader(s);
2389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                }
2399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                mRebuildShader = false;
2409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                copyBounds(mDstRect);
2419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
2429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            Shader shader = state.mPaint.getShader();
2449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (shader == null) {
2459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                if (mApplyGravity) {
2469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    Gravity.apply(state.mGravity, mBitmapWidth, mBitmapHeight,
2479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            getBounds(), mDstRect);
2489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    mApplyGravity = false;
2499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                }
2509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                canvas.drawBitmap(bitmap, null, mDstRect, state.mPaint);
2519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            } else {
2529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                if (mApplyGravity) {
2539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    mDstRect.set(getBounds());
2549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    mApplyGravity = false;
2559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                }
2569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                canvas.drawRect(mDstRect, state.mPaint);
2579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
2589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
2629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setAlpha(int alpha) {
2639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mPaint.setAlpha(alpha);
2649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
2679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void setColorFilter(ColorFilter cf) {
2689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mPaint.setColorFilter(cf);
2699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
2729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * A mutable BitmapDrawable still shares its Bitmap with any other Drawable
2739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * that comes from the same resource.
2749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
2759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return This drawable.
2769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
2779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
2789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public Drawable mutate() {
2799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (!mMutated && super.mutate() == this) {
2809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mBitmapState = new BitmapState(mBitmapState);
2819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mMutated = true;
2829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return this;
2849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
2879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public void inflate(Resources r, XmlPullParser parser, AttributeSet attrs)
2889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            throws XmlPullParserException, IOException {
2899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        super.inflate(r, parser, attrs);
2909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        TypedArray a = r.obtainAttributes(attrs, com.android.internal.R.styleable.BitmapDrawable);
2929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final int id = a.getResourceId(com.android.internal.R.styleable.BitmapDrawable_src, 0);
2949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (id == 0) {
2959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            throw new XmlPullParserException(parser.getPositionDescription() +
2969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    ": <bitmap> requires a valid src attribute");
2979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final Bitmap bitmap = BitmapFactory.decodeResource(r, id);
2999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (bitmap == null) {
3009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            throw new XmlPullParserException(parser.getPositionDescription() +
3019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    ": <bitmap> requires a valid src attribute");
3029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mBitmap = bitmap;
3049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setBitmap(bitmap);
3059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setDensityScale(r.getDisplayMetrics());
3069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final Paint paint = mBitmapState.mPaint;
3089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        paint.setAntiAlias(a.getBoolean(com.android.internal.R.styleable.BitmapDrawable_antialias,
3099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                paint.isAntiAlias()));
3109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        paint.setFilterBitmap(a.getBoolean(com.android.internal.R.styleable.BitmapDrawable_filter,
3119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                paint.isFilterBitmap()));
3129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        paint.setDither(a.getBoolean(com.android.internal.R.styleable.BitmapDrawable_dither,
3139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                paint.isDither()));
3149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setGravity(a.getInt(com.android.internal.R.styleable.BitmapDrawable_gravity, Gravity.FILL));
3159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        int tileMode = a.getInt(com.android.internal.R.styleable.BitmapDrawable_tileMode, -1);
3169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (tileMode != -1) {
3179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            switch (tileMode) {
3189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                case 0:
3199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    setTileModeXY(Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
3209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    break;
3219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                case 1:
3229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    setTileModeXY(Shader.TileMode.REPEAT, Shader.TileMode.REPEAT);
3239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    break;
3249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                case 2:
3259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    setTileModeXY(Shader.TileMode.MIRROR, Shader.TileMode.MIRROR);
3269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    break;
3279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
3289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        a.recycle();
3319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
3349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public int getIntrinsicWidth() {
3359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final Bitmap bitmap = mBitmap;
3369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final BitmapState state = mBitmapState;
3379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (!state.mAutoScale || state.mBitmapScale == Bitmap.DENSITY_SCALE_UNKNOWN) {
3399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return mBitmapWidth;
3409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        } else {
3419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return bitmap != null ? (int) (mBitmapWidth /
3429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    (state.mBitmapScale / state.mTargetDensityScale) + 0.5f) : -1;
3439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
3489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public int getIntrinsicHeight() {
3499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final Bitmap bitmap = mBitmap;
3509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final BitmapState state = mBitmapState;
3519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (!state.mAutoScale || state.mBitmapScale == Bitmap.DENSITY_SCALE_UNKNOWN) {
3539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return mBitmapHeight;
3549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        } else {
3559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return bitmap != null ? (int) (mBitmapHeight /
3569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    (state.mBitmapScale / state.mTargetDensityScale) + 0.5f) : -1;
3579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
3619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public int getOpacity() {
3629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (mBitmapState.mGravity != Gravity.FILL) {
3639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return PixelFormat.TRANSLUCENT;
3649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Bitmap bm = mBitmap;
3669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return (bm == null || bm.hasAlpha() || mBitmapState.mPaint.getAlpha() < 255) ?
3679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                PixelFormat.TRANSLUCENT : PixelFormat.OPAQUE;
3689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @Override
3719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final ConstantState getConstantState() {
3729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState.mChangingConfigurations = super.getChangingConfigurations();
3739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mBitmapState;
3749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    final static class BitmapState extends ConstantState {
3779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Bitmap mBitmap;
3789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        int mChangingConfigurations;
3799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        int mGravity = Gravity.FILL;
3809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Paint mPaint = new Paint(DEFAULT_PAINT_FLAGS);
3819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Shader.TileMode mTileModeX;
3829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Shader.TileMode mTileModeY;
3839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        boolean mAutoScale;
3849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        float mBitmapScale;
3859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        float mTargetDensityScale = 1.0f;
3869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        BitmapState(Bitmap bitmap) {
3889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mBitmap = bitmap;
3899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (bitmap != null) {
3909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                mBitmapScale = bitmap.getDensityScale();
3919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                mAutoScale = bitmap.isAutoScalingEnabled();
3929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            } else {
3939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                mBitmapScale = 1.0f;
3949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                mAutoScale = false;
3959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
3969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        BitmapState(BitmapState bitmapState) {
3999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            this(bitmapState.mBitmap);
4009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mChangingConfigurations = bitmapState.mChangingConfigurations;
4019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mGravity = bitmapState.mGravity;
4029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mTileModeX = bitmapState.mTileModeX;
4039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mTileModeY = bitmapState.mTileModeY;
4049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mTargetDensityScale = bitmapState.mTargetDensityScale;
4059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mPaint = new Paint(bitmapState.mPaint);
4069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
4079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        @Override
4099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        public Drawable newDrawable() {
4109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return new BitmapDrawable(this);
4119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
4129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        @Override
4149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        public int getChangingConfigurations() {
4159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return mChangingConfigurations;
4169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
4179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private BitmapDrawable(BitmapState state) {
4209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mBitmapState = state;
4219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        setBitmap(state.mBitmap);
4229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
424