blob: cc6b1e00af1dd1883107bd8e495b3cef6e45155d [file] [log] [blame]
/*
* Copyright (C) 2013 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.example.android.bitmapallocation;
import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.view.View;
import android.widget.CheckBox;
import android.widget.ImageView;
import android.widget.TextView;
/**
* This example shows how to speed up bitmap loading and reduce garbage collection
* by reusing existing bitmaps.
*
* Watch the associated video for this demo on the DevBytes channel of developer.android.com,
* or on YouTube at https://www.youtube.com/watch?v=rsQet4nBVi8.
*/
public class BitmapAllocation extends Activity {
// There are some assumptions in this demo app that don't carry over well to the real world:
// it assumes that all bitmaps are the same size and that loading all bitmaps as the activity
// starts is good enough. A real application would be take a more flexible and robust
// approach. But these assumptions are good enough for the purposes of this tutorial,
// which is about reusing existing bitmaps of the same size.
int mCurrentIndex = 0;
Bitmap mCurrentBitmap = null;
BitmapFactory.Options mBitmapOptions;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_bitmap_allocation);
final int[] imageIDs = {R.drawable.a, R.drawable.b, R.drawable.c, R.drawable.d,
R.drawable.e, R.drawable.f};
final CheckBox checkbox = (CheckBox) findViewById(R.id.checkbox);
final TextView durationTextview = (TextView) findViewById(R.id.loadDuration);
final ImageView imageview = (ImageView) findViewById(R.id.imageview);
// Create bitmap to be re-used, based on the size of one of the bitmaps
mBitmapOptions = new BitmapFactory.Options();
mBitmapOptions.inJustDecodeBounds = true;
BitmapFactory.decodeResource(getResources(), R.drawable.a, mBitmapOptions);
mCurrentBitmap = Bitmap.createBitmap(mBitmapOptions.outWidth,
mBitmapOptions.outHeight, Bitmap.Config.ARGB_8888);
mBitmapOptions.inJustDecodeBounds = false;
mBitmapOptions.inBitmap = mCurrentBitmap;
mBitmapOptions.inSampleSize = 1;
BitmapFactory.decodeResource(getResources(), R.drawable.a, mBitmapOptions);
imageview.setImageBitmap(mCurrentBitmap);
// When the user clicks on the image, load the next one in the list
imageview.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
mCurrentIndex = (mCurrentIndex + 1) % imageIDs.length;
BitmapFactory.Options bitmapOptions = null;
if (checkbox.isChecked()) {
// Re-use the bitmap by using BitmapOptions.inBitmap
bitmapOptions = mBitmapOptions;
bitmapOptions.inBitmap = mCurrentBitmap;
}
long startTime = System.currentTimeMillis();
mCurrentBitmap = BitmapFactory.decodeResource(getResources(),
imageIDs[mCurrentIndex], bitmapOptions);
imageview.setImageBitmap(mCurrentBitmap);
// One way you can see the difference between reusing and not is through the
// timing reported here. But you can also see a huge impact in the garbage
// collector if you look at logcat with and without reuse. Avoiding garbage
// collection when possible, especially for large items like bitmaps,
// is always a good idea.
durationTextview.setText("Load took " +
(System.currentTimeMillis() - startTime));
}
});
}
}