summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMark Wei <markwei@google.com>2013-10-30 14:23:50 -0700
committerMark Wei <markwei@google.com>2013-10-31 17:35:05 -0700
commit2e4d0863dba53435372ec96538f2ef3e1c3675bf (patch)
tree6d7bbae6bcb78563036ffe5f685ef1a334bd512c /src
parent22955165fab693684cc3614c84ee81883ae933c8 (diff)
downloadbitmap-2e4d0863dba53435372ec96538f2ef3e1c3675bf.tar.gz
Make ExtendedBitmapDrawable extend BasicBitmapDrawable.
Modify sample app to use ExtendedBitmapDrawable with the following features: Parallax, Placholder and progress, Decode aggregator. Change-Id: Ia9e0fe6e6fdab018077a465ddf2a40109efbddf7
Diffstat (limited to 'src')
-rw-r--r--src/com/android/bitmap/DecodeTask.java15
-rw-r--r--src/com/android/bitmap/drawable/BasicBitmapDrawable.java163
-rw-r--r--src/com/android/bitmap/drawable/ExtendedBitmapDrawable.java281
3 files changed, 173 insertions, 286 deletions
diff --git a/src/com/android/bitmap/DecodeTask.java b/src/com/android/bitmap/DecodeTask.java
index 76d6019..87beac1 100644
--- a/src/com/android/bitmap/DecodeTask.java
+++ b/src/com/android/bitmap/DecodeTask.java
@@ -134,16 +134,20 @@ public class DecodeTask extends AsyncTask<Void, Void, ReusableBitmap> {
}
}
- Trace.beginSection("create fd and stream");
if (mFactory != null) {
+ Trace.beginSection("create fd");
fd = mFactory.createFileDescriptor();
+ Trace.endSection();
} else {
in = reset(in);
if (in == null) {
return null;
}
}
- Trace.endSection();
+
+ if (isCancelled()) {
+ return null;
+ }
Trace.beginSection("get bytesize");
final long byteSize;
@@ -198,6 +202,9 @@ public class DecodeTask extends AsyncTask<Void, Void, ReusableBitmap> {
if (in == null) {
return null;
}
+ if (isCancelled()) {
+ return null;
+ }
}
Trace.beginSection("decodeBounds");
@@ -286,8 +293,12 @@ public class DecodeTask extends AsyncTask<Void, Void, ReusableBitmap> {
if (in == null) {
return null;
}
+ if (isCancelled()) {
+ return null;
+ }
}
+
Bitmap decodeResult = null;
final Rect srcRect = new Rect(); // Not orientation corrected. True coordinates.
if (CROP_DURING_DECODE) {
diff --git a/src/com/android/bitmap/drawable/BasicBitmapDrawable.java b/src/com/android/bitmap/drawable/BasicBitmapDrawable.java
index a7cfb48..53ab38d 100644
--- a/src/com/android/bitmap/drawable/BasicBitmapDrawable.java
+++ b/src/com/android/bitmap/drawable/BasicBitmapDrawable.java
@@ -57,12 +57,15 @@ import java.util.concurrent.TimeUnit;
*/
public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
Drawable.Callback, RequestKey.Callback {
+
protected static Rect sRect;
protected RequestKey mCurrKey;
- protected final Paint mPaint = new Paint();
+ protected RequestKey mPrevKey;
+ protected final Paint mPaint = new Paint();
private final BitmapCache mCache;
+
private final boolean mLimitDensity;
private final float mDensity;
private ReusableBitmap mBitmap;
@@ -83,6 +86,7 @@ public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
private static final int MAX_BITMAP_DENSITY = DisplayMetrics.DENSITY_HIGH;
private static final float VERTICAL_CENTER = 1f / 2;
+ private static final float NO_MULTIPLIER = 1f;
private static final String TAG = BasicBitmapDrawable.class.getSimpleName();
private static final boolean DEBUG = DecodeTask.DEBUG;
@@ -105,6 +109,10 @@ public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
return mCurrKey;
}
+ protected ReusableBitmap getBitmap() {
+ return mBitmap;
+ }
+
/**
* Set the dimensions to decode into.
*/
@@ -122,7 +130,7 @@ public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
setImage(key);
}
- private void setImage(final RequestKey key) {
+ protected void setImage(final RequestKey key) {
if (mCurrKey != null && mCurrKey.equals(key)) {
return;
}
@@ -134,6 +142,8 @@ public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
mBitmap = null;
}
Trace.endSection();
+
+ mPrevKey = mCurrKey;
mCurrKey = key;
if (mTask != null) {
@@ -168,6 +178,79 @@ public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
Trace.endSection();
}
+ protected void setBitmap(ReusableBitmap bmp) {
+ if (mBitmap != null && mBitmap != bmp) {
+ mBitmap.releaseReference();
+ }
+ mBitmap = bmp;
+ invalidateSelf();
+ }
+
+ protected void loadFileDescriptorFactory() {
+ if (mCurrKey == null || mDecodeWidth == 0 || mDecodeHeight == 0) {
+ return;
+ }
+
+ // Create file descriptor if request supports it.
+ mCreateFileDescriptorFactoryTask = mCurrKey
+ .createFileDescriptorFactoryAsync(mCurrKey, this);
+ if (mCreateFileDescriptorFactoryTask == null) {
+ // Use input stream if request does not.
+ decode(null);
+ }
+ }
+
+ @Override
+ public void fileDescriptorFactoryCreated(final RequestKey key,
+ final FileDescriptorFactory factory) {
+ if (mCreateFileDescriptorFactoryTask == null) {
+ // Cancelled.
+ return;
+ }
+ mCreateFileDescriptorFactoryTask = null;
+
+ if (key.equals(mCurrKey)) {
+ decode(factory);
+ }
+ }
+
+ protected void decode(final FileDescriptorFactory factory) {
+ Trace.beginSection("decode");
+ final int bufferW;
+ final int bufferH;
+ if (mLimitDensity) {
+ final float scale =
+ Math.min(1f, (float) MAX_BITMAP_DENSITY / DisplayMetrics.DENSITY_DEFAULT
+ / mDensity);
+ bufferW = (int) (mDecodeWidth * scale);
+ bufferH = (int) (mDecodeHeight * scale);
+ } else {
+ bufferW = mDecodeWidth;
+ bufferH = mDecodeHeight;
+ }
+
+ if (mTask != null) {
+ mTask.cancel();
+ }
+ final DecodeOptions opts = new DecodeOptions(bufferW, bufferH, getDecodeVerticalCenter(),
+ DecodeOptions.STRATEGY_ROUND_NEAREST);
+ mTask = new DecodeTask(mCurrKey, opts, factory, this, mCache);
+ mTask.executeOnExecutor(EXECUTOR);
+ Trace.endSection();
+ }
+
+ protected float getDrawVerticalCenter() {
+ return VERTICAL_CENTER;
+ }
+
+ protected float getDrawVerticalOffsetMultiplier() {
+ return NO_MULTIPLIER;
+ }
+
+ protected float getDecodeVerticalCenter() {
+ return VERTICAL_CENTER;
+ }
+
@Override
public void draw(final Canvas canvas) {
final Rect bounds = getBounds();
@@ -180,8 +263,8 @@ public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
mBitmap.getLogicalWidth(), mBitmap.getLogicalHeight(),
bounds.width(), bounds.height(),
bounds.height(), Integer.MAX_VALUE,
- VERTICAL_CENTER, false /* absoluteFraction */,
- 1, sRect);
+ getDrawVerticalCenter(), false /* absoluteFraction */,
+ getDrawVerticalOffsetMultiplier(), sRect);
final int orientation = mBitmap.getOrientation();
// calculateCroppedSrcRect() gave us the source rectangle "as if" the orientation has
@@ -243,78 +326,6 @@ public class BasicBitmapDrawable extends Drawable implements DecodeCallback,
@Override
public void onDecodeCancel(final RequestKey key) { }
- protected ReusableBitmap getBitmap() {
- return mBitmap;
- }
-
- private void setBitmap(ReusableBitmap bmp) {
- if (mBitmap != null && mBitmap != bmp) {
- mBitmap.releaseReference();
- }
- mBitmap = bmp;
- invalidateSelf();
- }
-
- private void loadFileDescriptorFactory() {
- if (mCurrKey == null) {
- return;
- }
- if (mDecodeWidth == 0 || mDecodeHeight == 0) {
- return;
- }
-
- // Create file descriptor if request supports it.
- mCreateFileDescriptorFactoryTask = mCurrKey
- .createFileDescriptorFactoryAsync(mCurrKey, this);
- if (mCreateFileDescriptorFactoryTask == null) {
- // Use input stream if request does not.
- decode(null);
- }
- }
-
- @Override
- public void fileDescriptorFactoryCreated(final RequestKey key,
- final FileDescriptorFactory factory) {
- if (mCreateFileDescriptorFactoryTask == null) {
- // Cancelled.
- return;
- }
- mCreateFileDescriptorFactoryTask = null;
-
- if (key.equals(mCurrKey)) {
- decode(factory);
- }
- }
-
- private void decode(final FileDescriptorFactory factory) {
- Trace.beginSection("decode");
- final int bufferW;
- final int bufferH;
- if (mLimitDensity) {
- final float scale =
- Math.min(1f, (float) MAX_BITMAP_DENSITY / DisplayMetrics.DENSITY_DEFAULT
- / mDensity);
- bufferW = (int) (mDecodeWidth * scale);
- bufferH = (int) (mDecodeHeight * scale);
- } else {
- bufferW = mDecodeWidth;
- bufferH = mDecodeHeight;
- }
-
- if (bufferW == 0 || bufferH == 0) {
- Trace.endSection();
- return;
- }
- if (mTask != null) {
- mTask.cancel();
- }
- final DecodeOptions opts = new DecodeOptions(bufferW, bufferH, VERTICAL_CENTER,
- DecodeOptions.STRATEGY_ROUND_NEAREST);
- mTask = new DecodeTask(mCurrKey, opts, factory, this, mCache);
- mTask.executeOnExecutor(EXECUTOR);
- Trace.endSection();
- }
-
@Override
public void invalidateDrawable(Drawable who) {
invalidateSelf();
diff --git a/src/com/android/bitmap/drawable/ExtendedBitmapDrawable.java b/src/com/android/bitmap/drawable/ExtendedBitmapDrawable.java
index 59b65bc..6f52061 100644
--- a/src/com/android/bitmap/drawable/ExtendedBitmapDrawable.java
+++ b/src/com/android/bitmap/drawable/ExtendedBitmapDrawable.java
@@ -23,31 +23,21 @@ import android.animation.ValueAnimator.AnimatorUpdateListener;
import android.content.res.Resources;
import android.graphics.Canvas;
import android.graphics.ColorFilter;
-import android.graphics.Paint;
-import android.graphics.PixelFormat;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;
import android.os.Handler;
-import android.util.DisplayMetrics;
import android.util.Log;
import android.view.animation.LinearInterpolator;
import com.android.bitmap.BitmapCache;
import com.android.bitmap.DecodeAggregator;
import com.android.bitmap.DecodeTask;
-import com.android.bitmap.DecodeTask.DecodeOptions;
import com.android.bitmap.R;
import com.android.bitmap.RequestKey;
+import com.android.bitmap.RequestKey.FileDescriptorFactory;
import com.android.bitmap.ReusableBitmap;
-import com.android.bitmap.util.BitmapUtils;
-import com.android.bitmap.util.RectUtils;
import com.android.bitmap.util.Trace;
-import java.util.concurrent.Executor;
-import java.util.concurrent.LinkedBlockingQueue;
-import java.util.concurrent.ThreadPoolExecutor;
-import java.util.concurrent.TimeUnit;
-
/**
* This class encapsulates all functionality needed to display a single image bitmap,
* including request creation/cancelling, data unbinding and re-binding, and fancy animations
@@ -56,47 +46,27 @@ import java.util.concurrent.TimeUnit;
* The actual bitmap decode work is handled by {@link DecodeTask}.
* TODO: have this class extend from BasicBitmapDrawable
*/
-public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.DecodeCallback,
- Drawable.Callback, Runnable, Parallaxable, DecodeAggregator.Callback {
-
- private RequestKey mCurrKey;
+public class ExtendedBitmapDrawable extends BasicBitmapDrawable implements
+ Runnable, Parallaxable, DecodeAggregator.Callback {
- private ReusableBitmap mBitmap;
- private final BitmapCache mCache;
- private final boolean mLimitDensity;
+ // Ordered display.
private DecodeAggregator mDecodeAggregator;
- private DecodeTask mTask;
- private int mDecodeWidth;
- private int mDecodeHeight;
- private int mLoadState = LOAD_STATE_UNINITIALIZED;
+
+ // Parallax.
private float mParallaxFraction = 0.5f;
private float mParallaxSpeedMultiplier;
+ private static final float DECODE_VERTICAL_CENTER = 1f / 3;
- // each attachment gets its own placeholder and progress indicator, to be shown, hidden,
- // and animated based on Drawable#setVisible() changes, which are in turn driven by
- // #setLoadState().
- private Placeholder mPlaceholder;
- private Progress mProgress;
-
- private static final Executor SMALL_POOL_EXECUTOR = new ThreadPoolExecutor(4, 4,
- 1, TimeUnit.SECONDS, new LinkedBlockingQueue<Runnable>());
-
- private static final Executor EXECUTOR = SMALL_POOL_EXECUTOR;
-
- private static final int MAX_BITMAP_DENSITY = DisplayMetrics.DENSITY_HIGH;
-
- private static final float VERTICAL_CENTER = 1f / 3;
-
+ // Placeholder and progress.
private static final int LOAD_STATE_UNINITIALIZED = 0;
private static final int LOAD_STATE_NOT_YET_LOADED = 1;
private static final int LOAD_STATE_LOADING = 2;
private static final int LOAD_STATE_LOADED = 3;
private static final int LOAD_STATE_FAILED = 4;
-
- private final float mDensity;
+ private int mLoadState = LOAD_STATE_UNINITIALIZED;
+ private Placeholder mPlaceholder;
+ private Progress mProgress;
private int mProgressDelayMs;
- private final Paint mPaint = new Paint();
- private final Rect mSrcRect = new Rect();
private final Handler mHandler = new Handler();
public static final boolean DEBUG = false;
@@ -105,12 +75,12 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
public ExtendedBitmapDrawable(final Resources res, final BitmapCache cache,
final boolean limitDensity, final DecodeAggregator decodeAggregator,
final Drawable placeholder, final Drawable progress) {
- mDensity = res.getDisplayMetrics().density;
- mCache = cache;
- mLimitDensity = limitDensity;
+ super(res, cache, limitDensity);
+
+ // Ordered display.
this.mDecodeAggregator = decodeAggregator;
- mPaint.setFilterBitmap(true);
+ // Placeholder and progress.
final int fadeOutDurationMs = res.getInteger(R.integer.bitmap_fade_animation_duration);
final int tileColor = res.getColor(R.color.bitmap_placeholder_background_color);
mProgressDelayMs = res.getInteger(R.integer.bitmap_progress_animation_delay);
@@ -126,91 +96,82 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
mProgress.setCallback(this);
}
- public RequestKey getKey() {
- return mCurrKey;
- }
-
- /**
- * Set the dimensions to which to decode into. For a parallax effect, ensure the height is
- * larger than the destination of the bitmap.
- * TODO: test parallax
- */
- public void setDecodeDimensions(int w, int h) {
- mDecodeWidth = w;
- mDecodeHeight = h;
- decode();
+ @Override
+ public void setParallaxFraction(float fraction) {
+ mParallaxFraction = fraction;
+ invalidateSelf();
}
public void setParallaxSpeedMultiplier(final float parallaxSpeedMultiplier) {
mParallaxSpeedMultiplier = parallaxSpeedMultiplier;
+ invalidateSelf();
}
+ /**
+ * This sets the drawable to the failed state, which remove all animations from the placeholder.
+ * This is different from unbinding to the uninitialized state, where we expect animations.
+ */
public void showStaticPlaceholder() {
setLoadState(LOAD_STATE_FAILED);
}
- public void unbind() {
- setImage(null);
- }
-
- public void bind(RequestKey key) {
- setImage(key);
- }
-
- private void setImage(final RequestKey key) {
+ @Override
+ protected void setImage(final RequestKey key) {
if (mCurrKey != null && mCurrKey.equals(key)) {
return;
}
- Trace.beginSection("set image");
- Trace.beginSection("release reference");
- if (mBitmap != null) {
- mBitmap.releaseReference();
- mBitmap = null;
- }
- Trace.endSection();
if (mCurrKey != null && mDecodeAggregator != null) {
mDecodeAggregator.forget(mCurrKey);
}
- mCurrKey = key;
-
- if (mTask != null) {
- mTask.cancel();
- mTask = null;
- }
mHandler.removeCallbacks(this);
// start from a clean slate on every bind
// this allows the initial transition to be specially instantaneous, so e.g. a cache hit
// doesn't unnecessarily trigger a fade-in
setLoadState(LOAD_STATE_UNINITIALIZED);
-
if (key == null) {
- invalidateSelf();
- Trace.endSection();
- return;
+ setLoadState(LOAD_STATE_FAILED);
}
- // find cached entry here and skip decode if found.
- final ReusableBitmap cached = mCache.get(key, true /* incrementRefCount */);
- if (cached != null) {
- setBitmap(cached);
- if (DEBUG) {
- Log.d(TAG, String.format("CACHE HIT key=%s", mCurrKey));
- }
- } else {
- decode();
- if (DEBUG) {
- Log.d(TAG, String.format(
- "CACHE MISS key=%s\ncache=%s", mCurrKey, mCache.toDebugString()));
- }
+ super.setImage(key);
+ }
+
+ @Override
+ protected void setBitmap(ReusableBitmap bmp) {
+ setLoadState((bmp != null) ? LOAD_STATE_LOADED : LOAD_STATE_FAILED);
+
+ super.setBitmap(bmp);
+ }
+
+ @Override
+ protected void decode(final FileDescriptorFactory factory) {
+ boolean executeStateChange = shouldExecuteStateChange();
+ if (executeStateChange) {
+ setLoadState(LOAD_STATE_NOT_YET_LOADED);
}
- Trace.endSection();
+
+ super.decode(factory);
+ }
+
+ protected boolean shouldExecuteStateChange() {
+ // TODO: AttachmentDrawable should override this method to match prev and curr request keys.
+ return /* opts.stateChanges */ true;
}
@Override
- public void setParallaxFraction(float fraction) {
- mParallaxFraction = fraction;
+ public float getDrawVerticalCenter() {
+ return mParallaxFraction;
+ }
+
+ @Override
+ protected float getDrawVerticalOffsetMultiplier() {
+ return mParallaxSpeedMultiplier;
+ }
+
+ @Override
+ protected float getDecodeVerticalCenter() {
+ return DECODE_VERTICAL_CENTER;
}
@Override
@@ -220,32 +181,7 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
return;
}
- if (mBitmap != null && mBitmap.bmp != null) {
- BitmapUtils.calculateCroppedSrcRect(
- mBitmap.getLogicalWidth(), mBitmap.getLogicalHeight(),
- bounds.width(), bounds.height(),
- bounds.height(), Integer.MAX_VALUE,
- mParallaxFraction, false /* absoluteFraction */,
- mParallaxSpeedMultiplier, mSrcRect);
-
- final int orientation = mBitmap.getOrientation();
- // calculateCroppedSrcRect() gave us the source rectangle "as if" the orientation has
- // been corrected. We need to decode the uncorrected source rectangle. Calculate true
- // coordinates.
- RectUtils.rotateRectForOrientation(orientation,
- new Rect(0, 0, mBitmap.getLogicalWidth(), mBitmap.getLogicalHeight()),
- mSrcRect);
-
- // We may need to rotate the canvas, so we also have to rotate the bounds.
- final Rect rotatedBounds = new Rect(bounds);
- RectUtils.rotateRect(orientation, bounds.centerX(), bounds.centerY(), rotatedBounds);
-
- // Rotate the canvas.
- canvas.save();
- canvas.rotate(orientation, bounds.centerX(), bounds.centerY());
- canvas.drawBitmap(mBitmap.bmp, mSrcRect, rotatedBounds, mPaint);
- canvas.restore();
- }
+ super.draw(canvas);
// Draw the two possible overlay layers in reverse-priority order.
// (each layer will no-op the draw when appropriate)
@@ -257,7 +193,7 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
@Override
public void setAlpha(int alpha) {
final int old = mPaint.getAlpha();
- mPaint.setAlpha(alpha);
+ super.setAlpha(alpha);
mPlaceholder.setAlpha(alpha);
mProgress.setAlpha(alpha);
if (alpha != old) {
@@ -267,19 +203,13 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
@Override
public void setColorFilter(ColorFilter cf) {
- mPaint.setColorFilter(cf);
+ super.setColorFilter(cf);
mPlaceholder.setColorFilter(cf);
mProgress.setColorFilter(cf);
invalidateSelf();
}
@Override
- public int getOpacity() {
- return (mBitmap != null && (mBitmap.bmp.hasAlpha() || mPaint.getAlpha() < 255)) ?
- PixelFormat.TRANSLUCENT : PixelFormat.OPAQUE;
- }
-
- @Override
protected void onBoundsChange(Rect bounds) {
super.onBoundsChange(bounds);
@@ -294,6 +224,7 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
} else {
onBecomeFirstExpected(key);
}
+ super.onDecodeBegin(key);
}
@Override
@@ -319,7 +250,7 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
mDecodeAggregator.execute(key, new Runnable() {
@Override
public void run() {
- onDecodeCompleteImpl(key, result);
+ ExtendedBitmapDrawable.super.onDecodeComplete(key, result);
}
@Override
@@ -328,19 +259,7 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
}
});
} else {
- onDecodeCompleteImpl(key, result);
- }
- }
-
- private void onDecodeCompleteImpl(final RequestKey key, final ReusableBitmap result) {
- if (key.equals(mCurrKey)) {
- setBitmap(result);
- } else {
- // if the requests don't match (i.e. this request is stale), decrement the
- // ref count to allow the bitmap to be pooled
- if (result != null) {
- result.releaseReference();
- }
+ super.onDecodeComplete(key, result);
}
}
@@ -349,53 +268,14 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
if (mDecodeAggregator != null) {
mDecodeAggregator.forget(key);
}
+ super.onDecodeCancel(key);
}
- private void setBitmap(ReusableBitmap bmp) {
- if (mBitmap != null && mBitmap != bmp) {
- mBitmap.releaseReference();
- }
- mBitmap = bmp;
- setLoadState((bmp != null) ? LOAD_STATE_LOADED : LOAD_STATE_FAILED);
- invalidateSelf();
- }
-
- private void decode() {
- final int bufferW;
- final int bufferH;
-
- if (mCurrKey == null) {
- return;
- }
-
- Trace.beginSection("decode");
- if (mLimitDensity) {
- final float scale =
- Math.min(1f, (float) MAX_BITMAP_DENSITY / DisplayMetrics.DENSITY_DEFAULT
- / mDensity);
- bufferW = (int) (mDecodeWidth * scale);
- bufferH = (int) (mDecodeHeight * scale);
- } else {
- bufferW = mDecodeWidth;
- bufferH = mDecodeHeight;
- }
-
- if (bufferW == 0 || bufferH == 0) {
- Trace.endSection();
- return;
- }
- if (mTask != null) {
- mTask.cancel();
- }
- setLoadState(LOAD_STATE_NOT_YET_LOADED);
- final DecodeOptions opts = new DecodeOptions(bufferW, bufferH, VERTICAL_CENTER,
- DecodeOptions.STRATEGY_ROUND_NEAREST);
- // TODO: file is null because we expect this class to extend BasicBitmapDrawable soon.
- mTask = new DecodeTask(mCurrKey, opts, null /* file */, this, mCache);
- mTask.executeOnExecutor(EXECUTOR);
- Trace.endSection();
- }
-
+ /**
+ * Each attachment gets its own placeholder and progress indicator, to be shown, hidden,
+ * and animated based on Drawable#setVisible() changes, which are in turn driven by
+ * setLoadState().
+ */
private void setLoadState(int loadState) {
if (DEBUG) {
Log.v(TAG, String.format("IN setLoadState. old=%s new=%s key=%s this=%s",
@@ -448,21 +328,6 @@ public class ExtendedBitmapDrawable extends Drawable implements DecodeTask.Decod
}
}
- @Override
- public void invalidateDrawable(Drawable who) {
- invalidateSelf();
- }
-
- @Override
- public void scheduleDrawable(Drawable who, Runnable what, long when) {
- scheduleSelf(what, when);
- }
-
- @Override
- public void unscheduleDrawable(Drawable who, Runnable what) {
- unscheduleSelf(what);
- }
-
private static class Placeholder extends TileDrawable {
private final ValueAnimator mPulseAnimator;