/* * Copyright (c) 2013. wyouflf (wyouflf@gmail.com) * * 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.lidroid.xutils.bitmap; import android.app.ActivityManager; import android.content.Context; import android.text.TextUtils; import com.lidroid.xutils.bitmap.core.BitmapCache; import com.lidroid.xutils.bitmap.download.DefaultDownloader; import com.lidroid.xutils.bitmap.download.Downloader; import com.lidroid.xutils.cache.FileNameGenerator; import com.lidroid.xutils.task.Priority; import com.lidroid.xutils.task.PriorityAsyncTask; import com.lidroid.xutils.task.PriorityExecutor; import com.lidroid.xutils.util.LogUtils; import com.lidroid.xutils.util.OtherUtils; import java.util.HashMap; /** * Author: wyouflf * Date: 13-7-31 * Time: 下午11:15 */ public class BitmapGlobalConfig { private String diskCachePath; public final static int MIN_MEMORY_CACHE_SIZE = 1024 * 1024 * 2; // 2M private int memoryCacheSize = 1024 * 1024 * 4; // 4MB public final static int MIN_DISK_CACHE_SIZE = 1024 * 1024 * 10; // 10M private int diskCacheSize = 1024 * 1024 * 50; // 50M private boolean memoryCacheEnabled = true; private boolean diskCacheEnabled = true; private Downloader downloader; private BitmapCache bitmapCache; private final static int DEFAULT_POOL_SIZE = 5; private final static PriorityExecutor BITMAP_LOAD_EXECUTOR = new PriorityExecutor(DEFAULT_POOL_SIZE); private final static PriorityExecutor DISK_CACHE_EXECUTOR = new PriorityExecutor(2); private long defaultCacheExpiry = 1000L * 60 * 60 * 24 * 30; // 30 days private int defaultConnectTimeout = 1000 * 15; // 15 sec private int defaultReadTimeout = 1000 * 15; // 15 sec private FileNameGenerator fileNameGenerator; private BitmapCacheListener bitmapCacheListener; private Context mContext; private final static HashMap<String, BitmapGlobalConfig> configMap = new HashMap<String, BitmapGlobalConfig>(1); /** * @param context * @param diskCachePath If null, use default appCacheDir+"/xBitmapCache" */ private BitmapGlobalConfig(Context context, String diskCachePath) { if (context == null) throw new IllegalArgumentException("context may not be null"); this.mContext = context; this.diskCachePath = diskCachePath; initBitmapCache(); } public synchronized static BitmapGlobalConfig getInstance(Context context, String diskCachePath) { if (TextUtils.isEmpty(diskCachePath)) { diskCachePath = OtherUtils.getDiskCacheDir(context, "xBitmapCache"); } if (configMap.containsKey(diskCachePath)) { return configMap.get(diskCachePath); } else { BitmapGlobalConfig config = new BitmapGlobalConfig(context, diskCachePath); configMap.put(diskCachePath, config); return config; } } private void initBitmapCache() { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_INIT_MEMORY_CACHE); new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_INIT_DISK_CACHE); } public String getDiskCachePath() { return diskCachePath; } public Downloader getDownloader() { if (downloader == null) { downloader = new DefaultDownloader(); } downloader.setContext(mContext); downloader.setDefaultExpiry(getDefaultCacheExpiry()); downloader.setDefaultConnectTimeout(getDefaultConnectTimeout()); downloader.setDefaultReadTimeout(getDefaultReadTimeout()); return downloader; } public void setDownloader(Downloader downloader) { this.downloader = downloader; } public long getDefaultCacheExpiry() { return defaultCacheExpiry; } public void setDefaultCacheExpiry(long defaultCacheExpiry) { this.defaultCacheExpiry = defaultCacheExpiry; } public int getDefaultConnectTimeout() { return defaultConnectTimeout; } public void setDefaultConnectTimeout(int defaultConnectTimeout) { this.defaultConnectTimeout = defaultConnectTimeout; } public int getDefaultReadTimeout() { return defaultReadTimeout; } public void setDefaultReadTimeout(int defaultReadTimeout) { this.defaultReadTimeout = defaultReadTimeout; } public BitmapCache getBitmapCache() { if (bitmapCache == null) { bitmapCache = new BitmapCache(this); } return bitmapCache; } public int getMemoryCacheSize() { return memoryCacheSize; } public void setMemoryCacheSize(int memoryCacheSize) { if (memoryCacheSize >= MIN_MEMORY_CACHE_SIZE) { this.memoryCacheSize = memoryCacheSize; if (bitmapCache != null) { bitmapCache.setMemoryCacheSize(this.memoryCacheSize); } } else { this.setMemCacheSizePercent(0.3f);// Set default memory cache size. } } /** * @param percent between 0.05 and 0.8 (inclusive) */ public void setMemCacheSizePercent(float percent) { if (percent < 0.05f || percent > 0.8f) { throw new IllegalArgumentException("percent must be between 0.05 and 0.8 (inclusive)"); } this.memoryCacheSize = Math.round(percent * getMemoryClass() * 1024 * 1024); if (bitmapCache != null) { bitmapCache.setMemoryCacheSize(this.memoryCacheSize); } } public int getDiskCacheSize() { return diskCacheSize; } public void setDiskCacheSize(int diskCacheSize) { if (diskCacheSize >= MIN_DISK_CACHE_SIZE) { this.diskCacheSize = diskCacheSize; if (bitmapCache != null) { bitmapCache.setDiskCacheSize(this.diskCacheSize); } } } public int getThreadPoolSize() { return BitmapGlobalConfig.BITMAP_LOAD_EXECUTOR.getPoolSize(); } public void setThreadPoolSize(int threadPoolSize) { BitmapGlobalConfig.BITMAP_LOAD_EXECUTOR.setPoolSize(threadPoolSize); } public PriorityExecutor getBitmapLoadExecutor() { return BitmapGlobalConfig.BITMAP_LOAD_EXECUTOR; } public PriorityExecutor getDiskCacheExecutor() { return BitmapGlobalConfig.DISK_CACHE_EXECUTOR; } public boolean isMemoryCacheEnabled() { return memoryCacheEnabled; } public void setMemoryCacheEnabled(boolean memoryCacheEnabled) { this.memoryCacheEnabled = memoryCacheEnabled; } public boolean isDiskCacheEnabled() { return diskCacheEnabled; } public void setDiskCacheEnabled(boolean diskCacheEnabled) { this.diskCacheEnabled = diskCacheEnabled; } public FileNameGenerator getFileNameGenerator() { return fileNameGenerator; } public void setFileNameGenerator(FileNameGenerator fileNameGenerator) { this.fileNameGenerator = fileNameGenerator; if (bitmapCache != null) { bitmapCache.setDiskCacheFileNameGenerator(fileNameGenerator); } } public BitmapCacheListener getBitmapCacheListener() { return bitmapCacheListener; } public void setBitmapCacheListener(BitmapCacheListener bitmapCacheListener) { this.bitmapCacheListener = bitmapCacheListener; } private int getMemoryClass() { return ((ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE)).getMemoryClass(); } ////////////////////////////////// bitmap cache management task /////////////////////////////////////// private class BitmapCacheManagementTask extends PriorityAsyncTask<Object, Void, Object[]> { public static final int MESSAGE_INIT_MEMORY_CACHE = 0; public static final int MESSAGE_INIT_DISK_CACHE = 1; public static final int MESSAGE_FLUSH = 2; public static final int MESSAGE_CLOSE = 3; public static final int MESSAGE_CLEAR = 4; public static final int MESSAGE_CLEAR_MEMORY = 5; public static final int MESSAGE_CLEAR_DISK = 6; public static final int MESSAGE_CLEAR_BY_KEY = 7; public static final int MESSAGE_CLEAR_MEMORY_BY_KEY = 8; public static final int MESSAGE_CLEAR_DISK_BY_KEY = 9; private BitmapCacheManagementTask() { this.setPriority(Priority.UI_TOP); } @Override protected Object[] doInBackground(Object... params) { if (params == null || params.length == 0) return params; BitmapCache cache = getBitmapCache(); if (cache == null) return params; try { switch ((Integer) params[0]) { case MESSAGE_INIT_MEMORY_CACHE: cache.initMemoryCache(); break; case MESSAGE_INIT_DISK_CACHE: cache.initDiskCache(); break; case MESSAGE_FLUSH: cache.flush(); break; case MESSAGE_CLOSE: cache.clearMemoryCache(); cache.close(); break; case MESSAGE_CLEAR: cache.clearCache(); break; case MESSAGE_CLEAR_MEMORY: cache.clearMemoryCache(); break; case MESSAGE_CLEAR_DISK: cache.clearDiskCache(); break; case MESSAGE_CLEAR_BY_KEY: if (params.length != 2) return params; cache.clearCache(String.valueOf(params[1])); break; case MESSAGE_CLEAR_MEMORY_BY_KEY: if (params.length != 2) return params; cache.clearMemoryCache(String.valueOf(params[1])); break; case MESSAGE_CLEAR_DISK_BY_KEY: if (params.length != 2) return params; cache.clearDiskCache(String.valueOf(params[1])); break; default: break; } } catch (Throwable e) { LogUtils.e(e.getMessage(), e); } return params; } @Override protected void onPostExecute(Object[] params) { if (bitmapCacheListener == null || params == null || params.length == 0) return; try { switch ((Integer) params[0]) { case MESSAGE_INIT_MEMORY_CACHE: bitmapCacheListener.onInitMemoryCacheFinished(); break; case MESSAGE_INIT_DISK_CACHE: bitmapCacheListener.onInitDiskFinished(); break; case MESSAGE_FLUSH: bitmapCacheListener.onFlushCacheFinished(); break; case MESSAGE_CLOSE: bitmapCacheListener.onCloseCacheFinished(); break; case MESSAGE_CLEAR: bitmapCacheListener.onClearCacheFinished(); break; case MESSAGE_CLEAR_MEMORY: bitmapCacheListener.onClearMemoryCacheFinished(); break; case MESSAGE_CLEAR_DISK: bitmapCacheListener.onClearDiskCacheFinished(); break; case MESSAGE_CLEAR_BY_KEY: if (params.length != 2) return; bitmapCacheListener.onClearCacheFinished(String.valueOf(params[1])); break; case MESSAGE_CLEAR_MEMORY_BY_KEY: if (params.length != 2) return; bitmapCacheListener.onClearMemoryCacheFinished(String.valueOf(params[1])); break; case MESSAGE_CLEAR_DISK_BY_KEY: if (params.length != 2) return; bitmapCacheListener.onClearDiskCacheFinished(String.valueOf(params[1])); break; default: break; } } catch (Throwable e) { LogUtils.e(e.getMessage(), e); } } } public void clearCache() { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_CLEAR); } public void clearMemoryCache() { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_CLEAR_MEMORY); } public void clearDiskCache() { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_CLEAR_DISK); } public void clearCache(String uri) { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_CLEAR_BY_KEY, uri); } public void clearMemoryCache(String uri) { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_CLEAR_MEMORY_BY_KEY, uri); } public void clearDiskCache(String uri) { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_CLEAR_DISK_BY_KEY, uri); } public void flushCache() { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_FLUSH); } public void closeCache() { new BitmapCacheManagementTask().execute(BitmapCacheManagementTask.MESSAGE_CLOSE); } }