Android应用APP自动更新功能的代码实现
程序员文章站
2024-03-01 09:41:16
由于android项目开源所致,市面上出现了n多安卓软件市场。为了让我们开发的软件有更多的用户使用,我们需要向n多市场发布,软件升级后,我们也必须到安卓市场上进行更新,给我...
由于android项目开源所致,市面上出现了n多安卓软件市场。为了让我们开发的软件有更多的用户使用,我们需要向n多市场发布,软件升级后,我们也必须到安卓市场上进行更新,给我们增加了工作量。因此我们有必要给我们的android应用增加自动更新的功能。
既然实现自动更新,我们首先必须让我们的应用知道是否存在新版本的软件,因此我们可以在自己的网站上放置配置文件,存放软件的版本信息:
<update> <version>2</version> <name>baidu_xinwen_1.1.0</name> <url>http://gdown.baidu.com/data/wisegame/f98d235e39e29031/baiduxinwen.apk</url> </update>
在这里我使用的是xml文件,方便读取。由于xml文件内容比较少,因此可通过dom方式进行文件的解析:
public class parsexmlservice { public hashmap<string, string> parsexml(inputstream instream) throws exception { hashmap<string, string> hashmap = new hashmap<string, string>(); // 实例化一个文档构建器工厂 documentbuilderfactory factory = documentbuilderfactory.newinstance(); // 通过文档构建器工厂获取一个文档构建器 documentbuilder builder = factory.newdocumentbuilder(); // 通过文档通过文档构建器构建一个文档实例 document document = builder.parse(instream); //获取xml文件根节点 element root = document.getdocumentelement(); //获得所有子节点 nodelist childnodes = root.getchildnodes(); for (int j = 0; j < childnodes.getlength(); j++) { //遍历子节点 node childnode = (node) childnodes.item(j); if (childnode.getnodetype() == node.element_node) { element childelement = (element) childnode; //版本号 if ("version".equals(childelement.getnodename())) { hashmap.put("version",childelement.getfirstchild().getnodevalue()); } //软件名称 else if (("name".equals(childelement.getnodename()))) { hashmap.put("name",childelement.getfirstchild().getnodevalue()); } //下载地址 else if (("url".equals(childelement.getnodename()))) { hashmap.put("url",childelement.getfirstchild().getnodevalue()); } } } return hashmap; }
通过parsexml()方法,我们可以获取服务器上应用的版本、文件名以及下载地址。紧接着我们就需要获取到我们手机上应用的版本信息:
/** * 获取软件版本号 * * @param context * @return */ private int getversioncode(context context) { int versioncode = 0; try { // 获取软件版本号, versioncode = context.getpackagemanager().getpackageinfo("com.szy.update", 0).versioncode; } catch (namenotfoundexception e) { e.printstacktrace(); } return versioncode; }
通过该方法我们获取到的versioncode对应androidmanifest.xml下android:versioncode。android:versioncode和android:versionname两个属性分别表示版本号,版本名称。versioncode是整数型,而versionname是字符串。由于versionname是给用户看的,不太容易比较大小,升级检查时,就可以检查versioncode。把获取到的手机上应用版本与服务器端的版本进行比较,应用就可以判断处是否需要更新软件。
处理流程
处理代码
package com.szy.update; import java.io.file; import java.io.fileoutputstream; import java.io.ioexception; import java.io.inputstream; import java.net.httpurlconnection; import java.net.malformedurlexception; import java.net.url; import java.util.hashmap; import android.app.alertdialog; import android.app.dialog; import android.app.alertdialog.builder; import android.content.context; import android.content.dialoginterface; import android.content.intent; import android.content.dialoginterface.onclicklistener; import android.content.pm.packagemanager.namenotfoundexception; import android.net.uri; import android.os.environment; import android.os.handler; import android.os.message; import android.view.layoutinflater; import android.view.view; import android.widget.progressbar; import android.widget.toast; public class updatemanager { /* 下载中 */ private static final int download = 1; /* 下载结束 */ private static final int download_finish = 2; /* 保存解析的xml信息 */ hashmap<string, string> mhashmap; /* 下载保存路径 */ private string msavepath; /* 记录进度条数量 */ private int progress; /* 是否取消更新 */ private boolean cancelupdate = false; private context mcontext; /* 更新进度条 */ private progressbar mprogress; private dialog mdownloaddialog; private handler mhandler = new handler() { public void handlemessage(message msg) { switch (msg.what) { // 正在下载 case download: // 设置进度条位置 mprogress.setprogress(progress); break; case download_finish: // 安装文件 installapk(); break; default: break; } }; }; public updatemanager(context context) { this.mcontext = context; } /** * 检测软件更新 */ public void checkupdate() { if (isupdate()) { // 显示提示对话框 shownoticedialog(); } else { toast.maketext(mcontext, r.string.soft_update_no, toast.length_long).show(); } } /** * 检查软件是否有更新版本 * * @return */ private boolean isupdate() { // 获取当前软件版本 int versioncode = getversioncode(mcontext); // 把version.xml放到网络上,然后获取文件信息 inputstream instream = parsexmlservice.class.getclassloader().getresourceasstream("version.xml"); // 解析xml文件。 由于xml文件比较小,因此使用dom方式进行解析 parsexmlservice service = new parsexmlservice(); try { mhashmap = service.parsexml(instream); } catch (exception e) { e.printstacktrace(); } if (null != mhashmap) { int servicecode = integer.valueof(mhashmap.get("version")); // 版本判断 if (servicecode > versioncode) { return true; } } return false; } /** * 获取软件版本号 * * @param context * @return */ private int getversioncode(context context) { int versioncode = 0; try { // 获取软件版本号,对应androidmanifest.xml下android:versioncode versioncode = context.getpackagemanager().getpackageinfo("com.szy.update", 0).versioncode; } catch (namenotfoundexception e) { e.printstacktrace(); } return versioncode; } /** * 显示软件更新对话框 */ private void shownoticedialog() { // 构造对话框 alertdialog.builder builder = new builder(mcontext); builder.settitle(r.string.soft_update_title); builder.setmessage(r.string.soft_update_info); // 更新 builder.setpositivebutton(r.string.soft_update_updatebtn, new onclicklistener() { @override public void onclick(dialoginterface dialog, int which) { dialog.dismiss(); // 显示下载对话框 showdownloaddialog(); } }); // 稍后更新 builder.setnegativebutton(r.string.soft_update_later, new onclicklistener() { @override public void onclick(dialoginterface dialog, int which) { dialog.dismiss(); } }); dialog noticedialog = builder.create(); noticedialog.show(); } /** * 显示软件下载对话框 */ private void showdownloaddialog() { // 构造软件下载对话框 alertdialog.builder builder = new builder(mcontext); builder.settitle(r.string.soft_updating); // 给下载对话框增加进度条 final layoutinflater inflater = layoutinflater.from(mcontext); view v = inflater.inflate(r.layout.softupdate_progress, null); mprogress = (progressbar) v.findviewbyid(r.id.update_progress); builder.setview(v); // 取消更新 builder.setnegativebutton(r.string.soft_update_cancel, new onclicklistener() { @override public void onclick(dialoginterface dialog, int which) { dialog.dismiss(); // 设置取消状态 cancelupdate = true; } }); mdownloaddialog = builder.create(); mdownloaddialog.show(); // 现在文件 downloadapk(); } /** * 下载apk文件 */ private void downloadapk() { // 启动新线程下载软件 new downloadapkthread().start(); } /** * 下载文件线程 * * @author coolszy */ private class downloadapkthread extends thread { @override public void run() { try { // 判断sd卡是否存在,并且是否具有读写权限 if (environment.getexternalstoragestate().equals(environment.media_mounted)) { // 获得存储卡的路径 string sdpath = environment.getexternalstoragedirectory() + "/"; msavepath = sdpath + "download"; url url = new url(mhashmap.get("url")); // 创建连接 httpurlconnection conn = (httpurlconnection) url.openconnection(); conn.connect(); // 获取文件大小 int length = conn.getcontentlength(); // 创建输入流 inputstream is = conn.getinputstream(); file file = new file(msavepath); // 判断文件目录是否存在 if (!file.exists()) { file.mkdir(); } file apkfile = new file(msavepath, mhashmap.get("name")); fileoutputstream fos = new fileoutputstream(apkfile); int count = 0; // 缓存 byte buf[] = new byte[1024]; // 写入到文件中 do { int numread = is.read(buf); count += numread; // 计算进度条位置 progress = (int) (((float) count / length) * 100); // 更新进度 mhandler.sendemptymessage(download); if (numread <= 0) { // 下载完成 mhandler.sendemptymessage(download_finish); break; } // 写入文件 fos.write(buf, 0, numread); } while (!cancelupdate);// 点击取消就停止下载. fos.close(); is.close(); } } catch (malformedurlexception e) { e.printstacktrace(); } catch (ioexception e) { e.printstacktrace(); } // 取消下载对话框显示 mdownloaddialog.dismiss(); } }; /** * 安装apk文件 */ private void installapk() { file apkfile = new file(msavepath, mhashmap.get("name")); if (!apkfile.exists()) { return; } // 通过intent安装apk文件 intent i = new intent(intent.action_view); i.setdataandtype(uri.parse("file://" + apkfile.tostring()), "application/vnd.android.package-archive"); mcontext.startactivity(i); } }
效果图
检查模拟器sdcard是否存在下载文件:
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。
推荐阅读
-
Android应用APP自动更新功能的代码实现
-
Android App调用MediaRecorder实现录音功能的实例
-
Android应用中图片浏览时实现自动切换功能的方法详解
-
Android App中实现向右滑动销毁功能的要点解析
-
Android开发5:应用程序窗口小部件App Widgets的实现(附demo)
-
Android App中使用RatingBar实现星级打分功能的教程
-
详解Android系统中跨应用数据分享功能的实现
-
Android中实现基本的短信拦截功能的代码示例
-
Android App实现应用内部自动更新的最基本方法示例
-
Android App中实现可以双击放大和缩小图片功能的实例