欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android实现检查并下载APK更新、安装APK及获取网络信息的方法

程序员文章站 2022-05-27 10:25:21
本文所述实例为一个天气预报中的android代码,主要包括了下载和安装apk、检查apk更新、显示'已经是最新'或者'无法获取版本信息'对话框、获取当前客户端版本信息、显示...

本文所述实例为一个天气预报中的android代码,主要包括了下载和安装apk、检查apk更新、显示'已经是最新'或者'无法获取版本信息'对话框、获取当前客户端版本信息、显示版本更新通知对话框、显示下载对话框、判断是否挂载了sd卡、显示文件大小格式:2个小数点显示等。具体实现代码如下:

import java.io.bytearrayinputstream;
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.text.decimalformat;
import org.apache.http.httpentity;
import org.apache.http.httpresponse;
import org.apache.http.client.methods.httpget;
import org.apache.http.conn.connecttimeoutexception;
import org.apache.http.impl.client.defaulthttpclient;
import org.apache.http.params.coreconnectionpnames;
import org.apache.http.util.entityutils;
import org.lmw.weather.r;
import org.lmw.weather.entity.appdetail;
import android.app.alertdialog;
import android.app.dialog;
import android.app.progressdialog;
import android.app.alertdialog.builder;
import android.content.context;
import android.content.dialoginterface;
import android.content.intent;
import android.content.dialoginterface.oncancellistener;
import android.content.dialoginterface.onclicklistener;
import android.content.pm.packageinfo;
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.textview;
import android.widget.toast;
public class downloadmanager {
  private static final int down_nosdcard = 0;
  private static final int down_update = 1;
  private static final int down_over = 2;
  private static final int down_error=3;
  private static final int dialog_type_latest = 0;
  private static final int dialog_type_fail = 1;
  private static final int dialog_type_interneterror = 2;
  private static downloadmanager downloadmanager;
  private context mcontext;
  // 通知对话框
  private dialog noticedialog;
  // 下载对话框
  private dialog downloaddialog;
  // 进度条
  private progressbar mprogress;
  // 显示下载数值
  private textview mprogresstext;
  // 查询动画
  private progressdialog mprodialog;
  // '已经是最新' 或者 '无法获取最新版本' 的对话框
  private dialog latestorfaildialog;
  // 返回的安装包url
  private string apkurl = "";
  // 进度值
  private int progress;
  // 下载线程
  private thread downloadthread;
  // 终止标记
  private boolean interceptflag;
  // 提示语
  private string updatemsg = "";
  // 下载包保存路径
  private string savepath = "";
  // apk保存完整路径
  private string apkfilepath = "";
  // 临时下载文件路径
  private string tmpfilepath = "";
  // 下载文件大小
  private string apkfilesize;
  // 已下载文件大小
  private string tmpfilesize;
  private string curversionname = "";
  private int curversioncode;
  private appdetail mdownload;
  private string checkurl="http://192.168.0.133:8080/lmw/androidmarket/simpleweather-20130701093349937/update.xml";
  private handler mhandler = new handler() {
 public void handlemessage(message msg) {
   switch (msg.what) {
   case down_update:
 mprogress.setprogress(progress);
 mprogresstext.settext(tmpfilesize + "/" + apkfilesize);
 break;
   case down_over:
 downloaddialog.dismiss();
 installapk();
 break;
   case down_nosdcard:
 downloaddialog.dismiss();
 toast.maketext(mcontext, "无法下载安装文件,请检查sd卡是否挂载",toast.length_short).show();
 break;
   case down_error:
 downloaddialog.dismiss();
 if(msg.arg1==0){
 toast.maketext(mcontext, "网络不给力啊", toast.length_short).show();
 }else if(msg.arg1==1||msg.arg1==2){
 toast.maketext(mcontext, "未找到资源",toast.length_short).show();
 }
 break;
   }
 };
  };
  public static downloadmanager getdownloadmanager() {
 if (downloadmanager == null) {
   downloadmanager = new downloadmanager();
 }
 downloadmanager.interceptflag = false;
 return downloadmanager;
  }
  public void downloader(context context, appdetail download) {
 this.mcontext = context;
 this.mdownload = download;
 showdownloaddialog();
  }
  /**
   * 检查app更新
   * @param context
   * @param isshowmsg
   * 是否显示提示消息
   */
  public void checkappupdate(context context, final boolean isshowmsg,final boolean notmain) {
 this.mcontext = context;
 getcurrentversion(mcontext);
 if (isshowmsg) {
   if (mprodialog == null)
 mprodialog = progressdialog.show(mcontext, null, "正在检测,请稍后...",true, true);
   else if (mprodialog.isshowing()|| (latestorfaildialog != null && latestorfaildialog.isshowing()))
 return;
 }
 final handler handler = new handler() {
   public void handlemessage(message msg) {
 // 进度条对话框不显示 - 检测结果也不显示
 if (mprodialog != null && !mprodialog.isshowing()) {
   return;
 }
 // 关闭并释放释放进度条对话框
 if (isshowmsg && mprodialog != null) {
   mprodialog.dismiss();
   mprodialog = null;
 }
 // 显示检测结果
 if (msg.what == 1) {
   mdownload = (appdetail) msg.obj;
   if (mdownload != null) {
  if (curversioncode < mdownload.getversioncode()) {
    apkurl = mdownload.geturi()+mdownload.getfilename();
    updatemsg = mdownload.getapphistory();
    shownoticedialog();
  } else if (isshowmsg) {
    if (notmain) {
  showlatestorfaildialog(dialog_type_latest);
    }
  }
   }
 }else if(msg.what==-1&&isshowmsg){
  showlatestorfaildialog(dialog_type_interneterror);
 }else if (isshowmsg) {
   showlatestorfaildialog(dialog_type_fail);
 }
   }
 };
 new thread() {
   public void run() {
 message msg = new message();
 try {
  defaulthttpclient client = new defaulthttpclient();
  client.getparams().setparameter(coreconnectionpnames.connection_timeout, 3000);
  httpget get = new httpget(checkurl);
  httpresponse response = client.execute(get);
  if (response.getstatusline().getstatuscode() == 200) {
  httpentity entity = response.getentity();
  inputstream stream = new bytearrayinputstream( entityutils.tostring(entity, "gb2312").getbytes());
   appdetail update = appdetail.parsexml(stream);
   msg.what = 1;
   msg.obj = update;
  }else{
   msg.what = -1;
  }
 } catch (exception e) {
   e.printstacktrace();
   msg.what = -1;
 }
 handler.sendmessage(msg);
   }
 }.start();
  }
  /*显示'已经是最新'或者'无法获取版本信息'对话框*/
  private void showlatestorfaildialog(int dialogtype) {
   string toastmsg="";
 if (latestorfaildialog != null) {
   // 关闭并释放之前的对话框
   latestorfaildialog.dismiss();
   latestorfaildialog = null;
 }
// alertdialog.builder builder = new builder(mcontext);
// builder.settitle("系统提示");
 if (dialogtype == dialog_type_latest) {
//   builder.setmessage("您当前已经是最新版本");
   toastmsg="您当前已经是最新版本";
 } else if (dialogtype == dialog_type_fail) {
//   builder.setmessage("无法获取版本更新信息");
 toastmsg="无法获取版本更新信息";
 }else if(dialogtype==dialog_type_interneterror){
// builder.setmessage("网络故障,无法连接服务器");
 toastmsg="网络故障,无法连接服务器";
 }
 toast.maketext(mcontext, toastmsg, toast.length_short).show();
  }
  /*获取当前客户端版本信息*/
  public string getcurrentversion(context context) {
 try {
   packageinfo info = context.getpackagemanager().getpackageinfo(context.getpackagename(), 0);
   curversionname = info.versionname;
   curversioncode = info.versioncode;
 } catch (namenotfoundexception e) {
   e.printstacktrace(system.err);
 }
 return curversionname;
  }
  /*显示版本更新通知对话框*/
  private void shownoticedialog() {
 alertdialog.builder builder = new builder(mcontext);
 builder.settitle("软件版本更新");
 builder.setmessage(updatemsg);
 builder.setpositivebutton("立即更新", new onclicklistener() {
   @override
   public void onclick(dialoginterface dialog, int which) {
 dialog.dismiss();
 showdownloaddialog();
   }
 });
 builder.setnegativebutton("以后再说", new onclicklistener() {
   @override
   public void onclick(dialoginterface dialog, int which) {
 dialog.dismiss();
   }
 });
 noticedialog = builder.create();
 noticedialog.show();
  }
  /*显示下载对话框*/
  private void showdownloaddialog() {
 alertdialog.builder builder = new builder(mcontext);
 builder.settitle("正在下载安装包");
 final layoutinflater inflater = layoutinflater.from(mcontext);
 view v = inflater.inflate(r.layout.download_progress, null);
 mprogress = (progressbar) v.findviewbyid(r.id.update_progress);
 mprogresstext = (textview) v.findviewbyid(r.id.update_progress_text);
 builder.setview(v);
 builder.setnegativebutton("取消", new onclicklistener() {
   @override
   public void onclick(dialoginterface dialog, int which) {
 dialog.dismiss();
 interceptflag = true;
   }
 });
 builder.setoncancellistener(new oncancellistener() {
   @override
   public void oncancel(dialoginterface dialog) {
 dialog.dismiss();
 interceptflag = true;
   }
 });
 downloaddialog = builder.create();
 downloaddialog.setcanceledontouchoutside(false);
 downloaddialog.show();
 downloadapk();
  }
  private runnable mdownapkrunnable = new runnable() {
 message error_msg=new message();
 @override
 public void run(){
   try {
 string apkname = mdownload.getfilename().replace(".apk","")+".apk";
 string tmpapk = mdownload.getfilename().replace(".apk","")+".tmp";
 // 判断是否挂载了sd卡
 string storagestate = environment.getexternalstoragestate();
 if (storagestate.equals(environment.media_mounted)) {
   savepath = environment.getexternalstoragedirectory().getabsolutepath() + "/qn/qnstore/";
   file file = new file(savepath);
   if (!file.exists()) {
  file.mkdirs();
   }
   apkfilepath = savepath + apkname;
   tmpfilepath = savepath + tmpapk;
 }
 // 没有挂载sd卡,无法下载文件
 if (apkfilepath == null || apkfilepath == "") {
   mhandler.sendemptymessage(down_nosdcard);
   return;
 }
 file apkfile = new file(apkfilepath);
 // 是否已下载更新文件
// if (apkfile.exists()) {
//   downloaddialog.dismiss();
//   installapk();
//   return;
// }
 // 输出临时下载文件
 file tmpfile = new file(tmpfilepath);
 fileoutputstream fos = new fileoutputstream(tmpfile);
 url url = new url(mdownload.geturi()+mdownload.getfilename());
 httpurlconnection conn = (httpurlconnection) url.openconnection();
 try {
   conn.connect();
 } catch (connecttimeoutexception e) {
   error_msg.what=down_error;
   error_msg.arg1=0;
   mhandler.sendmessage(error_msg);
 }
 int length = conn.getcontentlength();
 inputstream is = conn.getinputstream();
 // 显示文件大小格式:2个小数点显示
 decimalformat df = new decimalformat("0.00");
 // 进度条下面显示的总文件大小
 apkfilesize = df.format((float) length / 1024 / 1024) + "mb";
 int count = 0;
 byte buf[] = new byte[1024];
 do {
   int numread = is.read(buf);
   count += numread;
   // 进度条下面显示的当前下载文件大小
   tmpfilesize = df.format((float) count / 1024 / 1024) + "mb";
   // 当前进度值
   progress = (int) (((float) count / length) * 100);
   // 更新进度
   mhandler.sendemptymessage(down_update);
   if (numread <= 0) {
  // 下载完成 - 将临时下载文件转成apk文件
  if (tmpfile.renameto(apkfile)) {
    // 通知安装
    mhandler.sendemptymessage(down_over);
  }
  break;
   }
   fos.write(buf, 0, numread);
 } while (!interceptflag);// 点击取消就停止下载
 fos.close();
 is.close();
   } catch (malformedurlexception e) {
 error_msg.what=down_error;
 error_msg.arg1=1;
 mhandler.sendmessage(error_msg);
 e.printstacktrace();
   } catch (ioexception e) {
 error_msg.what=down_error;
 error_msg.arg1=2;
 mhandler.sendmessage(error_msg);
 e.printstacktrace();
   }
 }
  };
  /**
   * 下载apk
   * @param url
   */
  private void downloadapk() {
 downloadthread = new thread(mdownapkrunnable);
 downloadthread.start();
  }
  /**
   * 安装apk
   * @param url
   */
  private void installapk() {
 file apkfile = new file(apkfilepath);
 if (!apkfile.exists()) {
   return;
 }
 intent i = new intent(intent.action_view);
 i.setdataandtype(uri.parse("file://" + apkfile.tostring()),"application/vnd.android.package-archive");
 mcontext.startactivity(i);
  }
}