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

phonegap 自动更新android app 博客分类: 移动开发 phonegapandroid自动更新html5 

程序员文章站 2024-03-25 18:56:22
...
       最近在做一个html5 的移动开发,用的是jqm和phonegap,用dw开发环境,并在新浪云上进行app的打包。但是现在由于需要做android安装程序自动下载更新,发现phonegap有下载的功能,但是没有自动安装的功能,所以只能想到用phonegap插件。用phonegap插件必须要在eclipse的开发环境下开发,搭建参考地址如下:
http://www.phonegapcn.com/developers/get-started-13/get-started搭建完毕后将phonegap.jar放到src的包下面。
        下面解决两个问题,一个是下载android安装程序,利用phonegap里api,FileTransfer。注意download 只能在英文官网里找到。下载js代码如下:
// JavaScript Document
$('#login').live("pageinit", function () {		
	document.addEventListener("deviceready", onDeviceReady, false);//phonegap绑定backbutton和获取终端信
	var sourcedir1="app";//下载一级目录
	var sourcedir2="update";//下载二级目录息
	//客户端下载地址
	var url="http://192.168.103.58:8080/mobile/test.apk";
	var source="test.apk";
	function onDeviceReady() {	
	window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, function(fileSystem){     
					fileSystem.root.getDirectory(
						sourcedir1,
						{create:true,exclusive:false},
						function(entrydir){ 
							entrydir.getDirectory(
								sourcedir2,
								{create:true,exclusive:false},
								function(entrydir){
									entrydir.getFile(
										source,
										{create:true,exclusive:false}, 
									function(parent){
									var fileTransfer = new FileTransfer(); 
										var uri = encodeURI(url);
										fileTransfer.onprogress = function(progressEvent) {
										if (progressEvent.lengthComputable) {
									var percentLoaded = Math.round(100 * (progressEvent.loaded / progressEvent.total));
									var progressbarWidth = percentLoaded/2 + "%";
										//下载进度显示,可自己定义
						$.mobile.showPageLoadingMsg('a', "正在下载......  "+progressbarWidth,true);
										if(progressbarWidth=100){
											//设置延时
								setTimeout("$.mobile.hidePageLoadingMsg()",3000);
										}

										} else {
										loadingStatus.increment();
									}
								};
																						
									fileTransfer.download(
									uri,
									parent.fullPath,
									function(entry){ 
									//调用自动安装的插件	
		window.plugins.update.openFile(entry.fullPath,null,null);											
									},
									function(error) {alert("下载失败")}
								);
							},
						function(){alert("文件下载失败")}
					);
				},
			function(){alert("创建二级栏目失败")}
		);
},
function(){alert("创建一级目录失败");}
		); 
	}, function(evt){  
		console.log("加载文件系统出现错误");  
});
		  
}
		
	
 }); //pageshow
 
	  
   
  

        其中window.plugins.update.openFile(entry.fullPath,null,null);为调用phonegap插件js的代码,,下面解决第二个问题,即自动安装插件,该插件phonegap.jar1.9以上支持。插件js代码如下:
var Update = function(){};

Update.prototype.openFile = function(fullPath,onSuccess, onFail){
    cordova.exec(onSuccess, onFail, 'Update', 'openFile', [fullPath]);
};
Update.prototype.openApp = function(packageName,onSuccess, onFail){
    cordova.exec(onSuccess, onFail, 'Update', 'openApp', [packageName]);
};
if(!window.plugins) {
    window.plugins = {};
}
if (!window.plugins.update) {
    window.plugins.update = new Update();
}

       插件的java代码如下:
import java.io.File;
import java.util.List;

import org.apache.cordova.api.Plugin;
import org.apache.cordova.api.PluginResult;
import org.json.JSONArray;

import android.content.ComponentName;
import android.content.Intent;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.content.pm.ResolveInfo;
import android.net.Uri;


public class Update extends Plugin {
	
