app现在基本都有版本更新这个功能,实现起来也很简单
截图效果:
1. 获取当前app的版本号
/**
* 获取版本号
*
* @throws PackageManager.NameNotFoundException
*/
public static String getVersionName(Context context) throws PackageManager.NameNotFoundException {
// 获取packagemanager的实例
PackageManager packageManager = context.getPackageManager();
// getPackageName()是你当前类的包名,0代表是获取版本信息
PackageInfo packInfo = packageManager.getPackageInfo(context.getPackageName(), 0);
String version = packInfo.versionName;
return version;
}
2.根据版本号名称判断版本高低
/**
* 版本号比较
*0代表相等,1代表version1大于version2,-1代表version1小于version2
* @param version1
* @param version2
* @return
*/
public static int compareVersion(String version1, String version2) {
if (version1.equals(version2)) {
return 0;
}
String[] version1Array = version1.split("\\.");
String[] version2Array = version2.split("\\.");
int index = 0;
// 获取最小长度值
int minLen = Math.min(version1Array.length, version2Array.length);
int diff = 0;
// 循环判断每位的大小
while (index < minLen
&& (diff = Integer.parseInt(version1Array[index])
- Integer.parseInt(version2Array[index])) == 0) {
index++;
}
if (diff == 0) {
// 如果位数不一致,比较多余位数
for (int i = index; i < version1Array.length; i++) {
if (Integer.parseInt(version1Array[i]) > 0) {
return 1;
}
}
for (int i = index; i < version2Array.length; i++) {
if (Integer.parseInt(version2Array[i]) > 0) {
return -1;
}
}
return 0;
} else {
return diff > 0 ? 1 : -1;
}
}
3.从服务器获取最新版本号
/**
* 从服务器获取版本最新的版本信息
*/
private void getVersionInfoFromServer(){
//模拟从服务器获取信息 模拟更新王者荣耀
versionInfoBean = new VersionInfoBean("1.1.1","http://dlied5.myapp.com/myapp/1104466820/sgame/2017_com.tencent.tmgp.sgame_h162_1.33.1.8_9c4c7f.apk","1.修复若干bug\n\n2.新增图片编辑功能"
,getExternalCacheDir()+"/1.1.1.jpg");
SharedPreferences sharedPreferences = getSharedPreferences("data",MODE_PRIVATE);
sharedPreferences.edit().putString("url",versionInfoBean.getDownloadUrl()).commit();
sharedPreferences.edit().putString("path",versionInfoBean.getPath()).commit();//getExternalCacheDir获取到的路径 为系统为app分配的内存 卸载app后 该目录下的资源也会删除
//比较版本信息
try {
int result = Utils.compareVersion(Utils.getVersionName(this),versionInfoBean.getVersionName());
if(result==-1){//不是最新版本
showDialog();
}else{
Toast.makeText(MainActivity.this,"已经是最新版本",Toast.LENGTH_SHORT).show();
}
} catch (PackageManager.NameNotFoundException e) {
e.printStackTrace();
}
}
private void showDialog(){
final Dialog dialog = new Dialog(MainActivity.this);
LayoutInflater inflater = (LayoutInflater)MainActivity.this
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
TextView version,content;
Button left,right;
View view = inflater.inflate(R.layout.version_update,null,false);
version = (TextView)view.findViewById(R.id.version);
content = (TextView)view.findViewById(R.id.content);
left = (Button)view.findViewById(R.id.left);
right = (Button)view.findViewById(R.id.right);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
content.setText(Html.fromHtml(versionInfoBean.getDesc(),Html.FROM_HTML_MODE_LEGACY));
}else{
content.setText(Html.fromHtml(versionInfoBean.getDesc()));
}
content.setMovementMethod(LinkMovementMethod.getInstance());
version.setText("版本号:"+versionInfoBean.getVersionName());
dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
left.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
dialog.dismiss();
}
});
right.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
dialog.dismiss();
downloadNewVersionFromServer();
}
});
dialog.setContentView(view);
dialog.setCancelable(false);
Window dialogWindow = dialog.getWindow();
dialogWindow.setGravity(Gravity.CENTER);
//dialogWindow.setWindowAnimations(R.style.ActionSheetDialogAnimation);
WindowManager.LayoutParams lp = dialogWindow.getAttributes();
WindowManager wm = (WindowManager)
getSystemService(Context.WINDOW_SERVICE);
lp.width =wm.getDefaultDisplay().getWidth()/10*9;
dialogWindow.setAttributes(lp);
dialog.show();
}
/**
* 启动服务后台下载
*/
private void downloadNewVersionFromServer(){
if(new File(versionInfoBean.getPath()).exists()){
new File(versionInfoBean.getPath()).delete();
}
Toast.makeText(MainActivity.this,"开始下载...",Toast.LENGTH_SHORT).show();
LoadingService.startUploadImg(this);
}
声明变量isLoading表示下载状态
/**
* 定义广播接收者 接受下载状态
*/
public class MyReceive extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
if("android.intent.action.loading_over".equals(action)){
isLoading = false;
}else if("android.intent.action.loading".equals(action)){
isLoading = true;
}
}
}
7.创造service
public class LoadingService extends IntentService {
private HttpUtils httpUtils;
NotificationManager nm;
private String url,path;
private SharedPreferences sharedPreferences;
public LoadingService(String name) {
super(name);
}
public LoadingService() {
super("MyService");
}
public static void startUploadImg(Context context)
{
Intent intent = new Intent(context, LoadingService.class);
context.startService(intent);
}
public void onCreate() {
super.onCreate();
httpUtils = new HttpUtils();
httpUtils.configCurrentHttpCacheExpiry(0);
nm = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
sharedPreferences = getSharedPreferences("data",MODE_PRIVATE);
}
@Override
protected void onHandleIntent(@Nullable Intent intent) {
updateApk();
}
//开始下载apk 网络请求使用的是xutils框架
private void updateApk(){
url = sharedPreferences.getString("url","");
path = sharedPreferences.getString("path","");
httpUtils.download(url,
path , new RequestCallBack() {
@Override
public void onLoading(final long total, final long current,
boolean isUploading) {
createNotification(total,current);
sendBroadcast(new Intent().setAction("android.intent.action.loading"));//发送正在下载的广播
super.onLoading(total, current, isUploading);
}
@Override
public void onSuccess(ResponseInfo arg0) {
nm.cancel(R.layout.notification_item);
Toast.makeText(LoadingService.this,"下载成功...",Toast.LENGTH_SHORT).show();
installApk();//下载成功 打开安装界面
stopSelf();//结束服务
sendBroadcast(new Intent().setAction("android.intent.action.loading_over"));//发送下载结束的广播
}
@Override
public void onFailure(HttpException arg0, String arg1) {
Toast.makeText(LoadingService.this,"下载失败...",Toast.LENGTH_SHORT).show();
sendBroadcast(new Intent().setAction("android.intent.action.loading_over"));//发送下载结束的广播
nm.cancel(R.layout.notification_item);
stopSelf();
}
});
}
/**
* 安装下载的新版本
*/
protected void installApk() {
Intent intent = new Intent();
intent.addCategory(Intent.CATEGORY_DEFAULT);
File file = new File(path);
Uri uri = Uri.fromFile(file);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setDataAndType(uri, "application/vnd.android.package-archive");
this.startActivity(intent);
}
//发送通知 实时更新通知栏下载进度
private void createNotification(final long total, final long current){
NotificationCompat.Builder builder = new NotificationCompat.Builder(this);
builder.setSmallIcon(R.mipmap.ic_launcher);//必须要设置这个属性,否则不显示
RemoteViews contentView = new RemoteViews(this.getPackageName(),R.layout.notification_item);
contentView.setProgressBar(R.id.progress, (int)total, (int)current, false);
builder.setOngoing(true);//设置左右滑动不能删除
Notification notification = builder.build();
notification.contentView = contentView;
nm.notify(R.layout.notification_item,notification);//发送通知
}
ok 大功告成 demo地址: 点击打开链接