做一个app,有时候会用到数据库,尤其是外来的数据库,这时候就要先把数据库拷贝到系统
里,然后再连接数据库。通常把.db数据库放到assets文件里,然后复制到手机里,一般都是
把数据库复制到系统里,比较少复制到SD卡上。复制用流的方式,拷贝到系统里,由于是个
耗时操作,不能直接在UI线程操作,一般都是在子线程或开启个service来进行,复制之前先
判断系统中有没有该.db,如果有,不用复制,如果没有,复制。下面是个子线程的复制
/**
* 拷贝数据库文件到系统目录
*
* @param string
*/
private void copyDBToSystem(final String filename) {
// 判断是否已经拷贝过 数据库 如果已经拷贝过数据库 不再重新拷贝
File file = new File(getFilesDir(), filename);
if (file.exists() && file.length() > 0) {
Log.i(TAG, "数据库已经拷贝成功,无需考呗");
return;
}
new Thread() {
public void run() {
try {
// 文件拷贝.
Log.i(TAG, "拷贝数据库");
AssetManager am = getAssets();
InputStream is = am.open(filename);
File file = new File(getFilesDir(),
filename);
FileOutputStream fos = new
FileOutputStream(file);
byte[] buffer = new byte[1024];
int len = 0;
while ((len = is.read(buffer)) != -1) {
fos.write(buffer, 0, len);
}
fos.close();
is.close();
} catch (Exception e) {
e.printStackTrace();
}
};
}.start();
}
这种方式逻辑简单,但可能会产生漏洞。比如当前页面正在复制,结果activity跳转了,可
能产生bug了。一种解决方式就是加入Handler,当复制结束时在通知Handler进行页面跳转。
如果有两个db要复制,这时候可以加入一个int num;当复制结束时num++;然后发送信息给
Handler,在handler中判断num的值,如果num == 2,则执行页面跳转。
另一种方式就是开启一个service,在service里面做复制功能。service有个子类
IntentService,这个类的好处一是可以排序,顺序执行,二是封装了looper+handler信息,
可以做耗时操作,不用再开子线程,三是执行完任务后会自动关闭,提高效率。我们写个类
继承IntentService,重写onHandleIntent(Intent intent)抽象方法,在这个方法里面执行
上述子线程里面的代码即可。在启动IntentService前,先判断db是否已经复制过,如果没有
,启动IntentService。
外来数据库一个重要的功能就是查询,查询信息输入内容有误或者没有输入时,一般都给查
询框加个晃动动画或震动,起到提醒作用。动画效果在google官方的ApiDemo中有,震动也有
,直接上代码。
Animation shake = AnimationUtils.loadAnimation(this,R.anim.shake);
editText.startAnimation(shake);
shake:
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="1000"
android:fromXDelta="0"
android:interpolator="@anim/cycle_num"
android:toXDelta="10" />
cycle_num:
<cycleInterpolator xmlns:android="http://schemas.android.com/apk/res/android"
android:cycles="7" />
手机震动:
Vibrator vibrator = (Vibrator)context.getSystemService(Context.VIBRATOR_SERVICE);
vibrator.vibrate(200);// 200是时间,单位是毫秒
里,然后再连接数据库。通常把.db数据库放到assets文件里,然后复制到手机里,一般都是
把数据库复制到系统里,比较少复制到SD卡上。复制用流的方式,拷贝到系统里,由于是个
耗时操作,不能直接在UI线程操作,一般都是在子线程或开启个service来进行,复制之前先
判断系统中有没有该.db,如果有,不用复制,如果没有,复制。下面是个子线程的复制
/**
* 拷贝数据库文件到系统目录
*
* @param string
*/
private void copyDBToSystem(final String filename) {
// 判断是否已经拷贝过 数据库 如果已经拷贝过数据库 不再重新拷贝
File file = new File(getFilesDir(), filename);
if (file.exists() && file.length() > 0) {
Log.i(TAG, "数据库已经拷贝成功,无需考呗");
return;
}
new Thread() {
public void run() {
try {
// 文件拷贝.
Log.i(TAG, "拷贝数据库");
AssetManager am = getAssets();
InputStream is = am.open(filename);
File file = new File(getFilesDir(),
filename);
FileOutputStream fos = new
FileOutputStream(file);
byte[] buffer = new byte[1024];
int len = 0;
while ((len = is.read(buffer)) != -1) {
fos.write(buffer, 0, len);
}
fos.close();
is.close();
} catch (Exception e) {
e.printStackTrace();
}
};
}.start();
}
这种方式逻辑简单,但可能会产生漏洞。比如当前页面正在复制,结果activity跳转了,可
能产生bug了。一种解决方式就是加入Handler,当复制结束时在通知Handler进行页面跳转。
如果有两个db要复制,这时候可以加入一个int num;当复制结束时num++;然后发送信息给
Handler,在handler中判断num的值,如果num == 2,则执行页面跳转。
另一种方式就是开启一个service,在service里面做复制功能。service有个子类
IntentService,这个类的好处一是可以排序,顺序执行,二是封装了looper+handler信息,
可以做耗时操作,不用再开子线程,三是执行完任务后会自动关闭,提高效率。我们写个类
继承IntentService,重写onHandleIntent(Intent intent)抽象方法,在这个方法里面执行
上述子线程里面的代码即可。在启动IntentService前,先判断db是否已经复制过,如果没有
,启动IntentService。
外来数据库一个重要的功能就是查询,查询信息输入内容有误或者没有输入时,一般都给查
询框加个晃动动画或震动,起到提醒作用。动画效果在google官方的ApiDemo中有,震动也有
,直接上代码。
Animation shake = AnimationUtils.loadAnimation(this,R.anim.shake);
editText.startAnimation(shake);
shake:
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="1000"
android:fromXDelta="0"
android:interpolator="@anim/cycle_num"
android:toXDelta="10" />
cycle_num:
<cycleInterpolator xmlns:android="http://schemas.android.com/apk/res/android"
android:cycles="7" />
手机震动:
Vibrator vibrator = (Vibrator)context.getSystemService(Context.VIBRATOR_SERVICE);
vibrator.vibrate(200);// 200是时间,单位是毫秒