1 /*
2  * Copyright (C) 2014 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.systemui.shared.recents.model;
18 
19 import android.util.LruCache;
20 
21 import com.android.systemui.shared.recents.model.Task.TaskKey;
22 
23 import java.io.PrintWriter;
24 
25 /**
26  * A mapping of {@link TaskKey} to value, with additional LRU functionality where the least
27  * recently referenced key/values will be evicted as more values than the given cache size are
28  * inserted.
29  *
30  * In addition, this also allows the caller to invalidate cached values for keys that have since
31  * changed.
32  */
33 public class TaskKeyLruCache<V> extends TaskKeyCache<V> {
34 
35     public interface EvictionCallback {
onEntryEvicted(TaskKey key)36         void onEntryEvicted(TaskKey key);
37     }
38 
39     private final LruCache<Integer, V> mCache;
40     private final EvictionCallback mEvictionCallback;
41 
TaskKeyLruCache(int cacheSize)42     public TaskKeyLruCache(int cacheSize) {
43         this(cacheSize, null);
44     }
45 
TaskKeyLruCache(int cacheSize, EvictionCallback evictionCallback)46     public TaskKeyLruCache(int cacheSize, EvictionCallback evictionCallback) {
47         mEvictionCallback = evictionCallback;
48         mCache = new LruCache<Integer, V>(cacheSize) {
49 
50             @Override
51             protected void entryRemoved(boolean evicted, Integer taskId, V oldV, V newV) {
52                 if (mEvictionCallback != null) {
53                     mEvictionCallback.onEntryEvicted(mKeys.get(taskId));
54                 }
55 
56                 // Only remove from mKeys on cache remove, not a cache update.
57                 if (newV == null) {
58                     mKeys.remove(taskId);
59                 }
60             }
61         };
62     }
63 
64     /** Trims the cache to a specific size */
trimToSize(int cacheSize)65     public final void trimToSize(int cacheSize) {
66         mCache.trimToSize(cacheSize);
67     }
68 
dump(String prefix, PrintWriter writer)69     public void dump(String prefix, PrintWriter writer) {
70         String innerPrefix = prefix + "  ";
71 
72         writer.print(prefix); writer.print(TAG);
73         writer.print(" numEntries="); writer.print(mKeys.size());
74         writer.println();
75         int keyCount = mKeys.size();
76         for (int i = 0; i < keyCount; i++) {
77             writer.print(innerPrefix); writer.println(mKeys.get(mKeys.keyAt(i)));
78         }
79     }
80 
81     @Override
getCacheEntry(int id)82     protected V getCacheEntry(int id) {
83         return mCache.get(id);
84     }
85 
86     @Override
putCacheEntry(int id, V value)87     protected void putCacheEntry(int id, V value) {
88         mCache.put(id, value);
89     }
90 
91     @Override
removeCacheEntry(int id)92     protected void removeCacheEntry(int id) {
93         mCache.remove(id);
94     }
95 
96     @Override
evictAllCache()97     protected void evictAllCache() {
98         mCache.evictAll();
99     }
100 }
101