	@Override
	public PluginResult execute(String action, JSONArray args, String callbackId) {
		PluginResult.Status status = PluginResult.Status.OK;
		if (action.equals("openFile")) {
			try {
				openFile(new File(args.getString(0).replaceAll("file://", "")));
			} catch(Exception e){
				return new PluginResult(PluginResult.Status.ERROR, "打开错误");
			}
		}
		else if(action.equals("openApp")){
			try
				{
				if(checkApp(args.getString(0))){
					openApp(args.getString(0));
				}
			else{
				//Log.d("openApp", "没有应用");
				return new PluginResult(PluginResult.Status.ERROR, "没有应用");
			}
				}
			catch(Exception e){
				//Log.d("openApp", "打开错误");
				return new PluginResult(PluginResult.Status.ERROR, "错误");
			}
		}
		return new PluginResult(status, "成功");
	}
	
	private void openApp(String packageName) throws NameNotFoundException {
		PackageManager pm=this.cordova.getActivity().getPackageManager();
		PackageInfo pi = pm.getPackageInfo(packageName, 0);

		Intent resolveIntent = new Intent(Intent.ACTION_MAIN, null);
		resolveIntent.addCategory(Intent.CATEGORY_LAUNCHER);
		resolveIntent.setPackage(pi.packageName);

		List<ResolveInfo> apps = pm.queryIntentActivities(resolveIntent, 0);

		ResolveInfo ri = apps.iterator().next();
		if (ri != null ) {
		String packageName1 = ri.activityInfo.packageName;
		String className = ri.activityInfo.name;

		Intent intent = new Intent(Intent.ACTION_MAIN);
		intent.addCategory(Intent.CATEGORY_LAUNCHER);

		ComponentName cn = new ComponentName(packageName1, className);

		intent.setComponent(cn);
		this.cordova.getActivity().startActivity(intent);
			}
		}
	
	private boolean checkApp(String packageName) {   
	    if (packageName == null || "".equals(packageName))   
	        return false;   
	    try {   
	        ApplicationInfo info = this.cordova.getActivity().getPackageManager().getApplicationInfo(   
	                packageName, PackageManager.GET_UNINSTALLED_PACKAGES);   
	        return true;   
	    } catch (NameNotFoundException e) {   
	        return false;   
	    }   
	} 

	private void openFile(File f) {
		Intent intent = new Intent(Intent.ACTION_VIEW);
		intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

		/* 调用getMIMEType()来取得MimeType */
		String type = getMIMEType(f);
		/* 设置intent的file与MimeType */
		intent.setDataAndType(Uri.fromFile(f), type);
		this.cordova.getActivity().startActivity(intent);
	}

	/* 判断文件MimeType的method */
	private String getMIMEType(File f) {
		String type = "";
		String fName = f.getName();
		/* 取得扩展名 */
		String end = fName
				.substring(fName.lastIndexOf(".") + 1, fName.length())
				.toLowerCase();

		/* 依扩展名的类型决定MimeType */
		if (end.equals("m4a") || end.equals("mp3") || end.equals("mid")
				|| end.equals("xmf") || end.equals("ogg") || end.equals("wav")) {
			type = "audio";
		} else if (end.equals("3gp") || end.equals("mp4")) {
			type = "video";
		} else if (end.equals("jpg") || end.equals("gif") || end.equals("png")
				|| end.equals("jpeg") || end.equals("bmp")) {
			type = "image";
		} else if (end.equals("apk")) {
			/* android.permission.INSTALL_PACKAGES */
			type = "application/vnd.android.package-archive";
		} else {
			type = "*";
		}
		/* 如果无法直接打开,就跳出软件列表给用户选择 */
		if (end.equals("apk")) {
		} else {
			type += "/*";
		}
		return type;
	}

}


       另外还需在工程根目录res->xml中的config.xml里面配置插件信息<plugin name="Update" value="your package.Update"/>。
        代码测试通过,如有疑问,欢迎大家留言指正交流。