android端 版本升级
由于项目中要求实现版本升级,特写此代码,有因为这段代码基本都是通用,所以记录下来,以便下次直接拷贝...
public class ApkVersionUpdate { /** apk文件下载状态:正在下载 */
private static final int DOWNLOADING = 1; /** apk文件下载状态:已完成下载 */
private static final int DOWNLOADED = 2; /** 客户端保存到sd卡的路径 */
private String savePath; /** 下载文件对话框 */
private Dialog downloadDialog; /** 下载进度条 */
private ProgressBar downloadProgressBar; /** 下载文件时的进度值 */
private int progress; /** 是否取消更新,默认为否 */
private boolean cancelUpdate = false; private Context mContext;
private OkHttpHelper httpHelper = OkHttpHelper.getInstance();
private String downloadurl;
private String clientVersionCode;
private String desc;
private String apkName="sanxin"; public ApkVersionUpdate(Context context) {
mContext = context;
getPackageManage();
} public void checkVersion(final boolean showProgressDialog) {
final Message msg = Message.obtain();
Map<String,Object> params = new HashMap<>();
params.put("ports","children");
httpHelper.post(HttpUrl.version_url_http, params, new SimpleCallback<Version>(mContext) {
@Override
public void onSuccess(Response response, Version item) {
if(item.getResult()==0){
List<Version.VersionItem> list = item.getList();
Version.VersionItem versionItem = list.get(0);
String serverVersionCode = versionItem.getVersion(); downloadurl =versionItem.getDownloadurl();
desc = versionItem.getDesc();
Log.e("版本",clientVersionCode+"--"+serverVersionCode); // 当最新版本号大于当前版本号时,提示更新
if (!serverVersionCode.equals(clientVersionCode)) {
if(Integer.valueOf(versionItem.getUpdatevs())==0){
showNoticeDialog();
}else {
showNoticeDialog2();//强制更新
} } else {
if (showProgressDialog) {
Toast.makeText(mContext, "您现在使用的是最新版本哦", Toast.LENGTH_SHORT).show();
}
} }
} @Override
public void onError(Response response, int code, Exception e) { }
});
} private void showNoticeDialog() {
AlertDialog.Builder builder = new AlertDialog.Builder(mContext);
builder.setTitle("更新提醒");
builder.setMessage(desc); builder.setOnCancelListener(new DialogInterface.OnCancelListener() {
@Override
public void onCancel(DialogInterface dialog) {
dialog.dismiss();
}
});
builder.setNegativeButton("下次再说", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
});
builder.setPositiveButton("立刻更新", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
showDownloadDialog();
} });
builder.show();
}
private void showNoticeDialog2() {
AlertDialog.Builder builder = new AlertDialog.Builder(mContext);
builder.setTitle("更新提醒");
builder.setMessage(desc);
// builder.setCancelable(false); builder.setOnCancelListener(new DialogInterface.OnCancelListener() {
@Override
public void onCancel(DialogInterface dialog) {
dialog.dismiss();
}
});
builder.setPositiveButton("立刻更新", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
showDownloadDialog();
} });
builder.show();
}
/**
* 展示下载对话框
*/
private void showDownloadDialog() {
// 构造对话框
AlertDialog.Builder builder = new AlertDialog.Builder(mContext);
builder.setTitle("正在下载");
// 给下载对话框增加进度条
LayoutInflater inflater = LayoutInflater.from(mContext);
View v = inflater.inflate(R.layout.version_update_progress, null);
downloadProgressBar = (ProgressBar) v.findViewById(R.id.update_progress);
builder.setView(v);
// 取消更新
builder.setNegativeButton("取消", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
// 隐藏对话框
dialog.dismiss();
// 设置取消状态
cancelUpdate = true;
}
});
downloadDialog = builder.create();
downloadDialog.show();
// 下载文件
downloadApk();
} /**
* 下载apk文件
*/
private void downloadApk() {
new DownloadApkThread().start();
} // 文件下载线程
private class DownloadApkThread extends Thread {
@Override
public void run() {
try {
// 判断SD卡是否存在,并且是否具有读写权限
if (Environment.getExternalStorageState().equals(
Environment.MEDIA_MOUNTED)) {
// 获得存储卡的路径
String sdPath = Environment.getExternalStorageDirectory() + "/";
savePath = sdPath + "download";
URL url = new URL(downloadurl);
// 创建连接
HttpURLConnection conn = (HttpURLConnection) url
.openConnection();
conn.connect();
// 获取文件大小
int length = conn.getContentLength();
// 创建输入流
InputStream is = conn.getInputStream();
File file = new File(savePath);
// 判断文件目录是否存在
if (!file.exists()) {
file.mkdir();
}
File apkFile = new File(savePath, apkName);
FileOutputStream fos = new FileOutputStream(apkFile);
// 已下载量
int count = 0;
// 缓存
byte buf[] = new byte[1024];
// 写入到文件中,点击取消时停止下载
while (!cancelUpdate) {
int numread = is.read(buf);
count += numread;
// 计算进度条位置
progress = (int) (((float) count / length) * 100);
// 更新进度
downloadHandler.sendEmptyMessage(DOWNLOADING);
if (numread <= 0) {
// 下载完成
downloadHandler.sendEmptyMessage(DOWNLOADED);
break;
}
// 写入文件
fos.write(buf, 0, numread);
}
fos.close();
is.close();
} else {
Toast.makeText(mContext, "当前的存储卡不可用,无法完成更新", Toast.LENGTH_LONG).show();
}
} catch (Exception e) {
e.printStackTrace();
}
// 取消下载对话框显示
downloadDialog.dismiss();
}
}; /**
* 安装apk文件
*/
private void install() {
File apkFile = new File(savePath, apkName);
if (apkFile.exists()) {
Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setDataAndType(Uri.parse("file://" + apkFile.toString()),
"application/vnd.android.package-archive");
mContext.startActivity(intent);
}
} // 文件下载控制器
private Handler downloadHandler = new Handler() {
public void handleMessage(Message msg) {
switch (msg.what) {
case DOWNLOADING:
// 正在下载,更新进度条
downloadProgressBar.setProgress(progress);
break;
case DOWNLOADED:
// 下载完成,安装文件
install();
break;
default:
break;
}
}
}; private void getPackageManage() {
PackageManager packageManager = mContext.getPackageManager();
PackageInfo packInfo = null;
try {
packInfo = packageManager.getPackageInfo(
mContext.getPackageName(), 0);
String version = packInfo.versionName;
clientVersionCode = String.valueOf(packInfo.versionCode);
} catch (PackageManager.NameNotFoundException e) {
e.printStackTrace();
} }
/* *//**
* 多线程的下载器
*
* @param downloadurl
*//*
private void download(String downloadurl) {
// 多线程断点下载。
HttpUtils http = new HttpUtils();
http.download(downloadurl, "/mnt/sdcard/temp.apk",
new RequestCallBack<File>() {
@Override
public void onSuccess(ResponseInfo<File> arg0) {
UIUtils.showToast(activity,"下载完成...");
Intent intent = new Intent();
intent.setAction("android.intent.action.VIEW");
intent.addCategory("android.intent.category.DEFAULT"); intent.setDataAndType(Uri.fromFile(new File(Environment
.getExternalStorageDirectory(), "temp.apk")),
"application/vnd.android.package-archive");
startActivityForResult(intent, 0);
} @Override
public void onFailure(HttpException arg0, String arg1) {
ToastUtils.show(activity, "下载失败");
System.out.println(arg1);
arg0.printStackTrace();
//loadMainUI();
} @Override
public void onLoading(long total, long current,
boolean isUploading) {
//tv_info.setText(current + "/" + total);
super.onLoading(total, current, isUploading);
}
});
}*/ }
以上就是版本检测与下载的 工具类, 直接引入项目即可,可能做法比较简单,勿喷... 里面有一个判断==0,表示不需要强制更新,==1表示需要强制更新,根据客户要求做的,就是这个json字段
Integer.valueOf(versionItem.getUpdatevs())==0
布局如下:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content"> <ProgressBar
android:id="@+id/update_progress"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
style="?android:attr/progressBarStyleHorizontal" /> </LinearLayout>
上2个图片
android端 版本升级的更多相关文章
- [Android]Android端ORM框架——RapidORM(v2.1)
以下内容为原创,欢迎转载,转载请注明 来自天天博客:http://www.cnblogs.com/tiantianbyconan/p/6020412.html [Android]Android端ORM ...
- [Android]Android端ORM框架——RapidORM(v2.0)
以下内容为原创,欢迎转载,转载请注明 来自天天博客:http://www.cnblogs.com/tiantianbyconan/p/5626716.html [Android]Android端ORM ...
- Java服务器对外提供接口以及Android端向服务器请求数据
转载请注明出处:http://www.cnblogs.com/Joanna-Yan/p/5056780.html 讲解下java服务器是如何对移动终端提供接口的,以什么数据格式提供出去,移动端又是怎么 ...
- 【Android端 APP GPU过度绘制】GPU过度绘制及优化
一.Android端的卡顿 Android端APP在具体使用的过程中容易出现卡顿的情况,比如查看页面时出现一顿一顿的感受,切换tab之后响应很慢,或者具体滑动操作的时候也很慢. 二.卡顿的原因 卡顿的 ...
- 【Android端 APP 内存分析】使用工具进行APP的内存分析
Android端可以通过adb 命令直接获取内存信息,当然Android studio也提供了对内存的监控分析工具,并且后续可以结合MAT做分析 今天介绍的是通过Android studio和MAT工 ...
- 【Android端APP 安装包检查】安装包检查具体内容及实现方法
一.安装包检查的具体包含内容有哪些? 1.安装包检查的一般内容包括: 安装包基本信息检查: 文件大小: xx MB 包名: com.xx 名称: xx 本次安装包证书与外网证书对比一致性:是 版本号 ...
- pc端和android端应用程序测试有什么区别?(ps面试题)
pc端和android端应用程序测试有什么区别?(ps面试题) [VIP7]大连-凭海临风(215687736) 2014/4/10 8:56:171.测试环境不同PC平台一般都是windows an ...
- 【转载】Android端手机测试体系
1.冒烟测试 跟web端 的测试流程一样,你拿到一个你们开发做出来的apk首先得去冒烟,也就是保证他的稳定性,指定时间内不会崩溃.这款原生sdk自带的monkey可以当做 我们的测试工具.就跟我之前博 ...
- windows 代理服务器的搭建,提供Android 端访问公网.
这段时间遇到一个情况,移动的网络收费.但是可以访问学校内部的网络,比如说学校官网图书馆之类了.所以我这里便想到一个方法,用学校内部一个可以访问互联网的主机充当代理服务器(我这里使用自己的电脑,非服务器 ...
随机推荐
- 关于修改主机名和ssh免密登录
修改主机名的常规方法: 1.hostname name2.echo name > /proc/sys/kernel/hostname3.sysctl kernel.hostname=name4 ...
- React 练习项目,仿简书博客写作平台
Introduction 技术栈:react + redux + react-router + express + Nginx 练习点: redux 连接 react-router 路由跳转 scss ...
- ES6中比较实用的几个特性
1.Default Parameters(默认参数) in ES6 es6之前,定义默认参数的方法是在一个方法内部定义 var link = function (height, color, url) ...
- 白话--长短期记忆(LSTM)的几个步骤,附代码!
1. 什么是LSTM 在你阅读这篇文章时候,你都是基于自己已经拥有的对先前所见词的理解来推断当前词的真实含义.我们不会将所有的东西都全部丢弃,然后用空白的大脑进行思考.我们的思想拥有持久性.LSTM就 ...
- 入门MySQL——DML语句篇
前言: 在上篇文章中,主要为大家介绍的是DDL语句的用法,可能细心的同学已经发现了.本篇文章将主要聚焦于DML语句,为大家讲解表数据相关操作. 这里说明下DDL与DML语句的分类,可能有的同学还不太 ...
- K8S搭建-1 Master 2 Workers(dashboard+ingress)
本文讲述k8s最新版的搭建(v1.15.2) 分如下几个topic步骤: 各个节点的基本配置 master节点的构建 worker节点的构建 安装dashboard 安装ingress 常见命令 do ...
- DC6-靶机渗透
靶场下载链接: Download: http://www.five86.com/downloads/DC-6.zip Download (Mirror): https://download.vulnh ...
- 神经网络 OCR 参考
1. https://blog.csdn.net/u010159842/article/details/87271554 2. https://blog.csdn.net/weixin_4286104 ...
- Linux--shell的awk--10
一.awk介绍 全称:由Aho Weinberger Kernaighan三个人的首字母组合而成 1970年第一次出现在Unix机器上,后来在开源领域使用它 awk是一种单独的编程语言解释器 awk报 ...
- MongoDB 数据库的学习与使用
MongoDB 数据库 一.MongoDB 简介(了解) MongoDB 数据库是一种 NOSQL 数据库,NOSQL 数据库不是这几年才有的,从数据库的初期发展就以及存在了 NOSQL 数据库. ...