下面列出了怎么用android.util.LongSparseArray的API类实例代码及写法,或者点击链接到github查看源代码。
private void refreshCachedNodeLocked(int windowId, long sourceId) {
if (DEBUG) {
Log.i(LOG_TAG, "Refreshing cached node.");
}
LongSparseArray<AccessibilityNodeInfo> nodes = mNodeCache.get(windowId);
if (nodes == null) {
return;
}
AccessibilityNodeInfo cachedInfo = nodes.get(sourceId);
// If the source is not in the cache - nothing to do.
if (cachedInfo == null) {
return;
}
// The node changed so we will just refresh it right now.
if (mAccessibilityNodeRefresher.refreshNode(cachedInfo, true)) {
return;
}
// Weird, we could not refresh. Just evict the entire sub-tree.
clearSubTreeLocked(windowId, sourceId);
}
/**
* Gets a cached {@link AccessibilityNodeInfo} given the id of the hosting
* window and the accessibility id of the node.
*
* @param windowId The id of the window hosting the node.
* @param accessibilityNodeId The info accessibility node id.
* @return The cached {@link AccessibilityNodeInfo} or null if such not found.
*/
public AccessibilityNodeInfo getNode(int windowId, long accessibilityNodeId) {
synchronized(mLock) {
LongSparseArray<AccessibilityNodeInfo> nodes = mNodeCache.get(windowId);
if (nodes == null) {
return null;
}
AccessibilityNodeInfo info = nodes.get(accessibilityNodeId);
if (info != null) {
// Return a copy since the client calls to AccessibilityNodeInfo#recycle()
// will wipe the data of the cached info.
info = AccessibilityNodeInfo.obtain(info);
}
if (DEBUG) {
Log.i(LOG_TAG, "get(" + accessibilityNodeId + ") = " + info);
}
return info;
}
}
/**
* Clears nodes for the window with the given id
*/
private void clearNodesForWindowLocked(int windowId) {
if (DEBUG) {
Log.i(LOG_TAG, "clearNodesForWindowLocked(" + windowId + ")");
}
LongSparseArray<AccessibilityNodeInfo> nodes = mNodeCache.get(windowId);
if (nodes == null) {
return;
}
// Recycle the nodes before clearing the cache.
final int nodeCount = nodes.size();
for (int i = nodeCount - 1; i >= 0; i--) {
AccessibilityNodeInfo info = nodes.valueAt(i);
nodes.removeAt(i);
info.recycle();
}
mNodeCache.remove(windowId);
}
/**
* Match start/end values by Adapter item ID. Adds matched values to mStartValuesList
* and mEndValuesList and removes them from unmatchedStart and unmatchedEnd, using
* startItemIds and endItemIds as a guide for which Views have unique item IDs.
*/
private void matchItemIds(ArrayMap<View, TransitionValues> unmatchedStart,
ArrayMap<View, TransitionValues> unmatchedEnd,
LongSparseArray<View> startItemIds, LongSparseArray<View> endItemIds) {
int numStartIds = startItemIds.size();
for (int i = 0; i < numStartIds; i++) {
View startView = startItemIds.valueAt(i);
if (startView != null && isValidTarget(startView)) {
View endView = endItemIds.get(startItemIds.keyAt(i));
if (endView != null && isValidTarget(endView)) {
TransitionValues startValues = unmatchedStart.get(startView);
TransitionValues endValues = unmatchedEnd.get(endView);
if (startValues != null && endValues != null) {
mStartValuesList.add(startValues);
mEndValuesList.add(endValues);
unmatchedStart.remove(startView);
unmatchedEnd.remove(endView);
}
}
}
}
}
/**
* Adds a new entry to the cache.
*
* @param key a key that uniquely identifies the entry
* @param theme the theme against which this entry was inflated, or
* {@code null} if the entry has no theme applied
* @param entry the entry to cache
* @param usesTheme {@code true} if the entry is affected theme changes,
* {@code false} otherwise
*/
public void put(long key, @Nullable Theme theme, @NonNull T entry, boolean usesTheme) {
if (entry == null) {
return;
}
synchronized (this) {
final LongSparseArray<WeakReference<T>> entries;
if (!usesTheme) {
entries = getUnthemedLocked(true);
} else {
entries = getThemedLocked(theme, true);
}
if (entries != null) {
entries.put(key, new WeakReference<>(entry));
}
}
}
public void clearRecentSearch()
{
recentSearchObjectsById = new LongSparseArray<>();
recentSearchObjects = new ArrayList<>();
notifyDataSetChanged();
MessagesStorage.getInstance(currentAccount).getStorageQueue().postRunnable(() ->
{
try
{
MessagesStorage.getInstance(currentAccount).getDatabase().executeFast("DELETE FROM search_recent WHERE 1").stepThis().dispose();
}
catch (Exception e)
{
FileLog.e(e);
}
});
}
private void setRecentSearch(ArrayList<RecentSearchObject> arrayList, LongSparseArray<RecentSearchObject> hashMap)
{
recentSearchObjects = arrayList;
recentSearchObjectsById = hashMap;
for (int a = 0; a < recentSearchObjects.size(); a++)
{
RecentSearchObject recentSearchObject = recentSearchObjects.get(a);
if (recentSearchObject.object instanceof TLRPC.User)
{
MessagesController.getInstance(currentAccount).putUser((TLRPC.User) recentSearchObject.object, true);
}
else if (recentSearchObject.object instanceof TLRPC.Chat)
{
MessagesController.getInstance(currentAccount).putChat((TLRPC.Chat) recentSearchObject.object, true);
}
else if (recentSearchObject.object instanceof TLRPC.EncryptedChat)
{
MessagesController.getInstance(currentAccount).putEncryptedChat((TLRPC.EncryptedChat) recentSearchObject.object, true);
}
}
notifyDataSetChanged();
}
public void onResultBack(DataTransportResult arg6) {
Object v0_1;
long v2 = arg6.getDataItem().getCreateTime();
LongSparseArray v1 = TransporterClassic.a(this.a);
try {
v0_1 = TransporterClassic.a(this.a).get(v2);
TransporterClassic.a(this.a).remove(v2);
if (v0_1 == null) {
return;
}
} catch (Throwable v0) {
throw v0;
}
if (TransporterClassic.DEBUG) {
Log.d(TransporterClassic.b(this.a), "OnResultBack : " + arg6 + ", " + v0_1, new Object[0]);
}
((DataSendResultCallback) v0_1).onResultBack(arg6);
}
public void clearRecentSearch()
{
recentSearchObjectsById = new LongSparseArray<>();
recentSearchObjects = new ArrayList<>();
notifyDataSetChanged();
MessagesStorage.getInstance(currentAccount).getStorageQueue().postRunnable(() ->
{
try
{
MessagesStorage.getInstance(currentAccount).getDatabase().executeFast("DELETE FROM search_recent WHERE 1").stepThis().dispose();
}
catch (Exception e)
{
FileLog.e(e);
}
});
}
private void setRecentSearch(ArrayList<RecentSearchObject> arrayList, LongSparseArray<RecentSearchObject> hashMap)
{
recentSearchObjects = arrayList;
recentSearchObjectsById = hashMap;
for (int a = 0; a < recentSearchObjects.size(); a++)
{
RecentSearchObject recentSearchObject = recentSearchObjects.get(a);
if (recentSearchObject.object instanceof TLRPC.User)
{
MessagesController.getInstance(currentAccount).putUser((TLRPC.User) recentSearchObject.object, true);
}
else if (recentSearchObject.object instanceof TLRPC.Chat)
{
MessagesController.getInstance(currentAccount).putChat((TLRPC.Chat) recentSearchObject.object, true);
}
else if (recentSearchObject.object instanceof TLRPC.EncryptedChat)
{
MessagesController.getInstance(currentAccount).putEncryptedChat((TLRPC.EncryptedChat) recentSearchObject.object, true);
}
}
notifyDataSetChanged();
}
/**
* Returns the set of checked items ids. The result is only valid if the
* choice mode has not been set to {@link AbsListView#CHOICE_MODE_NONE} and the adapter
* has stable IDs. ({@link ListAdapter#hasStableIds()} == {@code true})
*
* @return A new array which contains the id of each checked item in the
* list.
*/
public long[] getCheckedItemIds() {
if (mChoiceMode == AbsListView.CHOICE_MODE_NONE || mCheckedIdStates == null) {
return new long[0];
}
final LongSparseArray<Integer> idStates = mCheckedIdStates;
final int count = idStates.size();
final long[] ids = new long[count];
for (int i = 0; i < count; i++) {
ids[i] = idStates.keyAt(i);
}
return ids;
}
private LongSparseArray<ThumbnailInfo> queryThumbnailInfoList() {
ContentResolver resolver = getContext().getApplicationContext().getContentResolver();
Uri uri = MediaStore.Video.Thumbnails.EXTERNAL_CONTENT_URI;
LongSparseArray<ThumbnailInfo> result = new LongSparseArray<>();
try (Cursor cursor = resolver.query(uri, null,
null, null, null)) {
if (cursor == null) {
return result;
}
if (cursor.moveToFirst()) {
do {
ThumbnailInfo info = createThumbnailInfo(cursor);
result.put(info.getId(), info);
} while (cursor.moveToNext());
}
return result;
}
}
@GuardedBy("mAm")
public boolean setMemFactorLocked(int memFactor, boolean screenOn, long now) {
mMemFactorLowered = memFactor < mLastMemOnlyState;
mLastMemOnlyState = memFactor;
if (mInjectedScreenState != null) {
screenOn = mInjectedScreenState;
}
if (screenOn) {
memFactor += ProcessStats.ADJ_SCREEN_ON;
}
if (memFactor != mProcessStats.mMemFactor) {
if (mProcessStats.mMemFactor != ProcessStats.STATE_NOTHING) {
mProcessStats.mMemFactorDurations[mProcessStats.mMemFactor]
+= now - mProcessStats.mStartTime;
}
mProcessStats.mMemFactor = memFactor;
mProcessStats.mStartTime = now;
final ArrayMap<String, SparseArray<LongSparseArray<ProcessStats.PackageState>>> pmap
= mProcessStats.mPackages.getMap();
for (int ipkg=pmap.size()-1; ipkg>=0; ipkg--) {
final SparseArray<LongSparseArray<ProcessStats.PackageState>> uids =
pmap.valueAt(ipkg);
for (int iuid=uids.size()-1; iuid>=0; iuid--) {
final LongSparseArray<ProcessStats.PackageState> vers = uids.valueAt(iuid);
for (int iver=vers.size()-1; iver>=0; iver--) {
final ProcessStats.PackageState pkg = vers.valueAt(iver);
final ArrayMap<String, ServiceState> services = pkg.mServices;
for (int isvc=services.size()-1; isvc>=0; isvc--) {
final ServiceState service = services.valueAt(isvc);
service.setMemFactor(memFactor, now);
}
}
}
}
return true;
}
return false;
}
/**
* Clears a subtree rooted at the node with the given id that is
* hosted in a given window.
*
* @param windowId The id of the hosting window.
* @param rootNodeId The root id.
*/
private void clearSubTreeLocked(int windowId, long rootNodeId) {
if (DEBUG) {
Log.i(LOG_TAG, "Clearing cached subtree.");
}
LongSparseArray<AccessibilityNodeInfo> nodes = mNodeCache.get(windowId);
if (nodes != null) {
clearSubTreeRecursiveLocked(nodes, rootNodeId);
}
}
/**
* Clears a subtree given a pointer to the root id and the nodes
* in the hosting window.
*
* @param nodes The nodes in the hosting window.
* @param rootNodeId The id of the root to evict.
*/
private void clearSubTreeRecursiveLocked(LongSparseArray<AccessibilityNodeInfo> nodes,
long rootNodeId) {
AccessibilityNodeInfo current = nodes.get(rootNodeId);
if (current == null) {
return;
}
nodes.remove(rootNodeId);
final int childCount = current.getChildCount();
for (int i = 0; i < childCount; i++) {
final long childNodeId = current.getChildId(i);
clearSubTreeRecursiveLocked(nodes, childNodeId);
}
current.recycle();
}
/**
* Returns an entry from the cache.
*
* @param key a key that uniquely identifies the entry
* @param theme the theme where the entry will be used
* @return a cached entry, or {@code null} if not in the cache
*/
@Nullable
public T get(long key, @Nullable Theme theme) {
// The themed (includes null-themed) and unthemed caches are mutually
// exclusive, so we'll give priority to whichever one we think we'll
// hit first. Since most of the framework drawables are themed, that's
// probably going to be the themed cache.
synchronized (this) {
final LongSparseArray<WeakReference<T>> themedEntries = getThemedLocked(theme, false);
if (themedEntries != null) {
final WeakReference<T> themedEntry = themedEntries.get(key);
if (themedEntry != null) {
return themedEntry.get();
}
}
final LongSparseArray<WeakReference<T>> unthemedEntries = getUnthemedLocked(false);
if (unthemedEntries != null) {
final WeakReference<T> unthemedEntry = unthemedEntries.get(key);
if (unthemedEntry != null) {
return unthemedEntry.get();
}
}
}
return null;
}
/**
* Returns the cached data for the specified theme, optionally creating a
* new entry if one does not already exist.
*
* @param t the theme for which to return cached data
* @param create {@code true} to create an entry if one does not already
* exist, {@code false} otherwise
* @return the cached data for the theme, or {@code null} if the cache is
* empty and {@code create} was {@code false}
*/
@Nullable
private LongSparseArray<WeakReference<T>> getThemedLocked(@Nullable Theme t, boolean create) {
if (t == null) {
if (mNullThemedEntries == null && create) {
mNullThemedEntries = new LongSparseArray<>(1);
}
return mNullThemedEntries;
}
if (mThemedEntries == null) {
if (create) {
mThemedEntries = new ArrayMap<>(1);
} else {
return null;
}
}
final ThemeKey key = t.getKey();
LongSparseArray<WeakReference<T>> cache = mThemedEntries.get(key);
if (cache == null && create) {
cache = new LongSparseArray<>(1);
final ThemeKey keyClone = key.clone();
mThemedEntries.put(keyClone, cache);
}
return cache;
}
private boolean pruneEntriesLocked(@Nullable LongSparseArray<WeakReference<T>> entries,
@Config int configChanges) {
if (entries == null) {
return true;
}
for (int i = entries.size() - 1; i >= 0; i--) {
final WeakReference<T> ref = entries.valueAt(i);
if (ref == null || pruneEntryLocked(ref.get(), configChanges)) {
entries.removeAt(i);
}
}
return entries.size() == 0;
}
private void returnBitmaps(final LongSparseArray<Bitmap> thumbnailList) {
new MainThreadExecutor().runTask("", new Runnable() {
@Override
public void run() {
mBitmapList = thumbnailList;
invalidate();
}
}
, 0L);
}
private boolean importWorkspace() throws Exception {
ArrayList<Long> allScreens = LauncherDbUtils.getScreenIdsFromCursor(
mContext.getContentResolver().query(mOtherScreensUri, null, null, null,
LauncherSettings.WorkspaceScreens.SCREEN_RANK));
// During import we reset the screen IDs to 0-indexed values.
if (allScreens.isEmpty()) {
// No thing to migrate
return false;
}
mHotseatSize = mMaxGridSizeX = mMaxGridSizeY = 0;
// Build screen update
ArrayList<ContentProviderOperation> screenOps = new ArrayList<>();
int count = allScreens.size();
LongSparseArray<Long> screenIdMap = new LongSparseArray<>(count);
for (int i = 0; i < count; i++) {
ContentValues v = new ContentValues();
v.put(LauncherSettings.WorkspaceScreens._ID, i);
v.put(LauncherSettings.WorkspaceScreens.SCREEN_RANK, i);
screenIdMap.put(allScreens.get(i), (long) i);
screenOps.add(ContentProviderOperation.newInsert(
LauncherSettings.WorkspaceScreens.CONTENT_URI).withValues(v).build());
}
mContext.getContentResolver().applyBatch(ProviderConfig.AUTHORITY, screenOps);
importWorkspaceItems(allScreens.get(0), screenIdMap);
GridSizeMigrationTask.markForMigration(mContext, mMaxGridSizeX, mMaxGridSizeY, mHotseatSize);
// Create empty DB flag.
LauncherSettings.Settings.call(mContext.getContentResolver(),
LauncherSettings.Settings.METHOD_CLEAR_EMPTY_DB_FLAG);
return true;
}
/**
* Builds a map of available channels.
*
* @param resolver Application's ContentResolver.
* @param inputId The ID of the TV input service that provides this TV channel.
* @return LongSparseArray mapping each channel's {@link Channels#_ID} to the Channel object.
* @hide
*/
public static LongSparseArray<Channel> buildChannelMap(
@NonNull ContentResolver resolver, @NonNull String inputId) {
Uri uri = TvContract.buildChannelsUriForInput(inputId);
LongSparseArray<Channel> channelMap = new LongSparseArray<>();
Cursor cursor = null;
try {
cursor = resolver.query(uri, Channel.PROJECTION, null, null, null);
if (cursor == null || cursor.getCount() == 0) {
if (DEBUG) {
Log.d(TAG, "Cursor is null or found no results");
}
return null;
}
while (cursor.moveToNext()) {
Channel nextChannel = Channel.fromCursor(cursor);
channelMap.put(nextChannel.getId(), nextChannel);
}
} catch (Exception e) {
Log.d(TAG, "Content provider query: " + Arrays.toString(e.getStackTrace()));
return null;
} finally {
if (cursor != null) {
cursor.close();
}
}
return channelMap;
}
@Test
public void testJobService() {
// Tests whether methods to get channels and programs are successful and valid
List<Channel> channelList = mSampleJobService.getChannels();
assertEquals(2, channelList.size());
ModelUtils.updateChannels(getActivity(), TestTvInputService.INPUT_ID, channelList, null);
LongSparseArray<Channel> channelMap = ModelUtils.buildChannelMap(
getActivity().getContentResolver(), TestTvInputService.INPUT_ID);
assertNotNull(channelMap);
assertEquals(channelMap.size(), channelList.size());
}
public static LongSparseArray<Drawable.ConstantState> hackPreloadDrawables(Resources res) {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR2) {
return hackPreloadDrawablesV15(res);
} else if (Build.VERSION.SDK_INT == Build.VERSION_CODES.JELLY_BEAN_MR2) {
return hackPreloadDrawablesV18(res);
} else {
return hackPreloadDrawablesV19(res);
}
}
public static LongSparseArray<Channel> buildChannelMap(ContentResolver resolver,
String inputId, List<Channel> channels) {
Uri uri = TvContract.buildChannelsUriForInput(inputId);
String[] projection = {
TvContract.Channels._ID,
TvContract.Channels.COLUMN_DISPLAY_NUMBER
};
LongSparseArray<Channel> channelMap = new LongSparseArray<>();
Cursor cursor = null;
try {
cursor = resolver.query(uri, projection, null, null, null);
if (cursor == null || cursor.getCount() == 0) {
return null;
}
while (cursor.moveToNext()) {
long channelId = cursor.getLong(0);
Log.d(TAG, "BUILD CHANNELS FOR "+channelId);
String channelNumber = cursor.getString(1);
channelMap.put(channelId, getChannelByNumber(channelNumber, channels));
}
} catch (Exception e) {
Log.d(TAG, "Content provider query: " + e.getStackTrace());
return null;
} finally {
if (cursor != null) {
cursor.close();
}
}
return channelMap;
}
/**
* Get Video List.
*
* @param cursorVideo Cursor Video
* @param list List
* @return counter Video data count.
*/
private int getVideoList(final Cursor cursorVideo, final List<MediaList> list) {
int counter = 0;
do {
LongSparseArray<ThumbnailInfo> thumbnails = queryThumbnailInfoList();
String lang = cursorVideo.getString(cursorVideo.getColumnIndex(MediaStore.Video.Media.LANGUAGE));
String id = cursorVideo.getString(cursorVideo.getColumnIndex(MediaStore.Video.Media._ID));
String type = cursorVideo.getString(cursorVideo.getColumnIndex(MediaStore.Video.Media.MIME_TYPE));
String title = cursorVideo.getString(cursorVideo.getColumnIndex(MediaStore.Video.Media.TITLE));
int duration = (cursorVideo.getInt(cursorVideo.getColumnIndex(MediaStore.Video.Media.DURATION)))
/ UNIT_SEC;
String artist = cursorVideo.getString(cursorVideo.getColumnIndex(MediaStore.Video.Media.ARTIST));
String thumbnailUri;
if (!cursorVideo.isNull(cursorVideo.getColumnIndex(MediaStore.Video.Media.MINI_THUMB_MAGIC))) {
int thumbnailId = cursorVideo.getInt(cursorVideo.getColumnIndex(MediaStore.Video.Media.MINI_THUMB_MAGIC));
ThumbnailInfo info = thumbnails.get(thumbnailId);
thumbnailUri = info == null ? null : info.getUri();
} else {
thumbnailUri = null;
}
list.add(new MediaList(id, type, title, artist, duration, null, lang, thumbnailUri, true));
counter++;
} while (cursorVideo.moveToNext());
return counter;
}
private LongSparseArrayIterator(LongSparseArray<E> array, int location) {
this.array = array;
if (location < 0) {
cursor = -1;
cursorNowhere = true;
} else if (location < array.size()) {
cursor = location;
cursorNowhere = false;
} else {
cursor = array.size() - 1;
cursorNowhere = true;
}
}
private Drawable getCachedDrawable(LongSparseArray<WeakReference<ConstantState>> drawableCache, long key) {
synchronized (mAccessLock) {
WeakReference<Drawable.ConstantState> wr = drawableCache.get(key);
if (wr != null) {
Drawable.ConstantState entry = wr.get();
if (entry != null) {
return entry.newDrawable(this);
} else {
drawableCache.delete(key);
}
}
}
return null;
}
/**
* Builds a map of available channels.
*
* @param resolver Application's ContentResolver.
* @param inputId The ID of the TV input service that provides this TV channel.
* @return LongSparseArray mapping each channel's {@link Channels#_ID} to the Channel object.
* @hide
*/
public static LongSparseArray<Channel> buildChannelMap(
@NonNull ContentResolver resolver, @NonNull String inputId) {
Uri uri = TvContract.buildChannelsUriForInput(inputId);
LongSparseArray<Channel> channelMap = new LongSparseArray<>();
Cursor cursor = null;
try {
cursor = resolver.query(uri, Channel.PROJECTION, null, null, null);
if (cursor == null || cursor.getCount() == 0) {
if (DEBUG) {
Log.d(TAG, "Cursor is null or found no results");
}
return null;
}
while (cursor.moveToNext()) {
Channel nextChannel = Channel.fromCursor(cursor);
channelMap.put(nextChannel.getId(), nextChannel);
}
} catch (Exception e) {
Log.d(TAG, "Content provider query: " + Arrays.toString(e.getStackTrace()));
return null;
} finally {
if (cursor != null) {
cursor.close();
}
}
return channelMap;
}
@Test
public void testJobService() {
// Tests whether methods to get channels and programs are successful and valid
List<Channel> channelList = mSampleJobService.getChannels();
assertEquals(2, channelList.size());
ModelUtils.updateChannels(getActivity(), TestTvInputService.INPUT_ID, channelList, null);
LongSparseArray<Channel> channelMap =
ModelUtils.buildChannelMap(
getActivity().getContentResolver(), TestTvInputService.INPUT_ID);
assertNotNull(channelMap);
assertEquals(channelMap.size(), channelList.size());
}
public StickersSearchAdapter(Context context, Delegate delegate, TLRPC.StickerSetCovered[] primaryInstallingStickerSets, LongSparseArray<TLRPC.StickerSetCovered> installingStickerSets, LongSparseArray<TLRPC.StickerSetCovered> removingStickerSets) {
this.context = context;
this.delegate = delegate;
this.primaryInstallingStickerSets = primaryInstallingStickerSets;
this.installingStickerSets = installingStickerSets;
this.removingStickerSets = removingStickerSets;
}