Safe-splash页面(1)

这个页面的功能有:基本的显示加载的logo页面,logo页面会有一些文本的信息,版本号版本名等信息。加载的时候,会保持logo页面至少2秒(睡眠的方式来实现)。进入的时候会判断一下当前的版本和服务端获取的json的版本信息,如果服务端的版本号大于现在的版本号会进行升级,同时splash页面会现在下载的进度等等信息。下载完成以后用户可以选择安装或者取消安装跳转首页,或者直接返回不安装跳转首页。

获取版本信息

/**
	 * 获取版本的版本名
	 */
	private String getVersionName() {
		// 获取到包的管理器
		PackageManager packagerManager = getPackageManager();

		try {
			// 获取包名
			PackageInfo packageInfo = packagerManager.getPackageInfo(
					getPackageName(), 0);
			// 版本号
			int versionCode = packageInfo.versionCode;
			// 版本名
			String versionName = packageInfo.versionName;
			System.out.println("versionName:" + versionName);
			return versionName;
		} catch (NameNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return "";
	}

	/**
	 * 获取版本的版本号
	 */
	private int getVersionCode() {
		// 获取到包的管理器
		PackageManager packagerManager = getPackageManager();

		try {
			// 获取包名
			PackageInfo packageInfo = packagerManager.getPackageInfo(
					getPackageName(), 0);
			// 版本号
			int versionCode = packageInfo.versionCode;
			// 版本名
			String versionName = packageInfo.versionName;
			System.out.println("versionCode:" + versionCode);
			return versionCode;
		} catch (NameNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return 0;
	}

下载版本,通过子线程的方式来进行下载,防止阻塞主线程,利用Handle消息队列机制来根据不同的消息来加载

/**
	 * 从服务器获取版本信息校验,确定是否需要进行升级
	 */
	private void checkVersion() {
		// 获取当前的时间
		final long startTime = System.currentTimeMillis();

		// 防止阻塞主线程
		new Thread() {
			@Override
			public void run() {
				String path = "http://192.168.0.100:8080/update.json";
				Message msg = Message.obtain();
				HttpURLConnection conn = null;
				try {
					URL url = new URL(path);
					conn = (HttpURLConnection) url.openConnection();
					conn.setRequestMethod("GET");// 请求方式
					conn.setConnectTimeout(5000);// 链接超时
					conn.setReadTimeout(5000);// 响应超时,连接成功,但服务器不给响应
					conn.connect();// 链接服务器
					int responseCode = conn.getResponseCode();// 获取响应码
					if (responseCode == 200) {
						InputStream inputStream = conn.getInputStream();
						String result = StreamUtils
								.readFromeStream(inputStream);
						System.out.println("返回的结果是:" + result);

						// 解析json,作者的版本鸡西不了json,因此设置成固定值,正常应该是解析出来的值,注释下面5行
						/*
						 * 解析不了json为了测试,写成固定值 JSONObject jo = new
						 * JSONObject(result); mVersionName =
						 * jo.getString("versionName"); mVersionCode =
						 * jo.getInt("VersionCode"); mDesc =
						 * jo.getString("description"); mDownloadUrl =
						 * jo.getString("downloadUrl");
						 */
						JSONObject jo = new JSONObject(result);
						mVersionName = "2.0";
						mVersionCode = 2;
						mDesc = "赶紧升级啊";
						mDownloadUrl = "http://192.168.0.100:8080/Safe2.0.apk";
						System.out.println("添加的功能:" + mDesc);
						if (mVersionCode > getVersionCode()) {
							// 服务器的版本号大于本地的版本号,需要升级
							// 需要升级,弹出升级对话框
							msg.what = CODE_UPDATE_DIALOG;
						} else {
							// 没有版本更新,跳转主页
							msg.what = CODE_ENTER_HOME;
						}

					}
				} catch (MalformedURLException e) {
					// 更新异常
					msg.what = CODE_UPDATE_ERROR;
					e.printStackTrace();
				} catch (IOException e) {
					// 网络异常
					msg.what = CODE_NET_ERROR;
					e.printStackTrace();
				} catch (JSONException e) {
					// JSON异常
					msg.what = CODE_JSON_ERROR;
					e.printStackTrace();
				} finally {
					// 强制logo界面加载显示2s
					long endTime = System.currentTimeMillis();
					long timeUsed = endTime - startTime;
					if (timeUsed < 2000) {
						try {
							Thread.sleep(2000 - timeUsed);
						} catch (InterruptedException e) {
							// TODO Auto-generated catch block
							e.printStackTrace();
						}
					}

					// 主线程发消息
					mHandler.sendMessage(msg);
					// 关闭网络连接
					if (conn != null) {
						conn.disconnect();
					}
				}
			}
		}.start();

	}

消息队列的处理

	private Handler mHandler = new Handler() {
		public void handleMessage(android.os.Message msg) {
			switch (msg.what) {
			case CODE_UPDATE_DIALOG:
				showUpdate();
				break;
			case CODE_UPDATE_ERROR:
				Toast.makeText(SplashActivity.this, "升级错误", Toast.LENGTH_SHORT)
						.show();
				// 跳转主页面
				enterHome();
				break;
			case CODE_NET_ERROR:
				Toast.makeText(SplashActivity.this, "网络错误", Toast.LENGTH_SHORT)
						.show();
				// 跳转主页面
				enterHome();
				break;
			case CODE_JSON_ERROR:
				Toast.makeText(SplashActivity.this, "JSON数据解析错误",
						Toast.LENGTH_SHORT).show();
				// 跳转主页面
				enterHome();
				break;
			case CODE_ENTER_HOME:
				// 跳转主页面
				enterHome();
				break;
			default:
				break;
			}
		}
	};

下载apk和安装apk的方法

/**
	 * 下载新版的apk
	 */
	protected void download() {
		// 先判断有没有sd卡
		if (Environment.getExternalStorageState().equals(
				Environment.MEDIA_MOUNTED)) {
			// 下载的时候让进度显示
			tv_progress.setVisibility(View.VISIBLE);

			// 文件下载的位置
			String target = Environment.getExternalStorageDirectory()
					+ "/UPDATE.APK";
			// 利用github的Xutils执行下载
			HttpUtils utils = new HttpUtils();
			utils.download(mDownloadUrl, target, new RequestCallBack<File>() {

				@Override
				public void onLoading(long total, long current,
						boolean isUploading) {
					super.onLoading(total, current, isUploading);
					System.out.println("下载进度" + current + "/" + total);

					tv_progress.setText("下载进度:" + current * 100 / total + "%");
				}

				// 下载失败
				@Override
				public void onFailure(HttpException arg0, String arg1) {
					Toast.makeText(SplashActivity.this, "下载失败",
							Toast.LENGTH_SHORT).show();

				}

				// 下载成功
				@Override
				public void onSuccess(ResponseInfo<File> arg0) {
					System.out.println("下载成功");
					// 跳转到系统的下载页面
					Intent intent = new Intent(Intent.ACTION_VIEW);
					intent.addCategory(Intent.CATEGORY_DEFAULT);
					intent.setDataAndType(Uri.fromFile(arg0.result),
							"application/vnd.android.package-archive");
					// startActivity(intent);
					startActivityForResult(intent, 0);// 如果用户取消安装,会返回结果,会调用发onActivityResult

				}

			});
		} else {
			Toast.makeText(SplashActivity.this, "没有sd卡", Toast.LENGTH_SHORT)
					.show();
		}

	}

在安装界面,用户可能点击返回,处理如下

/**
	 * 防止用户在升级界面按下返回按键
	 */
	@Override
	protected void onActivityResult(int requestCode, int resultCode, Intent data) {
		enterHome();
		super.onActivityResult(requestCode, resultCode, data);
	}

总代码如下:

package com.ldw.safe.Activity;

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 org.json.JSONException;
import org.json.JSONObject;

import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.DialogInterface.OnCancelListener;
import android.content.DialogInterface.OnClickListener;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.os.Handler;
import android.os.Message;
import android.view.View;
import android.view.animation.AlphaAnimation;
import android.widget.RelativeLayout;
import android.widget.TextView;
import android.widget.Toast;

import com.ldw.safe.R;
import com.ldw.safe.db.dao.AntiVirous;
import com.ldw.safe.utils.StreamUtils;
import com.lidroid.xutils.HttpUtils;
import com.lidroid.xutils.exception.HttpException;
import com.lidroid.xutils.http.ResponseInfo;
import com.lidroid.xutils.http.callback.RequestCallBack;
import com.lidroid.xutils.http.client.HttpRequest.HttpMethod;

public class SplashActivity extends Activity {

	protected static final int CODE_UPDATE_DIALOG = 0;
	protected static final int CODE_UPDATE_ERROR = 1;
	protected static final int CODE_NET_ERROR = 2;
	protected static final int CODE_JSON_ERROR = 3;
	protected static final int CODE_ENTER_HOME = 4;

	private TextView tv_version;
	private TextView tv_progress;// 下载进度显示

	// 服务器json参数
	private String mVersionName;
	private int mVersionCode;
	private String mDesc;
	private String mDownloadUrl;
	
	private SharedPreferences mPref;//把设置的数据保存在mPref

	private Handler mHandler = new Handler() {
		public void handleMessage(android.os.Message msg) {
			switch (msg.what) {
			case CODE_UPDATE_DIALOG:
				showUpdate();
				break;
			case CODE_UPDATE_ERROR:
				Toast.makeText(SplashActivity.this, "升级错误", Toast.LENGTH_SHORT)
						.show();
				// 跳转主页面
				enterHome();
				break;
			case CODE_NET_ERROR:
				Toast.makeText(SplashActivity.this, "网络错误", Toast.LENGTH_SHORT)
						.show();
				// 跳转主页面
				enterHome();
				break;
			case CODE_JSON_ERROR:
				Toast.makeText(SplashActivity.this, "JSON数据解析错误",
						Toast.LENGTH_SHORT).show();
				// 跳转主页面
				enterHome();
				break;
			case CODE_ENTER_HOME:
				// 跳转主页面
				enterHome();
				break;
			default:
				break;
			}
		}
	};
	private RelativeLayout splash;
	private AntiVirous virous;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_splash);
		// 显示版本号
		TextView tv_version = (TextView) findViewById(R.id.tv_version);
		tv_version.setText("版本号:" + getVersionName());

		// 下载进度显示,默认是隐藏的
		tv_progress = (TextView) findViewById(R.id.tv_progress);
		//获取splsh的全局属性
		splash = (RelativeLayout)findViewById(R.id.splash);
		
		mPref = getSharedPreferences("config", MODE_PRIVATE);
		
		copyDB("address.db");//拷贝数据库
		copyDB("antivirus.db");//拷贝病毒库
		
		//更新病毒库
		updateVirous();
		
		//检测设置是否设置了自动更新
		boolean autoUpdate = mPref.getBoolean("auto_update", true);
		if(autoUpdate){
			checkVersion();
		}else{
			//不自动升级
			mHandler.sendEmptyMessageDelayed(CODE_ENTER_HOME, 2000);//延迟2s进入主页
		}
		
		//让splash页面有一个渐变的效果
		AlphaAnimation anim = new AlphaAnimation(0.3f, 1f);
		anim.setDuration(2000);
		splash.startAnimation(anim);
		
	}

	/*
	 * 更新病毒数据库
	 */
	private void updateVirous() {
		virous = new AntiVirous();
		//联网从服务器获取到最新数据的md5的特征码
		HttpUtils httpUtils = new HttpUtils();
		//新增的病毒库
		String url = "http://192.168.0.2:8080/virus.json";
		
		httpUtils.send(HttpMethod.GET, url, new RequestCallBack<String>() {

			@Override
			public void onFailure(HttpException arg0, String arg1) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void onSuccess(ResponseInfo<String> arg0) {
				//解析json
				try {
					JSONObject jsonObject = new JSONObject(arg0.result);
					/*
					 谷歌的gojosn
					 Gson gson = new Gson();
					//解析json
					Virus virus = gson.fromJson(arg0.result, Virus.class);
					dao.addVirus(virus.md5, virus.desc);
					 */
					//json的key-value配对{}
					String md5 = jsonObject.getString("md5");
					String desc = jsonObject.getString("desc");
					
					virous.addVirous(md5, desc);
				} catch (JSONException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
				
			}
			
		});
		
	}

	/**
	 * 获取版本的版本名
	 */
	private String getVersionName() {
		// 获取到包的管理器
		PackageManager packagerManager = getPackageManager();

		try {
			// 获取包名
			PackageInfo packageInfo = packagerManager.getPackageInfo(
					getPackageName(), 0);
			// 版本号
			int versionCode = packageInfo.versionCode;
			// 版本名
			String versionName = packageInfo.versionName;
			System.out.println("versionName:" + versionName);
			return versionName;
		} catch (NameNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return "";
	}

	/**
	 * 获取版本的版本号
	 */
	private int getVersionCode() {
		// 获取到包的管理器
		PackageManager packagerManager = getPackageManager();

		try {
			// 获取包名
			PackageInfo packageInfo = packagerManager.getPackageInfo(
					getPackageName(), 0);
			// 版本号
			int versionCode = packageInfo.versionCode;
			// 版本名
			String versionName = packageInfo.versionName;
			System.out.println("versionCode:" + versionCode);
			return versionCode;
		} catch (NameNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return 0;
	}

	/**
	 * 从服务器获取版本信息校验,确定是否需要进行升级
	 */
	private void checkVersion() {
		// 获取当前的时间
		final long startTime = System.currentTimeMillis();

		// 防止阻塞主线程
		new Thread() {
			@Override
			public void run() {
				String path = "http://192.168.0.100:8080/update.json";
				Message msg = Message.obtain();
				HttpURLConnection conn = null;
				try {
					URL url = new URL(path);
					conn = (HttpURLConnection) url.openConnection();
					conn.setRequestMethod("GET");// 请求方式
					conn.setConnectTimeout(5000);// 链接超时
					conn.setReadTimeout(5000);// 响应超时,连接成功,但服务器不给响应
					conn.connect();// 链接服务器
					int responseCode = conn.getResponseCode();// 获取响应码
					if (responseCode == 200) {
						InputStream inputStream = conn.getInputStream();
						String result = StreamUtils
								.readFromeStream(inputStream);
						System.out.println("返回的结果是:" + result);

						// 解析json,作者的版本鸡西不了json,因此设置成固定值,正常应该是解析出来的值,注释下面5行
						/*
						 * 解析不了json为了测试,写成固定值 JSONObject jo = new
						 * JSONObject(result); mVersionName =
						 * jo.getString("versionName"); mVersionCode =
						 * jo.getInt("VersionCode"); mDesc =
						 * jo.getString("description"); mDownloadUrl =
						 * jo.getString("downloadUrl");
						 */
						JSONObject jo = new JSONObject(result);
						mVersionName = "2.0";
						mVersionCode = 2;
						mDesc = "赶紧升级啊";
						mDownloadUrl = "http://192.168.0.100:8080/Safe2.0.apk";
						System.out.println("添加的功能:" + mDesc);
						if (mVersionCode > getVersionCode()) {
							// 服务器的版本号大于本地的版本号,需要升级
							// 需要升级,弹出升级对话框
							msg.what = CODE_UPDATE_DIALOG;
						} else {
							// 没有版本更新,跳转主页
							msg.what = CODE_ENTER_HOME;
						}

					}
				} catch (MalformedURLException e) {
					// 更新异常
					msg.what = CODE_UPDATE_ERROR;
					e.printStackTrace();
				} catch (IOException e) {
					// 网络异常
					msg.what = CODE_NET_ERROR;
					e.printStackTrace();
				} catch (JSONException e) {
					// JSON异常
					msg.what = CODE_JSON_ERROR;
					e.printStackTrace();
				} finally {
					// 强制logo界面加载显示2s
					long endTime = System.currentTimeMillis();
					long timeUsed = endTime - startTime;
					if (timeUsed < 2000) {
						try {
							Thread.sleep(2000 - timeUsed);
						} catch (InterruptedException e) {
							// TODO Auto-generated catch block
							e.printStackTrace();
						}
					}

					// 主线程发消息
					mHandler.sendMessage(msg);
					// 关闭网络连接
					if (conn != null) {
						conn.disconnect();
					}
				}
			}
		}.start();

	}

	/**
	 * 弹出升级对话框
	 */
	private void showUpdate() {
		AlertDialog.Builder builder = new AlertDialog.Builder(this);
		builder.setTitle("最新版本:" + mVersionName);
		builder.setMessage(mDesc);
		// builder.setCancelable(false);//在升级页面不允许返回,这种方法不可取
		builder.setPositiveButton("立即更新", new OnClickListener() {

			@Override
			public void onClick(DialogInterface dialog, int which) {
				// 下载新版的apk
				download();

			}

		});

		builder.setNegativeButton("稍后更新", new OnClickListener() {

			@Override
			public void onClick(DialogInterface dialog, int which) {
				// 用户不升级直接跳转到主页
				enterHome();
			}

		});

		// 监听升级页面,用户按下返回按键,直接跳到主界面
		builder.setOnCancelListener(new OnCancelListener() {

			@Override
			public void onCancel(DialogInterface dialog) {
				// TODO Auto-generated method stub
				enterHome();
			}

		});

		builder.show();
	}

	/**
	 * 下载新版的apk
	 */
	protected void download() {
		// 先判断有没有sd卡
		if (Environment.getExternalStorageState().equals(
				Environment.MEDIA_MOUNTED)) {
			// 下载的时候让进度显示
			tv_progress.setVisibility(View.VISIBLE);

			// 文件下载的位置
			String target = Environment.getExternalStorageDirectory()
					+ "/UPDATE.APK";
			// 利用github的Xutils执行下载
			HttpUtils utils = new HttpUtils();
			utils.download(mDownloadUrl, target, new RequestCallBack<File>() {

				@Override
				public void onLoading(long total, long current,
						boolean isUploading) {
					super.onLoading(total, current, isUploading);
					System.out.println("下载进度" + current + "/" + total);

					tv_progress.setText("下载进度:" + current * 100 / total + "%");
				}

				// 下载失败
				@Override
				public void onFailure(HttpException arg0, String arg1) {
					Toast.makeText(SplashActivity.this, "下载失败",
							Toast.LENGTH_SHORT).show();

				}

				// 下载成功
				@Override
				public void onSuccess(ResponseInfo<File> arg0) {
					System.out.println("下载成功");
					// 跳转到系统的下载页面
					Intent intent = new Intent(Intent.ACTION_VIEW);
					intent.addCategory(Intent.CATEGORY_DEFAULT);
					intent.setDataAndType(Uri.fromFile(arg0.result),
							"application/vnd.android.package-archive");
					// startActivity(intent);
					startActivityForResult(intent, 0);// 如果用户取消安装,会返回结果,会调用发onActivityResult

				}

			});
		} else {
			Toast.makeText(SplashActivity.this, "没有sd卡", Toast.LENGTH_SHORT)
					.show();
		}

	}

	/**
	 * 防止用户在升级界面按下返回按键
	 */
	@Override
	protected void onActivityResult(int requestCode, int resultCode, Intent data) {
		enterHome();
		super.onActivityResult(requestCode, resultCode, data);
	}

	/**
	 * 进入主页面
	 */
	public void enterHome() {
		Intent intent = new Intent(this, HomeActivity.class);
		startActivity(intent);
	}
	
	/*
	 * 拷贝数据库
	 */
	public void copyDB(String dbName){
		//获取数据库的文件路径,要拷贝的目标地址
		File targetFile = new File(getFilesDir(), dbName);//
		//数据库存在
		if(targetFile.exists()){
			System.out.println("数据库已经存在");
			return;
		}
		FileOutputStream out = null;
		InputStream in = null;
		try {
			in = getAssets().open(dbName);
			out = new FileOutputStream(targetFile);
			//读数据
			int len = 0;
			byte[] buffer = new byte[1024];
			
			while((len = in.read(buffer)) != -1 ){
				out.write(buffer, 0, len);
			}
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}finally{
			try {
				in.close();
				out.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}

}



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值