diff --git a/app/build.gradle b/app/build.gradle index 8f544367..dc2f04ca 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -18,10 +18,6 @@ android { versionName "1.0" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" - - ndk { - abiFilters "armeabi", "armeabi-v7a" - } } buildTypes { @@ -34,11 +30,6 @@ android { sourceCompatibility JavaVersion.VERSION_11 targetCompatibility JavaVersion.VERSION_11 } - sourceSets { - main { - jniLibs.srcDirs = ['libs'] - } - } kotlinOptions { jvmTarget = '1.8' } @@ -52,7 +43,10 @@ android { dependencies { + implementation project(':collect-library') + + testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.5' androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1' @@ -81,6 +75,9 @@ dependencies { implementation 'org.apache.poi:poi:5.2.3' implementation 'org.apache.poi:poi-ooxml:5.2.3' + // 读取spatialite文件 + implementation 'com.github.sevar83:android-spatialite:2.0.1' + } //允许引用生成的代码 kapt { diff --git a/app/src/main/java/com/navinfo/omqs/OMQSApplication.kt b/app/src/main/java/com/navinfo/omqs/OMQSApplication.kt index 0442d351..eabe4308 100644 --- a/app/src/main/java/com/navinfo/omqs/OMQSApplication.kt +++ b/app/src/main/java/com/navinfo/omqs/OMQSApplication.kt @@ -2,6 +2,8 @@ package com.navinfo.omqs import android.app.Application import android.util.Log +import com.navinfo.collect.library.data.dao.impl.MapLifeDataBase +import com.navinfo.omqs.db.TraceDataBase import com.navinfo.omqs.tools.FileManager import com.navinfo.omqs.ui.manager.TakePhotoManager import com.navinfo.omqs.util.NetUtils diff --git a/app/src/main/java/com/navinfo/omqs/db/RoomAppDatabase.kt b/app/src/main/java/com/navinfo/omqs/db/RoomAppDatabase.kt index 260df186..be0365e2 100644 --- a/app/src/main/java/com/navinfo/omqs/db/RoomAppDatabase.kt +++ b/app/src/main/java/com/navinfo/omqs/db/RoomAppDatabase.kt @@ -2,6 +2,7 @@ package com.navinfo.omqs.db import androidx.room.Database import androidx.room.RoomDatabase +import com.navinfo.collect.library.data.entity.NiLocation import com.navinfo.omqs.bean.OfflineMapCityBean import com.navinfo.omqs.bean.ScProblemTypeBean import com.navinfo.omqs.bean.ScRootCauseAnalysisBean diff --git a/app/src/main/java/com/navinfo/omqs/db/TraceDataBase.java b/app/src/main/java/com/navinfo/omqs/db/TraceDataBase.java new file mode 100644 index 00000000..a37f25cd --- /dev/null +++ b/app/src/main/java/com/navinfo/omqs/db/TraceDataBase.java @@ -0,0 +1,184 @@ +package com.navinfo.omqs.db; + +import android.content.Context; +import android.os.AsyncTask; +import android.util.Log; +import androidx.annotation.NonNull; +import androidx.room.Database; +import androidx.room.Room; +import androidx.room.RoomDatabase; +import androidx.sqlite.db.SupportSQLiteDatabase; +import com.navinfo.collect.library.data.dao.impl.INiLocationDao; +import com.navinfo.collect.library.data.entity.NiLocation; +import com.tencent.wcdb.database.SQLiteCipherSpec; +import com.tencent.wcdb.database.SQLiteDatabase; +import com.tencent.wcdb.repair.BackupKit; +import com.tencent.wcdb.repair.RecoverKit; +import com.tencent.wcdb.room.db.WCDBDatabase; +import com.tencent.wcdb.room.db.WCDBOpenHelperFactory; + +@Database(entities = { NiLocation.class},version = 1, exportSchema = false) +public abstract class TraceDataBase extends RoomDatabase { + // marking the instance as volatile to ensure atomic access to the variable + /** + * 数据库单例对象 + */ + private static volatile TraceDataBase INSTANCE; + + /** + * 地图坐标库类 + */ + public abstract INiLocationDao getNiLocationDao(); + + /** + * 数据库秘钥 + */ + private final static String DB_PASSWORD = "123456"; + + public static TraceDataBase getDatabase(final Context context, final String name) { + if (INSTANCE == null) { + synchronized (TraceDataBase.class) { + if (INSTANCE == null) { + // [WCDB] To use Room library with WCDB, pass a WCDBOpenHelper factory object + // to the database builder with .openHelperFactory(...). In the factory object, + // you can specify passphrase and cipher options to open or create encrypted + // database, as well as optimization options like asynchronous checkpoint. + SQLiteCipherSpec cipherSpec = new SQLiteCipherSpec() + .setPageSize(1024) + .setSQLCipherVersion(3); + WCDBOpenHelperFactory factory = new WCDBOpenHelperFactory() + .passphrase(DB_PASSWORD.getBytes()) // passphrase to the database, remove this line for plain-text + .cipherSpec(cipherSpec) // cipher to use, remove for default settings + .writeAheadLoggingEnabled(true) // enable WAL mode, remove if not needed + .asyncCheckpointEnabled(true); // enable asynchronous checkpoint, remove if not needed + + INSTANCE = Room.databaseBuilder(context.getApplicationContext(), + TraceDataBase.class, name) + + // [WCDB] Specify open helper to use WCDB database implementation instead + // of the Android framework. + .openHelperFactory(factory) + + // Wipes and rebuilds instead of migrating if no Migration object. + // Migration is not part of this codelab. + .fallbackToDestructiveMigration() + .addCallback(sRoomDatabaseCallback) + .build(); + } + } + } + return INSTANCE; + } + + /** + * Override the onOpen method to populate the database. + * For this sample, we clear the database every time it is created or opened. + *

+ * If you want to populate the database only when the database is created for the 1st time, + * override RoomDatabase.Callback()#onCreate + */ + private static Callback sRoomDatabaseCallback = new Callback() { + + @Override + public void onOpen(@NonNull SupportSQLiteDatabase db) { + super.onOpen(db); + // If you want to keep the data through app restarts, + // comment out the following line. + new PopulateDbAsync(INSTANCE).execute(); + } + }; + + /** + * Populate the database in the background. + * If you want to start with more words, just add them. + */ + private static class PopulateDbAsync extends AsyncTask { + + private final ILayerManagerDao mLayerDao; + + PopulateDbAsync(TraceDataBase db) { + mLayerDao = db.getLayerManagerDao(); + } + + @Override + protected Void doInBackground(final Void... params) { + // Start the app with a clean database every time. + // Not needed if you only populate on creation. + //mDao.deleteAll(); + Log.e("qj", "doInBackground"); + return null; + } + } + + /** + * 数据恢复 + */ + protected boolean recoverData(){ + if(INSTANCE!=null){ + SQLiteDatabase sqlite = ((WCDBDatabase) INSTANCE.getOpenHelper().getWritableDatabase()).getInnerDatabase(); + RecoverKit recover = new RecoverKit( + sqlite, // 要恢复到的目标 DB + sqlite.getPath() + "-backup", // 备份文件 + DB_PASSWORD.getBytes() // 加密备份文件的密钥,非 DB 密钥 + ); + int result = recover.run(false); // fatal 参数传 false 表示遇到错误忽略并继续, + // 若传 true 遇到错误则中止并返回 FAILED + switch (result) { + case RecoverKit.RESULT_OK: + /* 成功 */ + Log.e("qj","sRoomDatabaseCallback==RecoverKit成功"); + return true; + case RecoverKit.RESULT_CANCELED: /* 取消操作 */ + Log.e("qj","sRoomDatabaseCallback==RecoverKit取消操作"); + break; + case RecoverKit.RESULT_FAILED: /* 失败 */ + Log.e("qj","sRoomDatabaseCallback==RecoverKit失败"); + break; + + } + + recover.release(); + } + + return false; + } + + /** + * 备份数据 + */ + protected boolean backup() { + Log.e("qj", "sRoomDatabaseCallback===backup==start"); + if (INSTANCE != null) { + //备份文件 + SQLiteDatabase sqlite = ((WCDBDatabase) INSTANCE.getOpenHelper().getWritableDatabase()).getInnerDatabase(); + BackupKit backup = new BackupKit( + sqlite, // 要备份的 DB + sqlite.getPath() + "-backup", // 备份文件 + "123456".getBytes(), // 加密备份文件的密钥,非 DB 密钥 + 0, null); + int result = backup.run(); + switch (result) { + case BackupKit.RESULT_OK: + /* 成功 */ + Log.e("qj", "sRoomDatabaseCallback==成功"); + return true; + case BackupKit.RESULT_CANCELED: + /* 取消操作 */ + Log.e("qj", "sRoomDatabaseCallback==取消操作"); + break; + case BackupKit.RESULT_FAILED: + /* 失败 */ + Log.e("qj", "sRoomDatabaseCallback==失败"); + break; + } + + backup.release(); + } + Log.e("qj", "sRoomDatabaseCallback===backup==end"); + return false; + } + + protected void release() { + INSTANCE = null; + } +} diff --git a/app/src/main/java/com/navinfo/omqs/ui/activity/map/MainActivity.kt b/app/src/main/java/com/navinfo/omqs/ui/activity/map/MainActivity.kt index 1dfcd262..fd89a97a 100644 --- a/app/src/main/java/com/navinfo/omqs/ui/activity/map/MainActivity.kt +++ b/app/src/main/java/com/navinfo/omqs/ui/activity/map/MainActivity.kt @@ -12,7 +12,9 @@ import com.navinfo.collect.library.map.NIMapController import com.navinfo.omqs.Constant import com.navinfo.omqs.R import com.navinfo.omqs.databinding.ActivityMainBinding +import com.navinfo.omqs.db.TraceDataBase import com.navinfo.omqs.http.offlinemapdownload.OfflineMapDownloadManager +import com.navinfo.omqs.system.SystemConstant import com.navinfo.omqs.ui.activity.BaseActivity import dagger.hilt.android.AndroidEntryPoint import javax.inject.Inject @@ -53,6 +55,8 @@ class MainActivity : BaseActivity() { binding.viewModel = viewModel // lifecycle.addObserver(viewModel) lifecycleScope + //初始化轨迹文件 + TraceDataBase.getDatabase(this,Constant.DATA_PATH+SystemConstant.USER_ID+"/trace.sqlite") } override fun onStart() { diff --git a/build.gradle b/build.gradle index 327b0ab8..63d6efae 100644 --- a/build.gradle +++ b/build.gradle @@ -3,9 +3,6 @@ buildscript { dependencies { - classpath 'com.android.tools.build:gradle:4.2.2' - classpath('androidx.multidex:multidex:2.0.1') - classpath 'com.github.dcendents:android-maven-gradle-plugin:2.1' classpath "io.realm:realm-gradle-plugin:10.11.1" } } diff --git a/collect-library/build.gradle b/collect-library/build.gradle index c0267699..3cca075f 100644 --- a/collect-library/build.gradle +++ b/collect-library/build.gradle @@ -6,25 +6,47 @@ plugins { id 'kotlin-kapt' id 'realm-android' } -apply plugin: 'kotlin-android' -apply plugin: 'kotlin-kapt' -apply plugin: 'realm-android' +ext.roomversion = "2.1.0" ext.vtmVersion = "0.18.0" ext.realm_version = '10.10.1' ext.appcompatVersion = "1.3.0" ext.materialVersion = "1.5.0" -ext.kotlin_version = '1.8.0' +ext.kotlin_version = '1.7.0' android { compileSdk 30 + defaultConfig { + minSdk 23 + targetSdk 30 + versionCode 1 + versionName "1.0" + + testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" + consumerProguardFiles "consumer-rules.pro" + + // 指定room.schemaLocation生成的文件路径 + javaCompileOptions { + annotationProcessorOptions { + arguments = ["room.schemaLocation": "$projectDir/schemas".toString()] + } + } + ndk { + abiFilters "armeabi", "armeabi-v7a", "arm64-v8a" + } + } + buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' } } + compileOptions { + sourceCompatibility JavaVersion.VERSION_1_8 + targetCompatibility JavaVersion.VERSION_1_8 + } sourceSets { main { @@ -33,11 +55,13 @@ android { } } - +//configurations.all { +// resolutionStrategy { +// force 'com.intellij:annotations:13.0' +// } +//} dependencies { api fileTree(dir: 'libs', include: ['*.jar', '*.aar']) - implementation "androidx.appcompat:appcompat:$appcompatVersion" - implementation "com.google.android.material:material:$materialVersion" api files('libs/BaiduLBS_Android.jar') //