Android获取各个应用程序的缓存文件代码小片段(使用AIDL)

import java.lang.reflect.InvocationTargetException;

import java.lang.reflect.Method;

import java.util.List;

import android.app.Activity;

import android.content.Intent;

import android.content.pm.ApplicationInfo;

import android.content.pm.IPackageDataObserver;

import android.content.pm.IPackageStatsObserver;

import android.content.pm.PackageInfo;

import android.content.pm.PackageManager;

import android.content.pm.PackageManager.NameNotFoundException;

import android.content.pm.PackageStats;

import android.net.Uri;

import android.os.Bundle;

import android.os.RemoteException;

import android.text.format.Formatter;

import android.view.View;

import android.view.View.OnClickListener;

import android.widget.ImageView;

import android.widget.LinearLayout;

import android.widget.ProgressBar;

import android.widget.TextView;

import android.widget.Toast;

public class CleanCacheActivity extends Activity {





private TextView tv_scan_status;


private ProgressBar pb;


private PackageManager pm;


private LinearLayout ll_container;


private boolean flag = false;


private long totalCleanSize = 0;


private long tempCache;


private View romoveview;


private boolean isExitsCache = true;


private Method getPackageSizeInfoMethod = null;  //API隐藏的方法


private String cleanPackgename ; //要清理缓存的包名


private Toast toast;








@Override


protected void onCreate(Bundle savedInstanceState) {


// TODO Auto-generated method stub


super.onCreate(savedInstanceState);


setContentView(R.layout.activity_clean_cache);





tv_scan_status = (TextView) findViewById(R.id.tv_scan_status);


pb = (ProgressBar) findViewById(R.id.pb);


ll_container = (LinearLayout) findViewById(R.id.ll_container);





scanCache();


}


/**


* 扫描手机里面全部应用程序的缓存信息


*/


private void scanCache() {


pm = getPackageManager();


new Thread(){


public void run() {





//1.先找到获取缓存的方法(这种方法是被API隐藏起来的。所以要先获取类的字节码。再反射)





Method[] methods = PackageManager.class.getMethods();


for(Method method : methods){


if("getPackageSizeInfo".equals(method.getName())){


getPackageSizeInfoMethod = method;


break;


}


}





//2.在每个应用程序中使用该方法获取全部的缓存文件


List<PackageInfo> packInfos = pm.getInstalledPackages(0);





pb.setMax(packInfos.size());


   int progress = 0;





for(PackageInfo packInfo : packInfos){


try {


getPackageSizeInfoMethod.invoke(pm, packInfo.packageName, new MyDataObserver()); //子线程中运行


Thread.sleep(200);


progress++;


pb.setProgress(progress);


} catch (Exception e) {


e.printStackTrace();


}


}


if(progress >= packInfos.size()){


runOnUiThread(new Runnable() {


@Override


public void run() {





tv_scan_status.setText("扫描完成...");


}


});


}


//所有扫描完成没有发现一个缓存


if(flag == false){


runOnUiThread( new Runnable() {


public void run() {





String text =  "恭喜您手机非常干净。没有缓存须要清理";


showToast(text);


tv_scan_status.setText("扫描完成。没发现缓存");


}


});


}





};


}.start();





}





//请注意,这个父类的方法是在子线程中运行的,所以要更新UI界面的话,要在主线程


private class MyDataObserver extends IPackageStatsObserver.Stub{


@Override


public void onGetStatsCompleted(final PackageStats pStats, boolean succeeded)


throws RemoteException {


final long cache = pStats.cacheSize;





final ApplicationInfo appInfo;


try {


appInfo = pm.getApplicationInfo(pStats.packageName, 0);





//更新界面


runOnUiThread(new Runnable() {


@Override


public void run() {


tv_scan_status.setText("正在扫描"+appInfo.loadLabel(pm).toString());


if(cache > 0){  //有缓存信息的应用


flag = true;//存在缓存文件


totalCleanSize += cache;








final View view = View.inflate(getApplicationContext(), R.layout.list_item_cacheinfo, null);





TextView tv_cache_size = (TextView) view.findViewById(R.id.tv_cache_size);


tv_cache_size.setText("缓存大小: "+ 


Formatter.formatFileSize(getApplicationContext(), cache));


TextView tv_name = (TextView) view.findViewById(R.id.tv_app_name);


tv_name.setText(appInfo.loadLabel(pm).toString());


ImageView iv_icon = (ImageView) view.findViewById(R.id.iv_app_icon);


iv_icon.setImageDrawable(appInfo.loadIcon(pm));


ImageView iv_clean = (ImageView) view.findViewById(R.id.iv_clean);


iv_clean.setOnClickListener(new OnClickListener() {


@Override


public void onClick(View v) {


tempCache = cache;


cleanPackgename = appInfo.packageName;


romoveview = view;


Intent intent = new Intent();


intent.setAction("android.settings.APPLICATION_DETAILS_SETTINGS");


intent.addCategory("android.intent.category.DEFAULT");


intent.setData(Uri.parse("package:" + cleanPackgename));





startActivityForResult(intent, 0);





}


});





ll_container.addView(view, 0);


}


}


});





} catch (NameNotFoundException e) {


// TODO Auto-generated catch block


e.printStackTrace();


}


}





}





//请注意。这个父类的方法是在子线程中运行的。所以要更新UI界面的话,要在主线程


private class MyDataObserver2 extends IPackageStatsObserver.Stub{


@Override


public void onGetStatsCompleted(final PackageStats pStats, boolean succeeded)


throws RemoteException {


isExitsCache = false;


System.out.println(pStats.cacheSize);


if(pStats.cacheSize > 0){   //还存在缓存


isExitsCache = true;


}


}


}





@Override


protected void onActivityResult(int requestCode, int resultCode, Intent data) {





//又一次查询一次看是否缓存已被清理


try {


getPackageSizeInfoMethod.invoke(pm, cleanPackgename, new MyDataObserver2());  //子线程中运行


Thread.sleep(200);


} catch (Exception e) {


e.printStackTrace();


}





if(isExitsCache){





}else{   //此缓存已经不存在了,更新界面


String text =  "释放了"+Formatter.formatFileSize(getApplicationContext(), tempCache)+"的内存空间";


showToast(text);


ll_container.removeView(romoveview);


}





super.onActivityResult(requestCode, resultCode, data);


}





//请注意。这个父类的方法是在子线程中运行的,所以要更新UI界面的话,要在主线程


private class MypackDataObserver extends IPackageDataObserver.Stub{


@Override


public void onRemoveCompleted(String packageName, boolean succeeded)


throws RemoteException {





runOnUiThread(new Runnable() {





@Override


public void run() {


ll_container.removeAllViews();


String text = "释放了"+ Formatter.formatFileSize(getApplicationContext(), totalCleanSize)+


"的内存空间\n恭喜您手机非常干净,没有缓存须要清理";


showToast(text);


totalCleanSize = 0;


tv_scan_status.setText("缓存清理完成");


}


});


}





}





/**


* 清理手机的所有缓存


* freeStorageAndNotify() 为系统隐藏的API,所以要用反射把它找出来


* @param view


*/


public void cleanAll(View view){





Method[] methods = PackageManager.class.getMethods();


for(Method method : methods){


if("freeStorageAndNotify".equals(method.getName())){


try {


method.invoke(pm, Integer.MAX_VALUE, new MypackDataObserver());





} catch (Exception e) {


e.printStackTrace();


}


}


}


}





private void showToast(String text) {


if(toast == null){


toast = Toast.makeText(getApplicationContext(), text, 0);


}else{


toast.setText(text);


toast.setDuration(0);


}


toast.show();


}




}

相关文章