summaryrefslogtreecommitdiffstats
path: root/core/java/android/content
diff options
context:
space:
mode:
authorAlan Viverette <alanv@google.com>2015-04-06 21:40:41 +0000
committerAndroid (Google) Code Review <android-gerrit@google.com>2015-04-06 21:40:45 +0000
commit863ba4c4bfdf1e1f701ec85c078aa80ba4d67e83 (patch)
tree519b60fc3bb8e821845e1da680e9b2642b80ff4e /core/java/android/content
parent3d518037fecb22eec33f860aceb34514ea76855c (diff)
parent4325f8e02a6aff999a11ad711d9e8aecc59c4ae2 (diff)
downloadframeworks_base-863ba4c4bfdf1e1f701ec85c078aa80ba4d67e83.zip
frameworks_base-863ba4c4bfdf1e1f701ec85c078aa80ba4d67e83.tar.gz
frameworks_base-863ba4c4bfdf1e1f701ec85c078aa80ba4d67e83.tar.bz2
Merge "Unify drawable caches"
Diffstat (limited to 'core/java/android/content')
-rw-r--r--core/java/android/content/res/Resources.java96
1 files changed, 53 insertions, 43 deletions
diff --git a/core/java/android/content/res/Resources.java b/core/java/android/content/res/Resources.java
index 299eb7e..334d180 100644
--- a/core/java/android/content/res/Resources.java
+++ b/core/java/android/content/res/Resources.java
@@ -117,6 +117,9 @@ public class Resources {
private static final LongSparseArray<android.content.res.ConstantState<ColorStateList>>
sPreloadedColorStateLists = new LongSparseArray<>();
+ private static final String CACHE_NOT_THEMED = "";
+ private static final String CACHE_NULL_THEME = "null_theme";
+
// Pool of TypedArrays targeted to this Resources object.
final SynchronizedPool<TypedArray> mTypedArrayPool = new SynchronizedPool<>(5);
@@ -2441,8 +2444,8 @@ public class Resources {
}
}
- // Next, check preloaded drawables. These are unthemed but may have
- // themeable attributes.
+ // Next, check preloaded drawables. These may contain unresolved theme
+ // attributes.
final ConstantState cs;
if (isColorDrawable) {
cs = sPreloadedColorDrawables.get(key);
@@ -2450,42 +2453,49 @@ public class Resources {
cs = sPreloadedDrawables[mConfiguration.getLayoutDirection()].get(key);
}
- final Drawable dr;
+ Drawable dr;
if (cs != null) {
- final Drawable clonedDr = cs.newDrawable(this);
- if (theme != null) {
- dr = clonedDr.mutate();
- dr.applyTheme(theme);
- dr.clearMutated();
- } else {
- dr = clonedDr;
- }
+ dr = cs.newDrawable(this);
} else if (isColorDrawable) {
dr = new ColorDrawable(value.data);
} else {
- dr = loadDrawableForCookie(value, id, theme);
+ dr = loadDrawableForCookie(value, id, null);
+ }
+
+ // Determine if the drawable has unresolved theme attributes. If it
+ // does, we'll need to apply a theme and store it in a theme-specific
+ // cache.
+ final String cacheKey;
+ if (!dr.canApplyTheme()) {
+ cacheKey = CACHE_NOT_THEMED;
+ } else if (theme == null) {
+ cacheKey = CACHE_NULL_THEME;
+ } else {
+ cacheKey = theme.getKey();
+ dr = dr.mutate();
+ dr.applyTheme(theme);
+ dr.clearMutated();
}
// If we were able to obtain a drawable, store it in the appropriate
- // cache (either preload or themed).
+ // cache: preload, not themed, null theme, or theme-specific.
if (dr != null) {
dr.setChangingConfigurations(value.changingConfigurations);
- cacheDrawable(value, theme, isColorDrawable, caches, key, dr);
+ cacheDrawable(value, isColorDrawable, caches, cacheKey, key, dr);
}
return dr;
}
- private void cacheDrawable(TypedValue value, Theme theme, boolean isColorDrawable,
+ private void cacheDrawable(TypedValue value, boolean isColorDrawable,
ArrayMap<String, LongSparseArray<WeakReference<ConstantState>>> caches,
- long key, Drawable dr) {
+ String cacheKey, long key, Drawable dr) {
final ConstantState cs = dr.getConstantState();
if (cs == null) {
return;
}
if (mPreloading) {
- // Preloaded drawables never have a theme, but may be themeable.
final int changingConfigs = cs.getChangingConfigurations();
if (isColorDrawable) {
if (verifyPreloadConfig(changingConfigs, 0, value.resourceId, "drawable")) {
@@ -2507,14 +2517,13 @@ public class Resources {
}
} else {
synchronized (mAccessLock) {
- final String themeKey = theme == null ? "" : theme.mKey;
- LongSparseArray<WeakReference<ConstantState>> themedCache = caches.get(themeKey);
+ LongSparseArray<WeakReference<ConstantState>> themedCache = caches.get(cacheKey);
if (themedCache == null) {
// Clean out the caches before we add more. This shouldn't
// happen very often.
pruneCaches(caches);
themedCache = new LongSparseArray<>(1);
- caches.put(themeKey, themedCache);
+ caches.put(cacheKey, themedCache);
}
themedCache.put(key, new WeakReference<>(cs));
}
@@ -2612,46 +2621,47 @@ public class Resources {
ArrayMap<String, LongSparseArray<WeakReference<ConstantState>>> caches,
long key, Theme theme) {
synchronized (mAccessLock) {
- final String themeKey = theme != null ? theme.mKey : "";
- final LongSparseArray<WeakReference<ConstantState>> themedCache = caches.get(themeKey);
- if (themedCache != null) {
- final Drawable themedDrawable = getCachedDrawableLocked(themedCache, key);
- if (themedDrawable != null) {
- return themedDrawable;
- }
+ // First search theme-agnostic cache.
+ final Drawable unthemedDrawable = getCachedDrawableLocked(
+ caches, key, CACHE_NOT_THEMED);
+ if (unthemedDrawable != null) {
+ return unthemedDrawable;
}
- // No cached drawable, we'll need to create a new one.
- return null;
+ // Next search theme-specific cache.
+ final String themeKey = theme != null ? theme.getKey() : CACHE_NULL_THEME;
+ return getCachedDrawableLocked(caches, key, themeKey);
}
}
+ private Drawable getCachedDrawableLocked(
+ ArrayMap<String, LongSparseArray<WeakReference<ConstantState>>> caches,
+ long key, String themeKey) {
+ final LongSparseArray<WeakReference<ConstantState>> cache = caches.get(themeKey);
+ if (cache != null) {
+ final ConstantState entry = getConstantStateLocked(cache, key);
+ if (entry != null) {
+ return entry.newDrawable(this);
+ }
+ }
+ return null;
+ }
+
private ConstantState getConstantStateLocked(
LongSparseArray<WeakReference<ConstantState>> drawableCache, long key) {
final WeakReference<ConstantState> wr = drawableCache.get(key);
- if (wr != null) { // we have the key
+ if (wr != null) {
final ConstantState entry = wr.get();
if (entry != null) {
- //Log.i(TAG, "Returning cached drawable @ #" +
- // Integer.toHexString(((Integer)key).intValue())
- // + " in " + this + ": " + entry);
return entry;
- } else { // our entry has been purged
+ } else {
+ // Our entry has been purged.
drawableCache.delete(key);
}
}
return null;
}
- private Drawable getCachedDrawableLocked(
- LongSparseArray<WeakReference<ConstantState>> drawableCache, long key) {
- final ConstantState entry = getConstantStateLocked(drawableCache, key);
- if (entry != null) {
- return entry.newDrawable(this);
- }
- return null;
- }
-
@Nullable
ColorStateList loadColorStateList(TypedValue value, int id, Theme theme)
throws NotFoundException {