Merge branch 'master' of gitlab.navinfo.com:CollectVehicle/OneMapQS
Conflicts: app/src/main/java/com/navinfo/omqs/OMQSApplication.kt
This commit is contained in:
commit
6da6a4d101
@ -75,6 +75,9 @@ dependencies {
|
|||||||
implementation 'org.apache.poi:poi:5.2.3'
|
implementation 'org.apache.poi:poi:5.2.3'
|
||||||
implementation 'org.apache.poi:poi-ooxml:5.2.3'
|
implementation 'org.apache.poi:poi-ooxml:5.2.3'
|
||||||
|
|
||||||
|
// 读取spatialite文件
|
||||||
|
implementation 'com.github.sevar83:android-spatialite:2.0.1'
|
||||||
|
|
||||||
}
|
}
|
||||||
//允许引用生成的代码
|
//允许引用生成的代码
|
||||||
kapt {
|
kapt {
|
||||||
|
@ -1,11 +1,15 @@
|
|||||||
package com.navinfo.omqs
|
package com.navinfo.omqs
|
||||||
|
|
||||||
import android.app.Application
|
import android.app.Application
|
||||||
|
import android.util.Log
|
||||||
import com.navinfo.omqs.tools.FileManager
|
import com.navinfo.omqs.tools.FileManager
|
||||||
import dagger.hilt.android.HiltAndroidApp
|
import dagger.hilt.android.HiltAndroidApp
|
||||||
import io.realm.Realm
|
import io.realm.Realm
|
||||||
import io.realm.RealmConfiguration
|
import io.realm.RealmConfiguration
|
||||||
|
import kotlinx.coroutines.launch
|
||||||
import java.io.File
|
import java.io.File
|
||||||
|
import java.math.BigInteger
|
||||||
|
import java.security.MessageDigest
|
||||||
|
|
||||||
@HiltAndroidApp
|
@HiltAndroidApp
|
||||||
class OMQSApplication : Application() {
|
class OMQSApplication : Application() {
|
||||||
@ -13,16 +17,26 @@ class OMQSApplication : Application() {
|
|||||||
super.onCreate()
|
super.onCreate()
|
||||||
FileManager.initRootDir(this)
|
FileManager.initRootDir(this)
|
||||||
Realm.init(this)
|
Realm.init(this)
|
||||||
val password = "password".encodeToByteArray().copyInto(ByteArray(64))
|
val password = "encryp".encodeToByteArray().copyInto(ByteArray(64))
|
||||||
// 1110000011000010111001101110011011101110110111101110010011001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
|
// 70617373776f72640000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
|
||||||
// Log.d("", "密码是: ${BigInteger(1, password).toString(2).padStart(64, '0')}")
|
Log.d("OMQSApplication", "密码是: ${byteArrayToHexString(password)}")
|
||||||
val config = RealmConfiguration.Builder()
|
val config = RealmConfiguration.Builder()
|
||||||
.directory(File(Constant.DATA_PATH))
|
.directory(File(Constant.DATA_PATH))
|
||||||
.name("HDData")
|
.name("OMQS.realm")
|
||||||
|
.encryptionKey(password)
|
||||||
// .modules(Realm.getDefaultModule(), MyRealmModule())
|
// .modules(Realm.getDefaultModule(), MyRealmModule())
|
||||||
.schemaVersion(1)
|
.schemaVersion(1)
|
||||||
// .encryptionKey(password)
|
|
||||||
.build()
|
.build()
|
||||||
Realm.setDefaultConfiguration(config)
|
Realm.setDefaultConfiguration(config)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun getKey(inputString: String): String {
|
||||||
|
val messageDigest = MessageDigest.getInstance("SHA-256")
|
||||||
|
val hashBytes = messageDigest.digest(inputString.toByteArray())
|
||||||
|
return hashBytes.joinToString("") { "%02x".format(it) };
|
||||||
|
}
|
||||||
|
|
||||||
|
fun byteArrayToHexString(byteArray: ByteArray): String {
|
||||||
|
return byteArray.joinToString("") { "%02x".format(it) }
|
||||||
|
}
|
||||||
}
|
}
|
5
app/src/main/java/com/navinfo/omqs/bean/ImportConfig.kt
Normal file
5
app/src/main/java/com/navinfo/omqs/bean/ImportConfig.kt
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
package com.navinfo.omqs.bean
|
||||||
|
|
||||||
|
class ImportConfig {
|
||||||
|
var tables: MutableList<String> = mutableListOf()
|
||||||
|
}
|
118
app/src/main/java/com/navinfo/omqs/db/ImportOMDBHelper.kt
Normal file
118
app/src/main/java/com/navinfo/omqs/db/ImportOMDBHelper.kt
Normal file
@ -0,0 +1,118 @@
|
|||||||
|
package com.navinfo.omqs.db
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import android.database.Cursor.*
|
||||||
|
import androidx.core.database.getBlobOrNull
|
||||||
|
import androidx.core.database.getFloatOrNull
|
||||||
|
import androidx.core.database.getIntOrNull
|
||||||
|
import androidx.core.database.getStringOrNull
|
||||||
|
import com.google.gson.Gson
|
||||||
|
import com.navinfo.omqs.bean.ImportConfig
|
||||||
|
import com.navinfo.omqs.hilt.ImportOMDBHiltFactory
|
||||||
|
import com.navinfo.omqs.hilt.OMDBDataBaseHiltFactory
|
||||||
|
import dagger.assisted.Assisted
|
||||||
|
import dagger.assisted.AssistedInject
|
||||||
|
import kotlinx.coroutines.Dispatchers
|
||||||
|
import kotlinx.coroutines.flow.Flow
|
||||||
|
import kotlinx.coroutines.flow.flow
|
||||||
|
import kotlinx.coroutines.withContext
|
||||||
|
import org.spatialite.database.SQLiteDatabase
|
||||||
|
import java.io.File
|
||||||
|
import javax.inject.Inject
|
||||||
|
import kotlin.streams.toList
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 导入omdb数据的帮助类
|
||||||
|
* */
|
||||||
|
class ImportOMDBHelper @AssistedInject constructor(@Assisted("context") val context: Context,@Assisted("omdbFile") val omdbFile: File,@Assisted("configFile") val configFile: File) {
|
||||||
|
@Inject
|
||||||
|
lateinit var omdbHiltFactory: OMDBDataBaseHiltFactory
|
||||||
|
@Inject
|
||||||
|
lateinit var gson: Gson
|
||||||
|
private val database by lazy { omdbHiltFactory.obtainOmdbDataBaseHelper(context, omdbFile.absolutePath, 1).writableDatabase }
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 读取config的配置文件
|
||||||
|
* */
|
||||||
|
fun openConfigFile(): ImportConfig {
|
||||||
|
val configStr = configFile.readText()
|
||||||
|
return gson.fromJson(configStr, ImportConfig::class.java)
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 读取指定数据表的数据集
|
||||||
|
* */
|
||||||
|
suspend fun getOMDBTableData(table: String): Flow<List<Map<String, Any>>> =
|
||||||
|
withContext(Dispatchers.IO) {
|
||||||
|
val listResult: MutableList<Map<String, Any>> = mutableListOf()
|
||||||
|
flow<List<Map<String, Any>>> {
|
||||||
|
if (database.isOpen) {
|
||||||
|
val comumns = mutableListOf<String>()
|
||||||
|
// 获取要读取的列名
|
||||||
|
val columns = getColumns(database, table)
|
||||||
|
// 处理列名,如果列名是GEOMETRY,则使用spatialite函数ST_AsText读取blob数据
|
||||||
|
val finalColumns = columns.stream().map {
|
||||||
|
val column = it.replace("\"", "", true)
|
||||||
|
if ("GEOMETRY".equals(column, ignoreCase = true)) {
|
||||||
|
"ST_AsText($column)"
|
||||||
|
} else {
|
||||||
|
column
|
||||||
|
}
|
||||||
|
}.toList()
|
||||||
|
|
||||||
|
val cursor = database.query(table, finalColumns.toTypedArray(), "1=1",
|
||||||
|
mutableListOf<String>().toTypedArray(), null, null, null, null)
|
||||||
|
with(cursor) {
|
||||||
|
if (moveToFirst()) {
|
||||||
|
while (moveToNext()) {
|
||||||
|
val rowMap = mutableMapOf<String, Any>()
|
||||||
|
for (columnIndex in 0 until columnCount) {
|
||||||
|
var columnName = getColumnName(columnIndex)
|
||||||
|
if (columnName.startsWith("ST_AsText(")) {
|
||||||
|
columnName = columnName.replace("ST_AsText(", "").substringBeforeLast(")")
|
||||||
|
}
|
||||||
|
when(getType(columnIndex)) {
|
||||||
|
FIELD_TYPE_NULL -> rowMap[columnName] = ""
|
||||||
|
FIELD_TYPE_INTEGER -> rowMap[columnName] = getInt(columnIndex)
|
||||||
|
FIELD_TYPE_FLOAT -> rowMap[columnName] = getFloat(columnIndex)
|
||||||
|
FIELD_TYPE_BLOB -> rowMap[columnName] = String(getBlob(columnIndex), Charsets.UTF_8)
|
||||||
|
else -> rowMap[columnName] = getString(columnIndex)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
listResult.add(rowMap)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
emit(listResult)
|
||||||
|
cursor.close()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取指定数据表的列名
|
||||||
|
fun getColumns(db: SQLiteDatabase, tableName: String): List<String> {
|
||||||
|
val columns = mutableListOf<String>()
|
||||||
|
|
||||||
|
// 查询 sqlite_master 表获取指定数据表的元数据信息
|
||||||
|
val cursor = db.query("sqlite_master", arrayOf("sql"), "type='table' AND name=?", arrayOf(tableName), null, null, null)
|
||||||
|
|
||||||
|
// 从元数据信息中解析出列名
|
||||||
|
if (cursor.moveToFirst()) {
|
||||||
|
val sql = cursor.getString(0)
|
||||||
|
val startIndex = sql.indexOf("(") + 1
|
||||||
|
val endIndex = sql.lastIndexOf(")")
|
||||||
|
val columnDefs = sql.substring(startIndex, endIndex).split(",")
|
||||||
|
for (columnDef in columnDefs) {
|
||||||
|
val columnName = columnDef.trim().split(" ")[0]
|
||||||
|
if (!columnName.startsWith("rowid", true)) { // 排除 rowid 列
|
||||||
|
columns.add(columnName)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
cursor.close()
|
||||||
|
return columns
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
20
app/src/main/java/com/navinfo/omqs/db/OmdbDataBaseHelper.kt
Normal file
20
app/src/main/java/com/navinfo/omqs/db/OmdbDataBaseHelper.kt
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
package com.navinfo.omqs.db
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import dagger.assisted.Assisted
|
||||||
|
import dagger.assisted.AssistedInject
|
||||||
|
import org.spatialite.database.SQLiteDatabase
|
||||||
|
import org.spatialite.database.SQLiteOpenHelper
|
||||||
|
|
||||||
|
class OmdbDataBaseHelper @AssistedInject constructor(@Assisted("context")context: Context, @Assisted("dbName") dbName: String, @Assisted("dbVersion") dbVersion: Int) :
|
||||||
|
SQLiteOpenHelper(context, dbName, null, dbVersion) {
|
||||||
|
override fun onCreate(db: SQLiteDatabase?) {
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onUpgrade(db: SQLiteDatabase?, oldVersion: Int, newVersion: Int) {
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onOpen(db: SQLiteDatabase?) {
|
||||||
|
super.onOpen(db)
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,12 @@
|
|||||||
|
package com.navinfo.omqs.hilt
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import com.navinfo.omqs.db.ImportOMDBHelper
|
||||||
|
import dagger.assisted.Assisted
|
||||||
|
import dagger.assisted.AssistedFactory
|
||||||
|
import java.io.File
|
||||||
|
|
||||||
|
@AssistedFactory
|
||||||
|
interface ImportOMDBHiltFactory {
|
||||||
|
fun obtainImportOMDBHelper(@Assisted("context")context: Context, @Assisted("omdbFile") omdbFile: File, @Assisted("configFile") dbVersion: File): ImportOMDBHelper
|
||||||
|
}
|
@ -0,0 +1,11 @@
|
|||||||
|
package com.navinfo.omqs.hilt
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import com.navinfo.omqs.db.OmdbDataBaseHelper
|
||||||
|
import dagger.assisted.Assisted
|
||||||
|
import dagger.assisted.AssistedFactory
|
||||||
|
|
||||||
|
@AssistedFactory
|
||||||
|
interface OMDBDataBaseHiltFactory {
|
||||||
|
fun obtainOmdbDataBaseHelper(@Assisted("context")context: Context, @Assisted("dbName") dbName: String, @Assisted("dbVersion") dbVersion: Int): OmdbDataBaseHelper
|
||||||
|
}
|
29
app/src/main/java/com/navinfo/omqs/tools/CoroutineUtils.kt
Normal file
29
app/src/main/java/com/navinfo/omqs/tools/CoroutineUtils.kt
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
package com.navinfo.omqs.tools
|
||||||
|
import android.app.ProgressDialog
|
||||||
|
import android.content.Context
|
||||||
|
import com.google.android.material.R
|
||||||
|
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||||
|
import kotlinx.coroutines.*
|
||||||
|
import kotlin.coroutines.CoroutineContext
|
||||||
|
|
||||||
|
object CoroutineUtils {
|
||||||
|
fun <T> launchWithLoading(
|
||||||
|
context: Context,
|
||||||
|
coroutineContext: CoroutineContext = Dispatchers.Main,
|
||||||
|
loadingMessage: String? = null,
|
||||||
|
task: suspend CoroutineScope.() -> T
|
||||||
|
): Job {
|
||||||
|
val progressDialog = MaterialAlertDialogBuilder(
|
||||||
|
context, R.style.MaterialAlertDialog_Material3).setMessage(loadingMessage).setCancelable(false).show()
|
||||||
|
|
||||||
|
return CoroutineScope(coroutineContext).launch {
|
||||||
|
try {
|
||||||
|
withContext(Dispatchers.IO) {
|
||||||
|
task.invoke(this)
|
||||||
|
}
|
||||||
|
} finally {
|
||||||
|
progressDialog.dismiss()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,16 +1,38 @@
|
|||||||
package com.navinfo.omqs.ui.activity
|
package com.navinfo.omqs.ui.activity
|
||||||
|
|
||||||
|
import android.app.Dialog
|
||||||
import android.content.pm.ActivityInfo
|
import android.content.pm.ActivityInfo
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.os.PersistableBundle
|
import android.os.PersistableBundle
|
||||||
|
import androidx.appcompat.app.AlertDialog
|
||||||
import androidx.appcompat.app.AppCompatActivity
|
import androidx.appcompat.app.AppCompatActivity
|
||||||
|
import com.google.android.material.R
|
||||||
|
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 基类
|
* 基类
|
||||||
*/
|
*/
|
||||||
open class BaseActivity : AppCompatActivity() {
|
open class BaseActivity : AppCompatActivity() {
|
||||||
|
private var loadingDialog: AlertDialog? = null
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
override fun onCreate(savedInstanceState: Bundle?) {
|
||||||
requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE//横屏
|
requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE//横屏
|
||||||
super.onCreate(savedInstanceState)
|
super.onCreate(savedInstanceState)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 显示loading dialog
|
||||||
|
*/
|
||||||
|
fun showLoadingDialog(message: String) {
|
||||||
|
loadingDialog?.dismiss()
|
||||||
|
loadingDialog = MaterialAlertDialogBuilder(
|
||||||
|
this@BaseActivity, R.style.MaterialAlertDialog_Material3).setMessage(message).setCancelable(false).show()
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 隐藏loading dialog
|
||||||
|
* */
|
||||||
|
fun hideLoadingDialog() {
|
||||||
|
loadingDialog?.dismiss()
|
||||||
|
loadingDialog = null
|
||||||
|
}
|
||||||
}
|
}
|
@ -3,19 +3,36 @@ package com.navinfo.omqs.ui.fragment.personalcenter
|
|||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
|
import android.util.Log
|
||||||
import android.view.LayoutInflater
|
import android.view.LayoutInflater
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.fragment.app.Fragment
|
import androidx.fragment.app.Fragment
|
||||||
import androidx.fragment.app.viewModels
|
import androidx.fragment.app.viewModels
|
||||||
|
import androidx.lifecycle.lifecycleScope
|
||||||
import androidx.navigation.fragment.findNavController
|
import androidx.navigation.fragment.findNavController
|
||||||
import com.blankj.utilcode.util.UriUtils
|
import com.blankj.utilcode.util.UriUtils
|
||||||
import com.github.k1rakishou.fsaf.FileChooser
|
import com.github.k1rakishou.fsaf.FileChooser
|
||||||
import com.github.k1rakishou.fsaf.callback.FSAFActivityCallbacks
|
import com.github.k1rakishou.fsaf.callback.FSAFActivityCallbacks
|
||||||
import com.github.k1rakishou.fsaf.callback.FileChooserCallback
|
import com.github.k1rakishou.fsaf.callback.FileChooserCallback
|
||||||
|
import com.navinfo.collect.library.data.RealmUtils
|
||||||
|
import com.navinfo.collect.library.data.entity.OMDBEntity
|
||||||
import com.navinfo.omqs.R
|
import com.navinfo.omqs.R
|
||||||
import com.navinfo.omqs.databinding.FragmentPersonalCenterBinding
|
import com.navinfo.omqs.databinding.FragmentPersonalCenterBinding
|
||||||
|
import com.navinfo.omqs.db.ImportOMDBHelper
|
||||||
|
import com.navinfo.omqs.hilt.ImportOMDBHiltFactory
|
||||||
|
import com.navinfo.omqs.tools.CoroutineUtils
|
||||||
|
import com.navinfo.omqs.ui.activity.BaseActivity
|
||||||
import dagger.hilt.android.AndroidEntryPoint
|
import dagger.hilt.android.AndroidEntryPoint
|
||||||
|
import io.realm.Realm
|
||||||
|
import io.realm.RealmDictionary
|
||||||
|
import kotlinx.coroutines.Dispatchers
|
||||||
|
import kotlinx.coroutines.flow.FlowCollector
|
||||||
|
import kotlinx.coroutines.launch
|
||||||
|
import kotlinx.coroutines.withContext
|
||||||
|
import java.io.File
|
||||||
|
import java.util.UUID
|
||||||
|
import javax.inject.Inject
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 个人中心
|
* 个人中心
|
||||||
@ -27,6 +44,8 @@ class PersonalCenterFragment : Fragment(), FSAFActivityCallbacks {
|
|||||||
private val binding get() = _binding!!
|
private val binding get() = _binding!!
|
||||||
private val fileChooser by lazy { FileChooser(requireContext()) }
|
private val fileChooser by lazy { FileChooser(requireContext()) }
|
||||||
private val viewModel by lazy { viewModels<PersonalCenterViewModel>().value }
|
private val viewModel by lazy { viewModels<PersonalCenterViewModel>().value }
|
||||||
|
@Inject
|
||||||
|
lateinit var importOMDBHiltFactory: ImportOMDBHiltFactory
|
||||||
|
|
||||||
|
|
||||||
override fun onCreateView(
|
override fun onCreateView(
|
||||||
@ -52,7 +71,11 @@ class PersonalCenterFragment : Fragment(), FSAFActivityCallbacks {
|
|||||||
override fun onResult(uri: Uri) {
|
override fun onResult(uri: Uri) {
|
||||||
val file = UriUtils.uri2File(uri)
|
val file = UriUtils.uri2File(uri)
|
||||||
// 开始导入数据
|
// 开始导入数据
|
||||||
viewModel.importOmdbData(file)
|
// 656e6372797000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
val job = CoroutineUtils.launchWithLoading(requireContext(), loadingMessage = "导入数据...") {
|
||||||
|
val importOMDBHelper: ImportOMDBHelper = importOMDBHiltFactory.obtainImportOMDBHelper(requireContext(), file, File(file.parentFile, "config.json"))
|
||||||
|
viewModel.importOMDBData(importOMDBHelper)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -1,39 +1,61 @@
|
|||||||
package com.navinfo.omqs.ui.fragment.personalcenter
|
package com.navinfo.omqs.ui.fragment.personalcenter
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
import android.util.Log
|
import android.util.Log
|
||||||
import androidx.lifecycle.ViewModel
|
import androidx.lifecycle.ViewModel
|
||||||
import androidx.lifecycle.viewModelScope
|
import androidx.lifecycle.viewModelScope
|
||||||
import com.blankj.utilcode.util.UriUtils
|
import com.blankj.utilcode.util.UriUtils
|
||||||
|
import com.navinfo.collect.library.data.entity.OMDBEntity
|
||||||
import com.navinfo.omqs.bean.ScProblemTypeBean
|
import com.navinfo.omqs.bean.ScProblemTypeBean
|
||||||
import com.navinfo.omqs.bean.ScRootCauseAnalysisBean
|
import com.navinfo.omqs.bean.ScRootCauseAnalysisBean
|
||||||
|
import com.navinfo.omqs.db.ImportOMDBHelper
|
||||||
import com.navinfo.omqs.db.RoomAppDatabase
|
import com.navinfo.omqs.db.RoomAppDatabase
|
||||||
import dagger.hilt.android.lifecycle.HiltViewModel
|
import dagger.hilt.android.lifecycle.HiltViewModel
|
||||||
|
import io.realm.Realm
|
||||||
|
import io.realm.RealmDictionary
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import org.apache.poi.ss.usermodel.Cell
|
|
||||||
import org.apache.poi.ss.usermodel.Row
|
import org.apache.poi.ss.usermodel.Row
|
||||||
import org.apache.poi.ss.usermodel.Sheet
|
|
||||||
import org.apache.poi.ss.usermodel.WorkbookFactory
|
import org.apache.poi.ss.usermodel.WorkbookFactory
|
||||||
import java.io.File
|
import java.io.File
|
||||||
import java.io.FileInputStream
|
import java.io.FileInputStream
|
||||||
import java.io.IOException
|
import java.io.IOException
|
||||||
import java.io.InputStream
|
import java.io.InputStream
|
||||||
|
import java.util.*
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@HiltViewModel
|
@HiltViewModel
|
||||||
class PersonalCenterViewModel @Inject constructor(
|
class PersonalCenterViewModel @Inject constructor(
|
||||||
private val roomAppDatabase: RoomAppDatabase
|
private val roomAppDatabase: RoomAppDatabase
|
||||||
) : ViewModel() {
|
) : ViewModel() {
|
||||||
fun importOmdbData(omdbFile: File) {
|
/**
|
||||||
// 检查File是否为sqlite数据库
|
* 导入OMDB数据
|
||||||
if (omdbFile == null || !omdbFile.exists()) {
|
* */
|
||||||
throw Exception("文件不存在")
|
suspend fun importOMDBData(importOMDBHelper: ImportOMDBHelper) {
|
||||||
|
Log.d("OMQSApplication", "开始导入数据")
|
||||||
|
// Realm.getDefaultInstance().beginTransaction()
|
||||||
|
for (table in importOMDBHelper.openConfigFile().tables/*listOf<String>("HAD_LINK")*/) {
|
||||||
|
importOMDBHelper.getOMDBTableData(table).collect {
|
||||||
|
for (map in it) {
|
||||||
|
val properties = RealmDictionary<String?>()
|
||||||
|
for (entry in map.entries) {
|
||||||
|
properties.putIfAbsent(entry.key, entry.value.toString())
|
||||||
}
|
}
|
||||||
if (!omdbFile.name.endsWith(".sqlite") and !omdbFile.name.endsWith("db")) {
|
// 将读取到的sqlite数据插入到Realm中
|
||||||
throw Exception("文件不存在")
|
Realm.getDefaultInstance().insert(OMDBEntity(table, properties))
|
||||||
|
// 将读取到的数据写入到json中
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
// Realm.getDefaultInstance().commitTransaction()
|
||||||
|
|
||||||
|
// 数据导入结束后,开始生成渲染表所需的json文件,并生成压缩包
|
||||||
|
|
||||||
|
|
||||||
|
Log.d("OMQSApplication", "导入数据完成")
|
||||||
|
}
|
||||||
|
|
||||||
fun importScProblemData(uri: Uri) {
|
fun importScProblemData(uri: Uri) {
|
||||||
viewModelScope.launch(Dispatchers.IO) {
|
viewModelScope.launch(Dispatchers.IO) {
|
||||||
|
@ -18,6 +18,10 @@
|
|||||||
android:id="@+id/personal_center_menu_import_yuan_data"
|
android:id="@+id/personal_center_menu_import_yuan_data"
|
||||||
android:icon="@drawable/ic_baseline_import_export_24"
|
android:icon="@drawable/ic_baseline_import_export_24"
|
||||||
android:title="导入元数据" />
|
android:title="导入元数据" />
|
||||||
|
<item
|
||||||
|
android:id="@+id/personal_center_menu_realm_data_backup"
|
||||||
|
android:icon="@drawable/ic_baseline_import_export_24"
|
||||||
|
android:title="备份数据" />
|
||||||
</group>
|
</group>
|
||||||
<group
|
<group
|
||||||
android:id="@+id/group2"
|
android:id="@+id/group2"
|
||||||
|
@ -0,0 +1,17 @@
|
|||||||
|
package com.navinfo.collect.library.data.entity
|
||||||
|
|
||||||
|
import io.realm.RealmDictionary
|
||||||
|
import io.realm.RealmObject
|
||||||
|
import io.realm.annotations.PrimaryKey
|
||||||
|
|
||||||
|
open class OMDBEntity(): RealmObject() {
|
||||||
|
@PrimaryKey
|
||||||
|
var id: Long = 0
|
||||||
|
lateinit var table: String
|
||||||
|
lateinit var properties: RealmDictionary<String?>
|
||||||
|
|
||||||
|
constructor(table: String, properties: RealmDictionary<String?>): this() {
|
||||||
|
this.table = table
|
||||||
|
this.properties = properties
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,38 @@
|
|||||||
|
package com.navinfo.collect.library.data.entity
|
||||||
|
|
||||||
|
import com.navinfo.collect.library.system.Constant
|
||||||
|
import com.navinfo.collect.library.utils.GeometryTools
|
||||||
|
import com.navinfo.collect.library.utils.GeometryToolsKt
|
||||||
|
import io.realm.RealmDictionary
|
||||||
|
import io.realm.RealmObject
|
||||||
|
import io.realm.RealmSet
|
||||||
|
import io.realm.annotations.PrimaryKey
|
||||||
|
import org.locationtech.jts.geom.Coordinate
|
||||||
|
import org.locationtech.jts.geom.Geometry
|
||||||
|
import org.oscim.core.MercatorProjection
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 渲染要素对应的实体
|
||||||
|
* */
|
||||||
|
open class RenderEntity(): RealmObject() {
|
||||||
|
@PrimaryKey
|
||||||
|
var id: Long = 0 // id
|
||||||
|
lateinit var name: String //要素名
|
||||||
|
var code: Int = 0 // 要素编码
|
||||||
|
var geometry: String = ""
|
||||||
|
get() = field
|
||||||
|
set(value) {
|
||||||
|
field = value
|
||||||
|
// 根据geometry自动计算当前要素的x-tile和y-tile
|
||||||
|
GeometryToolsKt.getTileXByGeometry(value, tileX)
|
||||||
|
GeometryToolsKt.getTileYByGeometry(value, tileY)
|
||||||
|
}
|
||||||
|
lateinit var properties: RealmDictionary<String?>
|
||||||
|
val tileX: RealmSet<Int> = RealmSet() // x方向的tile编码
|
||||||
|
val tileY: RealmSet<Int> = RealmSet() // y方向的tile编码
|
||||||
|
|
||||||
|
constructor(name: String, properties: RealmDictionary<String?>): this() {
|
||||||
|
this.name = name
|
||||||
|
this.properties = properties
|
||||||
|
}
|
||||||
|
}
|
@ -36,6 +36,7 @@ class NIMapController {
|
|||||||
measureLayerHandler = MeasureLayerHandler(context, mapView)
|
measureLayerHandler = MeasureLayerHandler(context, mapView)
|
||||||
mMapView = mapView
|
mMapView = mapView
|
||||||
mapView.setOptions(options)
|
mapView.setOptions(options)
|
||||||
|
mMapView.vtmMap.viewport().maxZoomLevel = Constant.MAX_ZOOM // 设置地图的最大级别
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -29,6 +29,7 @@ public class Constant {
|
|||||||
HAD_LAYER_INVISIABLE_ARRAY = HD_LAYER_VISIABLE_MAP.keySet().toArray(new String[HD_LAYER_VISIABLE_MAP.keySet().size()]);
|
HAD_LAYER_INVISIABLE_ARRAY = HD_LAYER_VISIABLE_MAP.keySet().toArray(new String[HD_LAYER_VISIABLE_MAP.keySet().size()]);
|
||||||
}
|
}
|
||||||
public static String[] HAD_LAYER_INVISIABLE_ARRAY;
|
public static String[] HAD_LAYER_INVISIABLE_ARRAY;
|
||||||
public static final int OVER_ZOOM = 23;
|
public static final int OVER_ZOOM = 21;
|
||||||
|
public static final int MAX_ZOOM = 25;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -173,7 +173,6 @@ public class GeometryTools {
|
|||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return createMultiPoint;
|
return createMultiPoint;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
package com.navinfo.collect.library.utils
|
package com.navinfo.collect.library.utils
|
||||||
|
|
||||||
|
import com.navinfo.collect.library.system.Constant
|
||||||
import io.realm.RealmSet
|
import io.realm.RealmSet
|
||||||
import org.locationtech.jts.geom.Geometry
|
import org.locationtech.jts.geom.Geometry
|
||||||
import org.locationtech.jts.io.WKTReader
|
import org.locationtech.jts.io.WKTReader
|
||||||
@ -10,7 +11,7 @@ class GeometryToolsKt {
|
|||||||
/**
|
/**
|
||||||
* 根据给定的geometry计算其横跨的20级瓦片Y值
|
* 根据给定的geometry计算其横跨的20级瓦片Y值
|
||||||
*/
|
*/
|
||||||
fun getTileYByGeometry(wkt: String, tileYSet: MutableSet<Int?>){
|
fun getTileYByGeometry(wkt: String, tileYSet: MutableSet<Int?>) {
|
||||||
|
|
||||||
val reader = WKTReader()
|
val reader = WKTReader()
|
||||||
val geometry = reader.read(wkt);
|
val geometry = reader.read(wkt);
|
||||||
@ -37,8 +38,8 @@ class GeometryToolsKt {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
// 分别计算最大和最小x值对应的tile号
|
// 分别计算最大和最小x值对应的tile号
|
||||||
val tileY0 = MercatorProjection.latitudeToTileY(minMaxY[0], 20.toByte())
|
val tileY0 = MercatorProjection.latitudeToTileY(minMaxY[0], Constant.OVER_ZOOM.toByte())
|
||||||
val tileY1 = MercatorProjection.latitudeToTileY(minMaxY[1], 20.toByte())
|
val tileY1 = MercatorProjection.latitudeToTileY(minMaxY[1], Constant.OVER_ZOOM.toByte())
|
||||||
val minTileY = if (tileY0 <= tileY1) tileY0 else tileY1
|
val minTileY = if (tileY0 <= tileY1) tileY0 else tileY1
|
||||||
val maxTileY = if (tileY0 <= tileY1) tileY1 else tileY0
|
val maxTileY = if (tileY0 <= tileY1) tileY1 else tileY0
|
||||||
println("getTileYByGeometry$envelope===$minTileY===$maxTileY")
|
println("getTileYByGeometry$envelope===$minTileY===$maxTileY")
|
||||||
@ -81,8 +82,8 @@ class GeometryToolsKt {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
// 分别计算最大和最小x值对应的tile号
|
// 分别计算最大和最小x值对应的tile号
|
||||||
val tileX0 = MercatorProjection.longitudeToTileX(minMaxX[0], 20.toByte())
|
val tileX0 = MercatorProjection.longitudeToTileX(minMaxX[0], Constant.OVER_ZOOM.toByte())
|
||||||
val tileX1 = MercatorProjection.longitudeToTileX(minMaxX[1], 20.toByte())
|
val tileX1 = MercatorProjection.longitudeToTileX(minMaxX[1], Constant.OVER_ZOOM.toByte())
|
||||||
val minTileX = if (tileX0 <= tileX1) tileX0 else tileX1
|
val minTileX = if (tileX0 <= tileX1) tileX0 else tileX1
|
||||||
val maxTileX = if (tileX0 <= tileX1) tileX1 else tileX0
|
val maxTileX = if (tileX0 <= tileX1) tileX1 else tileX0
|
||||||
println("getTileXByGeometry$envelope$minTileX===$maxTileX")
|
println("getTileXByGeometry$envelope$minTileX===$maxTileX")
|
||||||
|
Loading…
x
Reference in New Issue
Block a user