除了上面这个RecycleBitmapDrawable之外呢,我们还需要一个自定义的ImageView来控制什么时候显示Bitmap以及什么时候隐藏Bitmap对象
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
|
package com.example.bitmap;
import
import
import
import
import
public class RecycleImageView extends ImageView {
public RecycleImageView(Context context) {
super (context);
}
public RecycleImageView(Context context, AttributeSet attrs) {
super (context, attrs);
}
public RecycleImageView(Context context, AttributeSet attrs, int defStyle) {
super (context, attrs, defStyle);
}
@Override
public void setImageDrawable(Drawable drawable) {
Drawable previousDrawable = getDrawable();
super .setImageDrawable(drawable);
//显示新的drawable
notifyDrawable(drawable, true );
//回收之前的图片
notifyDrawable(previousDrawable, false );
}
@Override
protected void onDetachedFromWindow() {
//当View从窗口脱离的时候,清除drawable
setImageDrawable( null );
super .onDetachedFromWindow();
}
/**
* 通知该drawable显示或者隐藏
*
* @param drawable
* @param isDisplayed
*/
public static void notifyDrawable(Drawable drawable, boolean isDisplayed) {
if (drawable instanceof Recycle
((Recycle
} else if (drawable instanceof LayerDrawable) {
LayerDrawable layerDrawable = (LayerDrawable) drawable;
for ( int i = 0 , z = layerDrawable.getNumberOfLayers(); i < z; i++) {
notifyDrawable(layerDrawable.getDrawable(i), isDisplayed);
}
}
}
}
|
这个自定类也比较简单,重写了setImageDrawable()方法,在这个方法中我们先获取ImageView上面的图片,然后通知之前显示在ImageView的Drawable不在显示了,Drawable会判断是否需要调用recycle(),当View从Window脱离的时候会回调onDetachedFromWindow(),我们在这个方法中回收显示在ImageView的图片,具体的使用方法
1
2
3
|
ImageView imageView = new ImageView(context);
imageView.setImageDrawable( new Recycle
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
|
package com.example.bitmap;
import java.lang.ref.SoftReference;
import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
import
import
import
import
import
import
import
public class ImageCache {
private final static int MAX_MEMORY = 4 * 102 * 1024 ;
private LruCache private Set private void init() {
if (hasHoneycomb()) {
mReusable
.synchronizedSet( new HashSet }
mMemoryCache = new LruCache /**
* 当保存的BitmapDrawable对象从LruCache中移除出来的时候回调的方法
*/
@Override
protected void entryRemoved( boolean evicted, String key,
if (hasHoneycomb()) {
mReusable new SoftReference<
}
}
};
}
/**
* @param options
* @return
*/
protected
if (mReusable null && !mReusable
synchronized (mReusable
final Iterator .iterator();
while (iterator.hasNext()) {
item = iterator.next().get();
if ( null != item && item.isMutable()) {
if (canUseForIn
bitmap = item;
iterator.remove();
break ;
}
} else {
iterator.remove();
}
}
}
}
return bitmap;
}
/**
*
* @param candidate
* @param targetOptions
* @return
*/
@TargetApi (VERSION_CODES.KITKAT)
public static boolean canUseForIn
// 没有限制
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
int width = targetOptions.outWidth / targetOptions.inSampleSize;
int height = targetOptions.outHeight / targetOptions.inSampleSize;
int byteCount = width * height
* getBytesPerPixel(candidate.getConfig());
return byteCount <= candidate.getAllocationByteCount();
}
// 在Android
return candidate.getWidth() == targetOptions.outWidth
&& candidate.getHeight() == targetOptions.outHeight
&& targetOptions.inSampleSize == 1 ;
}
/**
* 获取每个像素所占用的Byte数
*
* @param config
* @return
*/
public static int getBytesPerPixel(Config config) {
if (config == Config.ARGB_8888) {
return 4 ;
} else if (config == Config.RGB_565) {
return 2 ;
} else if (config == Config.ARGB_4444) {
return 2 ;
} else if (config == Config.ALPHA_8) {
return 1 ;
}
return 1 ;
}
@TargetApi (VERSION_CODES.HONEYCOMB)
public static boolean hasHoneycomb() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB;
}
}
|