commit
e2890e1478
1063 changed files with 186575 additions and 0 deletions
@ -0,0 +1,31 @@ |
||||
#git submodule update --init --recursive |
||||
*.hprof |
||||
build/ |
||||
.vscode/ |
||||
.gradle |
||||
/local.properties |
||||
/.idea |
||||
.DS_Store |
||||
/captures |
||||
/build |
||||
/app/build |
||||
/app/release |
||||
/app/mapping.txt |
||||
/app/src/main/libs |
||||
/app/src/main/obj |
||||
/controlapp/mapping.txt |
||||
/controlapp/release |
||||
/alpha/build |
||||
/alpha/release |
||||
/alpha/mapping.txt |
||||
/alpha/src/main/schemas/zone.a.dimap.db.RecordsDataBase/1.json |
||||
*.iml |
||||
.idea |
||||
*.jks |
||||
obj/ |
||||
.cxx/ |
||||
*.class |
||||
#定制版本 |
||||
/app/*/release |
||||
/alpha/*/release |
||||
/pad/*/release |
@ -0,0 +1,3 @@ |
||||
[submodule "control_common"] |
||||
path = control_common |
||||
url = http://code.bingce.com/BingCe-Android/control_common.git |
Binary file not shown.
@ -0,0 +1,2 @@ |
||||
configurations.maybeCreate("default") |
||||
artifacts.add("default", file('base-release.aar')) |
@ -0,0 +1,2 @@ |
||||
/build |
||||
*/release |
@ -0,0 +1,5 @@ |
||||
打包注意事项: |
||||
1.检查 Test.java 中的DEBUG是否为false; |
||||
2.检查 打包版本号; |
||||
3.检查数据库版本号; |
||||
4.检查changelog.xml内容 |
@ -0,0 +1,150 @@ |
||||
import com.bingce.AndroidSdk |
||||
import com.bingce.App |
||||
import com.bingce.Libs |
||||
import com.bingce.ModuleName |
||||
|
||||
apply plugin: 'com.android.application' |
||||
apply plugin: 'org.jetbrains.kotlin.android' |
||||
apply plugin: 'kotlin-kapt' |
||||
apply plugin: 'kotlin-parcelize' |
||||
apply from: "../control_common/config.gradle" |
||||
|
||||
|
||||
android { |
||||
useLibrary Libs.httpLegacy |
||||
compileSdk AndroidSdk.compileSdkVersion |
||||
namespace App.ControlNetwork.applicationId |
||||
|
||||
defaultConfig { |
||||
versionName "1.0.1" |
||||
versionCode 1 |
||||
minSdkVersion AndroidSdk.minSdkVersion |
||||
targetSdkVersion AndroidSdk.targetSdkVersion |
||||
ndk {} |
||||
testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner" |
||||
multiDexEnabled true |
||||
|
||||
javaCompileOptions { |
||||
annotationProcessorOptions { |
||||
arguments = [ |
||||
//数据库room |
||||
"room.schemaLocation": "$projectDir/src/main/schemas".toString() |
||||
] |
||||
} |
||||
} |
||||
} |
||||
|
||||
buildFeatures { |
||||
viewBinding true |
||||
buildConfig true |
||||
} |
||||
|
||||
signingConfigs { |
||||
debug { |
||||
storeFile file('./debug.keystore') |
||||
} |
||||
} |
||||
|
||||
buildTypes { |
||||
debug { |
||||
signingConfig signingConfigs.debug |
||||
minifyEnabled false |
||||
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' |
||||
} |
||||
release { |
||||
minifyEnabled true |
||||
shrinkResources true |
||||
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' |
||||
} |
||||
} |
||||
|
||||
splits { |
||||
// Split apks on build target ABI, view all options for the splits here: |
||||
// http://tools.android.com/tech-docs/new-build-system/user-guide/apk-splits |
||||
abi { |
||||
enable true |
||||
reset() |
||||
include 'arm64-v8a'//,'armeabi-v7a', 'x86'//, 'x86_64', 'mips','armeabi', |
||||
} |
||||
} |
||||
|
||||
//为了解决部分第三方库重复打包了META-INF的问题 |
||||
packagingOptions { |
||||
exclude 'META-INF/DEPENDENCIES' |
||||
exclude 'META-INF/LICENSE.txt' |
||||
exclude 'META-INF/NOTICE.txt' |
||||
exclude 'META-INF/LICENSE' |
||||
exclude 'META-INF/NOTICE' |
||||
|
||||
exclude 'META-INF/*.kotlin_module' |
||||
exclude '/META-INF/{AL2.0,LGPL2.1}'//适配compose |
||||
// exclude 'schemaorg_apache_xmlbeans/**' |
||||
// exclude 'assets/org/apache/**' |
||||
// exclude 'org/apache/**' |
||||
// exclude 'font_metrics.properties' |
||||
} |
||||
|
||||
lintOptions { |
||||
abortOnError false |
||||
disable 'GoogleAppIndexingWarning' |
||||
} |
||||
} |
||||
|
||||
dependencies { |
||||
implementation fileTree(include: ['*.jar', '*.aar'], dir: 'libs') |
||||
implementation project(':control_common') |
||||
|
||||
def moduleName = new ModuleName(project) |
||||
implementation project(moduleName.bingceModule("appBase")) |
||||
implementation project(moduleName.bingceModule("repository")) |
||||
implementation project(moduleName.bingceModule("base")) |
||||
implementation project(moduleName.bingceModule("leancloud")) |
||||
implementation project(moduleName.bingceModule("base-java")) |
||||
implementation project(moduleName.bingceModule("utils")) |
||||
implementation project(moduleName.bingceModule("coordlib")) |
||||
implementation project(moduleName.bingceModule("device")) |
||||
implementation project(moduleName.bingceModule("device-ui")) |
||||
implementation project(moduleName.bingceModule("rtk")) |
||||
implementation project(moduleName.bingceModule("totalstation")) |
||||
implementation project(moduleName.bingceModule("level")) |
||||
implementation project(moduleName.bingceModule("bcdialog-style")) |
||||
implementation project(moduleName.openSourceModule("utilcode")) |
||||
implementation project(moduleName.openSourceModule("colorful"))//选择主题颜色 |
||||
implementation project(moduleName.openSourceModule("dragExpandGrid"))//管理里的布局 |
||||
implementation project(moduleName.openSourceModule("lsettingitemlibrary"))//用户信息里 |
||||
implementation project(moduleName.openSourceModule("spinkit"))//loading控件 导出使用 |
||||
implementation project(moduleName.openSourceModule("splashview"))//广告view |
||||
implementation project(moduleName.openSourceModule("poishadowjar"))//导入excel |
||||
implementation project(moduleName.openSourceModule("safFilePicker"))//选择文件 |
||||
implementation project(moduleName.openSourceModule("fastjson")) |
||||
implementation project(moduleName.openSourceModule("agentweb")) |
||||
implementation project(":opensource:exFilePicker") |
||||
implementation project(":sdk:tensorFlowTTS")//语音播报 |
||||
implementation Libs.RxImagePicker.core |
||||
// implementation Libs.RxImagePicker.support |
||||
// implementation Libs.RxImagePicker.supportWechat |
||||
|
||||
constraints { |
||||
implementation("org.jetbrains.kotlin:kotlin-stdlib-jdk7:1.9.10") { |
||||
because("kotlin-stdlib-jdk7 is now a part of kotlin-stdlib") |
||||
} |
||||
implementation("org.jetbrains.kotlin:kotlin-stdlib-jdk8:1.9.10") { |
||||
because("kotlin-stdlib-jdk8 is now a part of kotlin-stdlib") |
||||
} |
||||
} |
||||
|
||||
// implementation "cn.leancloud:storage-android:8.2.5" |
||||
// implementation "cn.leancloud:realtime-android:8.2.5" |
||||
implementation Libs.LeanCloud.storage |
||||
implementation Libs.LeanCloud.realtime |
||||
|
||||
testImplementation "junit:junit:4.13.2" |
||||
androidTestImplementation "androidx.test:runner:1.1.0" |
||||
androidTestImplementation "androidx.test:rules:1.1.0" |
||||
androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.0' |
||||
|
||||
implementation 'com.google.android.gms:play-services-auth:20.7.0' |
||||
|
||||
project.ext.dependencies.each { k, v -> implementation v } |
||||
project.ext.kapt.each { k, v -> kapt v } |
||||
} |
Binary file not shown.
@ -0,0 +1,44 @@ |
||||
{ |
||||
"_type": "Project", |
||||
"_id": "AAAAAAFF+h6SjaM2Hec=", |
||||
"name": "Untitled", |
||||
"ownedElements": [ |
||||
{ |
||||
"_type": "UMLModel", |
||||
"_id": "AAAAAAFF+qBWK6M3Z8Y=", |
||||
"_parent": { |
||||
"$ref": "AAAAAAFF+h6SjaM2Hec=" |
||||
}, |
||||
"name": "Model", |
||||
"ownedElements": [ |
||||
{ |
||||
"_type": "UMLStateMachine", |
||||
"_id": "AAAAAAF5RXOA7okfG2A=", |
||||
"_parent": { |
||||
"$ref": "AAAAAAFF+qBWK6M3Z8Y=" |
||||
}, |
||||
"name": "StateMachine1", |
||||
"ownedElements": [ |
||||
{ |
||||
"_type": "UMLStatechartDiagram", |
||||
"_id": "AAAAAAF5RXOA7okhiTg=", |
||||
"_parent": { |
||||
"$ref": "AAAAAAF5RXOA7okfG2A=" |
||||
}, |
||||
"name": "StatechartDiagram1" |
||||
} |
||||
], |
||||
"regions": [ |
||||
{ |
||||
"_type": "UMLRegion", |
||||
"_id": "AAAAAAF5RXOA7okgaKU=", |
||||
"_parent": { |
||||
"$ref": "AAAAAAF5RXOA7okfG2A=" |
||||
} |
||||
} |
||||
] |
||||
} |
||||
] |
||||
} |
||||
] |
||||
} |
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,276 @@ |
||||
# Add project specific ProGuard rules here. |
||||
# By default, the flags in this file are appended to flags specified |
||||
# in C:\Users\Administrator\AppData\Local\Android\sdk/tools/proguard/proguard-android.txt |
||||
# You can edit the include path and order by changing the proguardFiles |
||||
# directive in build.gradle. |
||||
# |
||||
# For more details, see |
||||
# http://developer.android.com/guide/developing/tools/proguard.html |
||||
|
||||
# Add any project specific keep options here: |
||||
|
||||
# If your project uses WebView with JS, uncomment the following |
||||
# and specify the fully qualified class name to the JavaScript interface |
||||
# class: |
||||
#-keepclassmembers class fqcn.of.javascript.interface.for.webview { |
||||
# public *; |
||||
#} |
||||
-keepclassmembers class * { |
||||
public <init>(org.json.JSONObject); |
||||
} |
||||
-keep public class cn.liuyanbing.surveyor.R$*{ |
||||
public static final int *; |
||||
} |
||||
-keepclassmembers enum * { |
||||
public static **[] values(); |
||||
public static ** valueOf(java.lang.String); |
||||
} |
||||
#混淆前后的映射 |
||||
-printmapping mapping.txt |
||||
|
||||
-keep class androidx.appcompat.widget.SearchView { *; } |
||||
-keep class cn.aigestudio.datepicker.**{*;} |
||||
|
||||
-dontwarn javax.** |
||||
|
||||
-keep class com.tencent.mm.sdk.** { |
||||
*; |
||||
} |
||||
|
||||
-dontwarn com.tencent.** |
||||
-keep class com.tencent.** {*;} |
||||
|
||||
-ignorewarnings |
||||
|
||||
# Apache POI |
||||
-dontwarn org.apache.** |
||||
-dontwarn org.openxmlformats.schemas.** |
||||
-dontwarn org.etsi.** |
||||
-dontwarn org.w3.** |
||||
-dontwarn com.microsoft.schemas.** |
||||
-dontwarn com.fasterxml.** |
||||
-dontwarn javax.naming.** |
||||
-dontwarn java.lang.management.** |
||||
-dontwarn org.slf4j.impl.** |
||||
|
||||
-dontnote org.apache.** |
||||
-dontnote org.openxmlformats.schemas.** |
||||
-dontnote org.etsi.** |
||||
-dontnote org.w3.** |
||||
-dontnote com.microsoft.schemas.** |
||||
-dontnote com.fasterxml.** |
||||
-dontnote javax.naming.** |
||||
-dontnote java.lang.management.** |
||||
-dontnote org.slf4j.impl.** |
||||
|
||||
-keeppackagenames org.apache.poi.ss.formula.function |
||||
|
||||
-keep class org.apache.** {*;} |
||||
-keep class org.openxmlformats.** {*;} |
||||
-keep class org.etsi.** {*;} |
||||
-keep class org.w3.** {*;} |
||||
-keep class com.microsoft.** {*;} |
||||
-keep class com.fasterxml.** {*;} |
||||
-keep class schemaorg_apache_xmlbeans.** {*;} |
||||
|
||||
# ------------------------ leancloud sdk ------------------------ |
||||
-keepattributes Signature |
||||
-dontwarn com.jcraft.jzlib.** |
||||
-keep class com.jcraft.jzlib.** { *;} |
||||
|
||||
-dontwarn sun.misc.** |
||||
-keep class sun.misc.** { *;} |
||||
|
||||
-dontwarn alibaba.fastjson.** |
||||
-dontnote alibaba.fastjson.** |
||||
-keep class alibaba.fastjson.** { *;} |
||||
|
||||
-dontwarn sun.security.** |
||||
-keep class sun.security.** { *; } |
||||
|
||||
-dontwarn com.google.** |
||||
-keep class com.google.** { *;} |
||||
|
||||
-dontwarn com.avos.** |
||||
-dontnote com.avos.** |
||||
-keep class com.avos.** { *;} |
||||
|
||||
-dontwarn cn.leancloud.** |
||||
-dontnote cn.leancloud.** |
||||
-keep class cn.leancloud.** { *;} |
||||
|
||||
-keep public class android.net.http.SslError |
||||
-keep public class android.webkit.WebViewClient |
||||
|
||||
-dontwarn android.webkit.WebView |
||||
-dontwarn android.net.http.SslError |
||||
-dontwarn android.webkit.WebViewClient |
||||
-dontnote android.net.http.** |
||||
|
||||
-dontwarn android.support.** |
||||
|
||||
-dontwarn org.jivesoftware.smack.** |
||||
-keep class org.jivesoftware.smack.** { *;} |
||||
|
||||
-dontwarn com.loopj.** |
||||
-keep class com.loopj.** { *;} |
||||
|
||||
-dontwarn com.squareup.okhttp.** |
||||
-keep class com.squareup.okhttp.** { *;} |
||||
-keep interface com.squareup.okhttp.** { *; } |
||||
|
||||
# keep okhttp3、okio |
||||
-dontwarn okhttp3.** |
||||
-keep class okhttp3.** { *;} |
||||
-keep interface okhttp3.** { *; } |
||||
-dontwarn okio.** |
||||
|
||||
-keep class com.google.protobuf.** { *; } |
||||
-keep public class * extends com.google.protobuf.** { *; } |
||||
-dontwarn com.google.protobuf.** |
||||
|
||||
-dontwarn org.xbill.** |
||||
-keep class org.xbill.** { *;} |
||||
|
||||
-keepattributes *Annotation* |
||||
|
||||
|
||||
# ------------------------ ChatKit ------------------------ |
||||
-dontwarn cn.leancloud.chatkit.** |
||||
-keep class cn.leancloud.chatkit.** { *;} |
||||
-dontnote cn.leancloud.chatkit.** |
||||
|
||||
# ------------------------ picasso ------------------------ |
||||
-dontwarn com.squareup.picasso** |
||||
-keep class com.squareup.picasso.**{*;} |
||||
|
||||
# ------------------------ eventbus ------------------------ |
||||
-keepattributes *Annotation* |
||||
-keepclassmembers class * { |
||||
@org.greenrobot.eventbus.Subscribe <methods>; |
||||
} |
||||
-keep enum org.greenrobot.eventbus.ThreadMode { *; } |
||||
|
||||
# Only required if you use AsyncExecutor |
||||
-keepclassmembers class * extends org.greenrobot.eventbus.util.ThrowableFailureEvent { |
||||
<init>(java.lang.Throwable); |
||||
} |
||||
#--------------------------工具集----------------------------- |
||||
-keep class blankj.utilcode.** { *; } |
||||
-keepclassmembers class blankj.utilcode.** { *; } |
||||
-dontwarn blankj.utilcode.** |
||||
|
||||
-keep class com.chad.library.adapter.** { |
||||
*; |
||||
} |
||||
-keep public class * extends com.chad.library.adapter.base.BaseQuickAdapter |
||||
-keep public class * extends com.chad.library.adapter.base.BaseViewHolder |
||||
-keepclassmembers class **$** extends com.chad.library.adapter.base.BaseViewHolder { |
||||
<init>(...); |
||||
} |
||||
|
||||
# glide 的混淆代码 |
||||
-keep public class * implements com.bumptech.glide.module.GlideModule |
||||
-keep public enum com.bumptech.glide.load.resource.bitmap.ImageHeaderParser$** { |
||||
**[] $VALUES; |
||||
public *; |
||||
} |
||||
# banner 的混淆代码 |
||||
-keep class com.youth.banner.** { |
||||
*; |
||||
} |
||||
# 华测sdk |
||||
-keep class com.chc.gnss.sdk.** { *; } |
||||
-dontwarn com.chc.gnss.sdk.** |
||||
# 中国移动sdk |
||||
-keep class com.cmcc.sy.hap.** { *; } |
||||
-dontwarn com.cmcc.sy.hap.** |
||||
# 梦想CAD sdk |
||||
-keep class org.cocos2dx.** { *; } |
||||
-dontwarn org.cocos2dx.** |
||||
-keep class com.chukong.cocosplay.client.** { *; } |
||||
-dontwarn com.chukong.cocosplay.client.** |
||||
-keep class com.MxDraw.** { *; } |
||||
-dontwarn com.MxDraw.** |
||||
#agentweb |
||||
-keep class com.just.agentweb.** { |
||||
*; |
||||
} |
||||
-dontwarn com.just.agentweb.** |
||||
|
||||
#androidx |
||||
-keep class com.google.android.material.** {*;} |
||||
-keep class androidx.** {*;} |
||||
-keep public class * extends androidx.** |
||||
-keep interface androidx.** {*;} |
||||
-dontwarn com.google.android.material.** |
||||
-dontnote com.google.android.material.** |
||||
-dontwarn androidx.** |
||||
|
||||
# 南方坐标转换 |
||||
-keep class com.qxwz.sdk.** { *; } |
||||
-dontwarn com.qxwz.sdk.** |
||||
|
||||
-keep class com.bingce.device.rtk.configuration.** { *; } |
||||
-keep class com.bingce.device.rtk.model.** { *; } |
||||
-keep class com.bingce.totalstation.TsConfig { *; } |
||||
|
||||
#OkSocket |
||||
-dontwarn xuhao.didi.socket.client.** |
||||
-dontwarn xuhao.didi.socket.common.** |
||||
-dontwarn xuhao.didi.socket.server.** |
||||
-dontwarn xuhao.didi.core.** |
||||
|
||||
-keep class xuhao.didi.socket.client.** { *; } |
||||
-keep class xuhao.didi.socket.common.** { *; } |
||||
-keep class xuhao.didi.socket.server.** { *; } |
||||
-keep class xuhao.didi.core.** { *; } |
||||
|
||||
-keep class xuhao.didi.socket.client.sdk.client.OkSocketOptions$* { |
||||
*; |
||||
} |
||||
-keep class xuhao.didi.socket.server.impl.OkServerOptions$* { |
||||
*; |
||||
} |
||||
|
||||
#gsyvideoplayer |
||||
-keep class com.shuyu.gsyvideoplayer.video.** { *; } |
||||
-dontwarn com.shuyu.gsyvideoplayer.video.** |
||||
-keep class com.shuyu.gsyvideoplayer.video.base.** { *; } |
||||
-dontwarn com.shuyu.gsyvideoplayer.video.base.** |
||||
-keep class com.shuyu.gsyvideoplayer.utils.** { *; } |
||||
-dontwarn com.shuyu.gsyvideoplayer.utils.** |
||||
-keep class tv.danmaku.ijk.** { *; } |
||||
-dontwarn tv.danmaku.ijk.** |
||||
|
||||
-keep public class * extends android.view.View{ |
||||
*** get*(); |
||||
void set*(***); |
||||
public <init>(android.content.Context); |
||||
public <init>(android.content.Context, android.util.AttributeSet); |
||||
public <init>(android.content.Context, android.util.AttributeSet, int); |
||||
} |
||||
|
||||
# # keep rx |
||||
# -dontwarn sun.misc.** |
||||
# -keepclassmembers class rx.internal.util.unsafe.*ArrayQueue*Field* { |
||||
# long producerIndex; |
||||
# long consumerIndex; |
||||
# } |
||||
# -keepclassmembers class rx.internal.util.unsafe.BaseLinkedQueueProducerNodeRef { |
||||
# rx.internal.util.atomic.LinkedQueueNode producerNode; |
||||
# } |
||||
# -keepclassmembers class rx.internal.util.unsafe.BaseLinkedQueueConsumerNodeRef { |
||||
# rx.internal.util.atomic.LinkedQueueNode consumerNode; |
||||
# } |
||||
# |
||||
# -keep class cn.liuyanbing.surveyor.model.base.SerializableStringArray { *; } |
||||
|
||||
-dontwarn com.yalantis.ucrop** |
||||
-keep class com.yalantis.ucrop** { *; } |
||||
-keep interface com.yalantis.ucrop** { *; } |
||||
|
||||
-keep class com.bingce.event.WxLoginSuccessEvent{ *; } |
||||
|
||||
# 友盟 |
||||
-keep class com.umeng.** {*;} |
@ -0,0 +1,19 @@ |
||||
package cn.liuyanbing.surveyor.activity; |
||||
|
||||
import android.util.Log; |
||||
|
||||
import org.junit.Test; |
||||
|
||||
public class MainActivityTest { |
||||
|
||||
@Test |
||||
public void initSound() { |
||||
Log.d("hwhw", "initSound"); |
||||
} |
||||
|
||||
@Test |
||||
public void onCreate() { |
||||
Log.d("hwhw", "onCreate"); |
||||
|
||||
} |
||||
} |
@ -0,0 +1,49 @@ |
||||
import android.util.Log |
||||
import com.bingce.controlnetwork.http.RetrofitClient |
||||
import com.bingce.controlnetwork.http.sevice.CommonService |
||||
import kotlinx.coroutines.delay |
||||
import kotlinx.coroutines.launch |
||||
import kotlinx.coroutines.runBlocking |
||||
import org.junit.Test |
||||
|
||||
class HelloKotlin { |
||||
|
||||
@Test |
||||
fun test() { |
||||
// runBlocking { |
||||
// |
||||
// launch { |
||||
// Log.d("hwhw", "请求1") |
||||
// |
||||
// delay(1000) |
||||
// Log.d("hwhw", "请求1 delay") |
||||
// |
||||
// val apiCall = RetrofitClient.apiCall { |
||||
// RetrofitClient.createService<CommonService>().getPassageData() |
||||
// } |
||||
// |
||||
// apiCall?.let { |
||||
// Log.d("hwhw", "请求成功1,$it") |
||||
// } |
||||
// } |
||||
// |
||||
// launch { |
||||
// Log.d("hwhw", "请求2") |
||||
// |
||||
// delay(1000) |
||||
// Log.d("hwhw", "请求2 delay") |
||||
// |
||||
// val apiCall1 = RetrofitClient.apiCall { |
||||
// RetrofitClient.createService<CommonService>().getPassageData() |
||||
// } |
||||
// apiCall1?.let { |
||||
// Log.d("hwhw", "请求成功2,$it") |
||||
// } |
||||
// } |
||||
// |
||||
// |
||||
// } |
||||
} |
||||
|
||||
|
||||
} |
@ -0,0 +1,217 @@ |
||||
<?xml version="1.0" encoding="utf-8"?> |
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android" |
||||
xmlns:tools="http://schemas.android.com/tools"> |
||||
|
||||
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" /> |
||||
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> |
||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> |
||||
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" /> |
||||
<uses-permission android:name="android.permission.CALL_PHONE" /> |
||||
<uses-permission android:name="android.permission.CAMERA" /> |
||||
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE" /> |
||||
<uses-permission android:name="android.permission.FLASHLIGHT" /> |
||||
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" /> |
||||
<uses-permission android:name="android.permission.GET_TASKS" /> |
||||
<uses-permission android:name="android.permission.INTERNET" /> |
||||
<uses-permission android:name="android.permission.READ_PHONE_STATE" /> |
||||
<uses-permission android:name="android.permission.RECORD_AUDIO" /> |
||||
<uses-permission android:name="android.permission.VIBRATE" /> |
||||
<uses-permission android:name="android.permission.WAKE_LOCK" /> |
||||
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" /> |
||||
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> |
||||
<uses-permission |
||||
android:name="android.permission.MANAGE_EXTERNAL_STORAGE" |
||||
tools:ignore="ScopedStorage" /> |
||||
<uses-permission android:name="android.permission.BLUETOOTH" /> <!-- 蓝牙 --> |
||||
<uses-permission android:name="android.permission.BLUETOOTH_CONNECT" /> |
||||
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN" /> |
||||
<uses-permission |
||||
android:name="android.permission.BLUETOOTH_SCAN" |
||||
android:usesPermissionFlags="neverForLocation" /> |
||||
<uses-permission android:name="android.permission.BLUETOOTH_ADVERTISE" /> |
||||
|
||||
<application |
||||
android:name="com.bingce.controlnetwork.App" |
||||
android:allowBackup="false" |
||||
android:extractNativeLibs="true" |
||||
android:icon="@drawable/icon" |
||||
android:label="@string/app_name" |
||||
android:networkSecurityConfig="@xml/network_security_config" |
||||
android:requestLegacyExternalStorage="true" |
||||
android:theme="@style/CustomThemeLight" |
||||
tools:replace="android:label,android:allowBackup"> |
||||
<!-- the following MUST be in application, not activity --> |
||||
<uses-library |
||||
android:name="org.apache.http.legacy" |
||||
android:required="false" /> |
||||
|
||||
<activity |
||||
android:name=".activity.MainActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/app_name" |
||||
android:windowSoftInputMode="adjustResize|stateHidden"> |
||||
|
||||
</activity> |
||||
<activity |
||||
android:name="com.bingce.controlnetwork.wxapi.WXEntryActivity" |
||||
android:exported="true" |
||||
android:launchMode="singleTop" /> |
||||
<activity |
||||
android:name="com.bingce.controlnetwork.wxapi.WXPayEntryActivity" |
||||
android:exported="true" |
||||
android:launchMode="singleTop" /> |
||||
|
||||
<service android:name="cn.leancloud.push.PushService" /> <!-- 即时通讯和推送都需要 PushService --> |
||||
<activity |
||||
android:name=".activity.SettingsActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/settings" /> |
||||
<activity |
||||
android:name=".activity.user.RegisterActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/inactivated" /> |
||||
<activity |
||||
android:name=".activity.user.OpeningRenewalVipActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/opening_renewal" /> |
||||
<activity |
||||
android:name=".activity.ChangelogActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/changelog" /> |
||||
<activity |
||||
android:name=".activity.NotificationActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/notification" /> |
||||
<activity |
||||
android:name=".activity.AboutActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/about" /> |
||||
<activity |
||||
android:name="com.bingce.surveyor.agentweb.AgentWebActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:hardwareAccelerated="true" |
||||
android:windowSoftInputMode="adjustUnspecified|stateHidden" /> |
||||
<activity |
||||
android:name=".activity.user.UserInfoActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/user_info" |
||||
android:windowSoftInputMode="adjustPan|stateHidden" /> |
||||
<activity |
||||
android:name=".activity.user.RedeemVipActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/redeem" |
||||
android:windowSoftInputMode="adjustPan|stateHidden" /> |
||||
<activity |
||||
android:name=".activity.fragmentcontainer.FragmentContainerActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:windowSoftInputMode="adjustUnspecified|stateHidden" /> |
||||
<activity |
||||
android:name=".activity.LogCollectActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/log_collect_activity" /> |
||||
<activity |
||||
android:name="com.yalantis.ucrop.UCropActivity" |
||||
android:exported="true" |
||||
android:screenOrientation="portrait" |
||||
android:theme="@style/Theme.AppCompat.Light.NoActionBar" /> |
||||
<activity |
||||
android:name=".activity.backup.BackupExportActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/backup" /> |
||||
<activity |
||||
android:name=".activity.backup.launch.MigrationFolder2PrivateRoomActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name="ru.bartwell.exfilepicker.ui.activity.ExFilePickerActivity" |
||||
android:exported="true" |
||||
android:theme="@style/ExFilePickerThemeCustom" /> |
||||
<activity |
||||
android:name=".activity.SplashActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true"> |
||||
<intent-filter> |
||||
<action android:name="android.intent.action.MAIN" /> |
||||
|
||||
<category android:name="android.intent.category.LAUNCHER" /> |
||||
</intent-filter> |
||||
|
||||
<meta-data |
||||
android:name="android.app.shortcuts" |
||||
android:resource="@xml/shortcuts" /> |
||||
</activity> |
||||
|
||||
<activity |
||||
android:name=".activity.user.EditNicknamePasswordActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".activity.user.LoginActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" |
||||
android:label="@string/log_in" /> |
||||
<activity |
||||
android:name=".activity.user.VerifyEmailCodeActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".activity.user.VerifySMSCodeActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".activity.user.InputPhoneNumberActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".activity.user.InputEmailActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".newui.createeditpoint.CreateEditPointActvity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".newui.stationsetting.StationSettingsActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".newui.projectedit.ProjectCreateEditActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".func.level.activity.LevelStationSettingActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:exported="true" /> |
||||
<activity |
||||
android:name=".func.level.idetection.LevelIDetectionRecordActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:label="i角检测" /> |
||||
<activity |
||||
android:name=".func.level.idetection.LevelIDetectionListActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:label="i角检测" /> |
||||
<activity |
||||
android:name=".func.level.idetection.LevelIDetectionSampleActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:label="i角检测" /> |
||||
<activity |
||||
android:name=".func.level.idetection.LevelIDetectionStationSettingActivity" |
||||
android:configChanges="orientation|keyboardHidden|screenSize" |
||||
android:label="i角检测" /> |
||||
|
||||
</application> |
||||
|
||||
</manifest> |
@ -0,0 +1 @@ |
||||
#controlnetwork |
Binary file not shown.
Binary file not shown.
@ -0,0 +1,8 @@ |
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<summary> |
||||
欢迎使用导线助手App!我们将通过《用户协议》和《隐私政策》帮助您了解我们收集、使用、存储和共享个人信息的情况,以及您所享有的相关权利。 |
||||
• 为了向您提供语音播报、文件生成存储、头像上传、用户注册等功能服务,我们需要使用您的一些存储权限、音视频录制权限、相机权限、获取设备信息等权限及信息。 |
||||
• 我们会采用业界领先的安全技术保护好您的个人信息。 |
||||
您可以通过阅读完整版用户隐私政策,了解个人信息类型与用途的对应关系等更加详尽的个人信息处理规则。 |
||||
如您同意,请点击“同意”开始接受我们的服务。 |
||||
</summary> |
@ -0,0 +1,4 @@ |
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<summary> |
||||
Welcome to the Surveyor App! Through the "User Agreement" and "Privacy Policy", we will help you understand our collection, use, storage and sharing of personal information, as well as your related rights. • In order to provide you with voice broadcasting, file generation and storage, avatar upload, user registration and other functional services, we need to use some of your storage permissions, audio and video recording permissions, camera permissions, access to device information and other permissions and information. • We will protect your personal information with industry-leading security technology. You can read the full version of the user's privacy policy to understand the more detailed personal information processing rules such as the correspondence between personal information types and uses. If you agree, please click "Agree" to start accepting our services. |
||||
</summary> |
@ -0,0 +1,868 @@ |
||||
[{ |
||||
"name": "城市轨道交通", |
||||
"level": [{ |
||||
"name": "城市轨道交通精密导线", |
||||
"precision": [{ |
||||
"name": "I级", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "3", |
||||
"singleCycleDistanceDifference": "3", |
||||
"allCycleDistanceDifference": "4", |
||||
"cycleCount": "4" |
||||
}, { |
||||
"name": "II级", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "4", |
||||
"singleCycleDistanceDifference": "4", |
||||
"allCycleDistanceDifference": "6", |
||||
"cycleCount": "6" |
||||
}] |
||||
}] |
||||
}, { |
||||
"name": "铁路工程测量", |
||||
"level": [{ |
||||
"name": "铁路工程测量二等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "4", |
||||
"horCycleDirect2CDifference": "6", |
||||
"horCyclesDirectValueDifference": "4", |
||||
"hor2C": "6", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "2", |
||||
"singleCycleDistanceDifference": "2", |
||||
"allCycleDistanceDifference": "3", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "6", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "铁路工程测量三等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "4", |
||||
"horCycleDirect2CDifference": "6", |
||||
"horCyclesDirectValueDifference": "4", |
||||
"hor2C": "6", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "2", |
||||
"singleCycleDistanceDifference": "2", |
||||
"allCycleDistanceDifference": "3", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "2", |
||||
"singleCycleDistanceDifference": "2", |
||||
"allCycleDistanceDifference": "3", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "铁路工程测量四等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "4", |
||||
"horCycleDirect2CDifference": "*", |
||||
"horCyclesDirectValueDifference": "4", |
||||
"hor2C": "6", |
||||
"horCyclesDirect2CDifference": "6", |
||||
"distanceReadDifference": "2", |
||||
"singleCycleDistanceDifference": "2", |
||||
"allCycleDistanceDifference": "3", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "3" |
||||
}] |
||||
}, { |
||||
"name": "铁路工程测量一级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "2", |
||||
"singleCycleDistanceDifference": "2", |
||||
"allCycleDistanceDifference": "?", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "?", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "3" |
||||
}] |
||||
}, { |
||||
"name": "铁路工程测量二级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "2", |
||||
"singleCycleDistanceDifference": "2", |
||||
"allCycleDistanceDifference": "?", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "?", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "*", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "*", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "20", |
||||
"singleCycleDistanceDifference": "20", |
||||
"allCycleDistanceDifference": "30", |
||||
"cycleCount": "3" |
||||
}] |
||||
}] |
||||
}, { |
||||
"name": "水利水电工程测量", |
||||
"level": [{ |
||||
"name": "水利水电工程测量二等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "2", |
||||
"horHalfReturnZeroDifference": "4", |
||||
"horCycleDirect2CDifference": "6", |
||||
"horCyclesDirectValueDifference": "3", |
||||
"hor2C": "6", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "4", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "6", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}] |
||||
}, { |
||||
"name": "水利水电工程测量三等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "2", |
||||
"horHalfReturnZeroDifference": "4", |
||||
"horCycleDirect2CDifference": "6", |
||||
"horCyclesDirectValueDifference": "3", |
||||
"hor2C": "6", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "4", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "6", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}] |
||||
}, { |
||||
"name": "水利水电工程测量四等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "2", |
||||
"horHalfReturnZeroDifference": "4", |
||||
"horCycleDirect2CDifference": "6", |
||||
"horCyclesDirectValueDifference": "3", |
||||
"hor2C": "6", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "4", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "6", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}] |
||||
}, { |
||||
"name": "水利水电工程测量五等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "4", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "3" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "4", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "6", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "12", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "24", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "24", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}] |
||||
}, { |
||||
"name": "工程测量", |
||||
"level": [{ |
||||
"name": "工程测量三等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "工程测量四等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "工程测量一级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "12", |
||||
"horCycleDirect2CDifference": "18", |
||||
"horCyclesDirectValueDifference": "12", |
||||
"hor2C": "18", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "*", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "*", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "工程测量二级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "24", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "24", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "工程测量三级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "24", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "24", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "10", |
||||
"singleCycleDistanceDifference": "10", |
||||
"allCycleDistanceDifference": "15", |
||||
"cycleCount": "2" |
||||
}] |
||||
}] |
||||
}, { |
||||
"name": "城市测量", |
||||
"level": [{ |
||||
"name": "城市测量三等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "城市测量四等导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "6", |
||||
"horCycleDirect2CDifference": "9", |
||||
"horCyclesDirectValueDifference": "6", |
||||
"hor2C": "9", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "城市测量一级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "*", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "*", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "城市测量二级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "*", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "*", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}, { |
||||
"name": "城市测量三级导线", |
||||
"precision": [{ |
||||
"name": "0.5秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "1秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "2秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "8", |
||||
"horCycleDirect2CDifference": "13", |
||||
"horCyclesDirectValueDifference": "9", |
||||
"hor2C": "13", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}, { |
||||
"name": "6秒", |
||||
"horReadDifference": "3", |
||||
"horHalfReturnZeroDifference": "18", |
||||
"horCycleDirect2CDifference": "*", |
||||
"horCyclesDirectValueDifference": "24", |
||||
"hor2C": "*", |
||||
"horCyclesDirect2CDifference": "*", |
||||
"distanceReadDifference": "5", |
||||
"singleCycleDistanceDifference": "5", |
||||
"allCycleDistanceDifference": "7", |
||||
"cycleCount": "2" |
||||
}] |
||||
}] |
||||
}] |
@ -0,0 +1,574 @@ |
||||
[Group][Radio] |
||||
[Model][Valid] |
||||
Baudrate:1:4800,9600,19200:1,0,2 |
||||
Power:10:1,2,5,10,20:2,6,3,4,5 |
||||
Stepper:10:125,250:0,2 |
||||
[Model][RadioChannels] |
||||
High:456.05,456.55,457.05,458.05,459.05,460.05,461.05,462.05,462.55 |
||||
Middle:430.00,432.50,435.00,437.50,440.00,442.50,445.00,447.50,450.00 |
||||
Low:415.05,416.05,417.05,418.05,419.05,420.05,421.05,422.05,423.05 |
||||
[Model][Advanced For Satel] |
||||
Step-Protocol-Baudrate:125-8-9600 |
||||
Step-Protocol-Baudrate:125-16-9600 |
||||
Step-Protocol-Baudrate:125-2-4800 |
||||
Step-Protocol-Baudrate:125-4-4800 |
||||
Step-Protocol-Baudrate:250-8-19200 |
||||
Step-Protocol-Baudrate:250-16-19200 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
[Model][Advanced For HuaXin] |
||||
Step-Protocol-Baudrate:250-1-9600 |
||||
Step-Protocol-Baudrate:250-1-19200 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
[Model][Advanced For HuaXin-EX] |
||||
Step-Protocol-Baudrate:125-1-4800 |
||||
Step-Protocol-Baudrate:125-2-4800 |
||||
Step-Protocol-Baudrate:125-4-4800 |
||||
Step-Protocol-Baudrate:250-1-9600 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-1-19200 |
||||
[Model][Advanced For HuaXin-EX2] |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-256-9600 |
||||
Step-Protocol-Baudrate:250-512-9600 |
||||
Step-Protocol-Baudrate:250-256-19200 |
||||
Step-Protocol-Baudrate:250-512-19200 |
||||
[Model][Advanced For HuaXin-SOUTH] |
||||
Step-Protocol-Baudrate:125-1-4800 |
||||
Step-Protocol-Baudrate:125-2-4800 |
||||
Step-Protocol-Baudrate:125-4-4800 |
||||
Step-Protocol-Baudrate:125-256-4800 |
||||
Step-Protocol-Baudrate:250-1-9600 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-256-9600 |
||||
Step-Protocol-Baudrate:250-1-19200 |
||||
Step-Protocol-Baudrate:250-256-19200 |
||||
[Model][Advanced For D352] |
||||
Step-Protocol-Baudrate:125-1-9600 |
||||
Step-Protocol-Baudrate:125-2-9600 |
||||
Step-Protocol-Baudrate:125-4-9600 |
||||
Step-Protocol-Baudrate:125-1-19200 |
||||
Step-Protocol-Baudrate:125-2-19200 |
||||
Step-Protocol-Baudrate:125-4-19200 |
||||
Step-Protocol-Baudrate:200-1-9600 |
||||
Step-Protocol-Baudrate:200-2-9600 |
||||
Step-Protocol-Baudrate:200-4-9600 |
||||
Step-Protocol-Baudrate:200-1-19200 |
||||
Step-Protocol-Baudrate:200-2-19200 |
||||
Step-Protocol-Baudrate:200-4-19200 |
||||
Step-Protocol-Baudrate:250-1-9600 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-1-19200 |
||||
Step-Protocol-Baudrate:250-2-19200 |
||||
Step-Protocol-Baudrate:250-4-19200 |
||||
[Model][Advanced For D352_CHCX] |
||||
Step-Protocol-Baudrate:125-1-9600 |
||||
Step-Protocol-Baudrate:125-2-9600 |
||||
Step-Protocol-Baudrate:125-4-9600 |
||||
Step-Protocol-Baudrate:125-2-19200 |
||||
Step-Protocol-Baudrate:125-4-19200 |
||||
Step-Protocol-Baudrate:125-4096-19200 |
||||
Step-Protocol-Baudrate:200-1-9600 |
||||
Step-Protocol-Baudrate:200-2-9600 |
||||
Step-Protocol-Baudrate:200-4-9600 |
||||
Step-Protocol-Baudrate:200-2-19200 |
||||
Step-Protocol-Baudrate:200-4-19200 |
||||
Step-Protocol-Baudrate:200-4096-19200 |
||||
Step-Protocol-Baudrate:250-1-9600 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-2-19200 |
||||
Step-Protocol-Baudrate:250-4-19200 |
||||
Step-Protocol-Baudrate:250-4096-19200 |
||||
[Model][Advanced For HuaXin-SOUTH_CHCX] |
||||
Step-Protocol-Baudrate:125-1-4800 |
||||
Step-Protocol-Baudrate:125-2-4800 |
||||
Step-Protocol-Baudrate:125-4-4800 |
||||
Step-Protocol-Baudrate:125-256-4800 |
||||
Step-Protocol-Baudrate:250-1-9600 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-256-9600 |
||||
Step-Protocol-Baudrate:250-256-19200 |
||||
Step-Protocol-Baudrate:250-4096-19200 |
||||
[Model][Advanced For HuaXin_SOUTH_ZHD_CHCX] |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-256-9600 |
||||
Step-Protocol-Baudrate:250-512-9600 |
||||
Step-Protocol-Baudrate:250-256-19200 |
||||
Step-Protocol-Baudrate:250-512-19200 |
||||
Step-Protocol-Baudrate:250-4096-19200 |
||||
[Model][Advanced For HuaXin_SOUTH_ZHD] |
||||
Step-Protocol-Baudrate:250-1-9600 |
||||
Step-Protocol-Baudrate:250-2-9600 |
||||
Step-Protocol-Baudrate:250-4-9600 |
||||
Step-Protocol-Baudrate:250-256-9600 |
||||
Step-Protocol-Baudrate:250-512-9600 |
||||
Step-Protocol-Baudrate:250-1-19200 |
||||
Step-Protocol-Baudrate:250-256-19200 |
||||
Step-Protocol-Baudrate:250-512-19200 |
||||
[Model][Features] |
||||
Size:19 |
||||
ID:1:RX |
||||
Range:450,470 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125 |
||||
Protocol:1,2,4 |
||||
Power:NONE |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:0,0 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:0,0 |
||||
CallSign:0,0 |
||||
ID:2:RXTX |
||||
Range:450,470 |
||||
Baudrate:9600 |
||||
Stepper:125 |
||||
Protocol:1,2,4,128 |
||||
Power:1,5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:0,0 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:0,0 |
||||
CallSign:0,0 |
||||
ID:3:Satel |
||||
Range:403,473 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:2,4,8,16 |
||||
Power:1,5,10 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:0,0 |
||||
Power:1,1 |
||||
Sensitivity:1,1 |
||||
FEC:1,1 |
||||
Stepper:1,1 |
||||
CallSign:1,1 |
||||
ID:4:LFS |
||||
Range:455,463 |
||||
Baudrate:9600 |
||||
Stepper:250 |
||||
Protocol:1 |
||||
Power:1,5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:0,0 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:0,0 |
||||
CallSign:0,0 |
||||
ID:5:RXTX-MOREBAUDS |
||||
Range:450,470 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125 |
||||
Protocol:1,2,4 |
||||
Power:1,5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:0,0 |
||||
CallSign:0,0 |
||||
ID:6:LFS-MOREBAUDS |
||||
Range:455,463 |
||||
Baudrate:9600,19200 |
||||
Stepper:250 |
||||
Protocol:1 |
||||
Power:1,5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:0,0 |
||||
CallSign:0,0 |
||||
ID:7:LFS-Low |
||||
Range:412,422 |
||||
Baudrate:9600 |
||||
Stepper:250 |
||||
Protocol:1 |
||||
Power:1,5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:0,0 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:0,0 |
||||
CallSign:0,0 |
||||
ID:8:Satel-I80 |
||||
Range:403,473 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:2,4,8,16 |
||||
Power:1,2,5,10 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,0 |
||||
Power:1,1 |
||||
Sensitivity:1,1 |
||||
FEC:1,1 |
||||
Stepper:1,1 |
||||
CallSign:1,1 |
||||
ID:9:HX |
||||
Range:410,470 |
||||
Baudrate:9600,19200 |
||||
Stepper:250 |
||||
Protocol:1,2,4 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:0,0 |
||||
CallSign:0,0 |
||||
ID:10:HX-EX |
||||
Range:410,470 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:1,2,4 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:11:Satel-TR8 |
||||
Range:865,867 |
||||
Baudrate:19200 |
||||
Stepper:250 |
||||
Protocol:8 |
||||
Power:1,5,10 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:1,1 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:12:HX-EX2 |
||||
Range:410,470 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:2,4,256,512 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:13:D352 |
||||
Range:410,470 |
||||
Baudrate:9600,19200 |
||||
Stepper:125,200,250 |
||||
Protocol:1,2,4 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:14:HX_SOUTH |
||||
Range:410,470 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:1,2,4,256 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:15:HX_865 |
||||
Range:1,8 |
||||
Baudrate:19200 |
||||
Stepper:125 |
||||
Protocol:1 |
||||
Power:5,10 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:16:D352_CHCX |
||||
Range:410,470 |
||||
Baudrate:9600,19200 |
||||
Stepper:125,200,250 |
||||
Protocol:1,2,4,4096 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:17:HX_SOUTH_CHCX |
||||
Range:410,470 |
||||
Baudrate:4800,9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:1,2,4,256,4096 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:18:HX_SOUTH_ZHD_CHCX |
||||
Range:410,470 |
||||
Baudrate:9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:2,4,256,512,4096 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
ID:19:HX_SOUTH_ZHD |
||||
Range:410,470 |
||||
Baudrate:9600,19200 |
||||
Stepper:125,250 |
||||
Protocol:1,2,4,256,512 |
||||
Power:5,10,20 |
||||
[Model][Operations] |
||||
Frequency:1,1 |
||||
Baudrate:1,1 |
||||
Power:1,1 |
||||
Sensitivity:0,0 |
||||
FEC:0,0 |
||||
Stepper:1,1 |
||||
CallSign:0,0 |
||||
[Group][NMEA] |
||||
[Model][Features] |
||||
Size:8 |
||||
ID:1 |
||||
Type:1,2,3,4,5,6,7,8,9,12,13,14,19,20 |
||||
Frequency:3,4,5,6,7,8,9,10,11 |
||||
ID:2 |
||||
Type:1,2,3,4,5,6,7,8,9,10,11,12 |
||||
Frequency:4,5,6,7,8,9,10,11 |
||||
ID:4 |
||||
Type:1,2,3,4,5,6,7,8,9,12,15,16 |
||||
Frequency:5,6,7,8 |
||||
ID:6 |
||||
Type:1,2,3,5,6,7,8,9,10,11 |
||||
Frequency:4,5,6,7,8,9,10,11 |
||||
ID:7 |
||||
Type:1,2,3,4,5,6,7,8,9,12,15,16 |
||||
Frequency:5,6,7,8,9,10,11 |
||||
ID:8 |
||||
Type:1,2,3,4,5,6,7,8,9,12,13,14,17,18,19,20,21,22,23,24,25 |
||||
Frequency:5,6,7,8,9,10 |
||||
ID:12 |
||||
Type:1,2,3,4,5,6,7,8,9,12,19 |
||||
Frequency:8,9,10,11 |
||||
ID:14 |
||||
Type:1,2,3,5,6,7,8,9,10,11 |
||||
Frequency:4,5,6,7,8,9,10,11 |
||||
[Group][Precision] |
||||
[Model][Features] |
||||
Size:5 |
||||
ID:1 |
||||
HP:0.2 |
||||
VP:0.2 |
||||
XP:0.2 |
||||
YP:0.2 |
||||
RMS:0.2 |
||||
Status:11 |
||||
DiffAge:-1 |
||||
ID:2 |
||||
HP:0.6 |
||||
VP:0.6 |
||||
XP:0.6 |
||||
YP:0.6 |
||||
RMS:0.6 |
||||
Status:-1 |
||||
DiffAge:5 |
||||
ID:3 |
||||
HP:0.6 |
||||
VP:0.6 |
||||
XP:0.6 |
||||
YP:0.6 |
||||
RMS:0.6 |
||||
Status:-1 |
||||
DiffAge:5 |
||||
ID:7 |
||||
HP:0.3 |
||||
VP:0.3 |
||||
XP:0.3 |
||||
YP:0.3 |
||||
RMS:0.3 |
||||
Status:11 |
||||
DiffAge:-1 |
||||
ID:8 |
||||
HP:0.2 |
||||
VP:0.2 |
||||
XP:0.2 |
||||
YP:0.2 |
||||
RMS:0.2 |
||||
Status:11 |
||||
DiffAge:-1 |
||||
[Group][EBubbleMatrix] |
||||
[Model][Features] |
||||
Size:4 |
||||
ID:1 |
||||
Type:-2 |
||||
Matrix:0,1,-1,0 |
||||
ID:2 |
||||
Type:-1 |
||||
Matrix:1,0,0,1 |
||||
ID:3 |
||||
Type:0 |
||||
Matrix:-1,0,0,1 |
||||
ID:4 |
||||
Type:1 |
||||
Matrix:-1,0,0,1 |
||||
[Group][StaticSampleFreq] |
||||
[Model][Features] |
||||
Size:4 |
||||
ID:1 |
||||
Type:0 |
||||
FreqList:7,8,9,10,11,12,15,16 |
||||
ID:2 |
||||
Type:1 |
||||
FreqList:4,5,6,7,8,9,10,11,12,15,16 |
||||
ID:3 |
||||
Type:2 |
||||
FreqList:6,8,9,10,11,12,15,16 |
||||
ID:4 |
||||
Type:3 |
||||
FreqList:8,9,10,11 |
||||
[Group][SmartGNSSPN] |
||||
[Model][Features] |
||||
Size:13 |
||||
ID:1 |
||||
Type:1 |
||||
Name:N72 |
||||
CalibrationType:1 |
||||
Main:72 |
||||
Sub:00,01,10 |
||||
ID:2 |
||||
Type:2 |
||||
Name:I80 |
||||
CalibrationType:1 |
||||
Main:80 |
||||
Sub:00,01 |
||||
ID:3 |
||||
Type:3 |
||||
Name:X10 |
||||
CalibrationType:1 |
||||
Main:80 |
||||
Sub:02,03 |
||||
ID:4 |
||||
Type:4 |
||||
Name:T8 |
||||
CalibrationType:1 |
||||
Main:80 |
||||
Sub:06,07 |
||||
ID:5 |
||||
Type:5 |
||||
Name:X9 |
||||
CalibrationType:1 |
||||
Main:80 |
||||
Sub:11,15 |
||||
ID:6 |
||||
Type:6 |
||||
Name:M6 |
||||
CalibrationType:2 |
||||
Main:80 |
||||
Sub:08 |
||||
ID:7 |
||||
Type:7 |
||||
Name:I70 |
||||
CalibrationType:1 |
||||
Main:80 |
||||
Sub:09,10,13 |
||||
ID:8 |
||||
Type:8 |
||||
Name:T7 |
||||
CalibrationType:1 |
||||
Main:80 |
||||
Sub:14 |
||||
ID:9 |
||||
Type:9 |
||||
Name:X360 |
||||
CalibrationType:1 |
||||
Main:36 |
||||
Sub: |
||||
ID:10 |
||||
Type:10 |
||||
Name:NX100 |
||||
CalibrationType:0 |
||||
Main:74 |
||||
Sub:12,24 |
||||
ID:11 |
||||
Type:11 |
||||
Name:NX101 |
||||
CalibrationType:0 |
||||
Main:75 |
||||
Sub: |
||||
ID:12 |
||||
Type:12 |
||||
Name:MC100 |
||||
CalibrationType:0 |
||||
Main:76 |
||||
Sub:00,01 |
||||
ID:13 |
||||
Type:13 |
||||
Name:NX200 |
||||
CalibrationType:0 |
||||
Main:77 |
||||
Sub: |
||||
[Group][SupportGNSSType] |
||||
[Model][SMARTGNSS] |
||||
Type:0 |
||||
MainBoard:0 |
||||
[Model][ARM] |
||||
Type:0 |
||||
MainBoard:0 |
||||
[Model][DIRECT] |
||||
Type:0 |
||||
MainBoard:0 |
After Width: | Height: | Size: 14 KiB |
@ -0,0 +1,45 @@ |
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<content> |
||||
This application respects and protects the personal privacy of all users of the service. In order to provide you with more accurate and personalized services, this application will use and disclose your personal information in accordance with the provisions of this privacy policy. However, this application will treat this information with a high degree of diligence and prudence. Except as otherwise provided in this Privacy Policy, this application will not disclose this information to third parties or provide it to third parties without your prior permission. This app will update this privacy policy from time to time. |
||||
When you agree to this application service use agreement, you are deemed to have agreed to the entire content of this privacy policy. This privacy policy is an integral part of this application service usage agreement. |
||||
|
||||
Scope of application |
||||
(a) when you register for this application account, the personal registration information you provided in accordance with the requirements of this application; |
||||
(b) |
||||
When you use this application web service or visit this application platform web page, this application automatically receives and records information on your browser and computer, including but not limited to your IP address, browser type, language used , Access date and time, software and hardware characteristic information, and web page records such as your requirements; |
||||
(c) User personal data obtained by this application from business partners through legal channels. |
||||
You understand and agree that the following information does not apply to this privacy policy: |
||||
(a) the keyword information you enter when using the search services provided by this application platform; |
||||
(b) relevant information and data collected by this application and released by you in this application, including but not limited to participation activities, transaction information and evaluation details; |
||||
(c) Violations of laws or violations of this application rule and the actions this application has taken against you. |
||||
2. Use of information |
||||
(a) This application will not provide, sell, rent, share or trade your personal information to any unrelated third party, unless you have obtained your permission in advance, or the third party and this application (including this application affiliate) alone or jointly To provide you with a service, and after the service has ended, it will be barred from access to all of this material, including its previous access. |
||||
(b) This application also does not allow any third party to collect, edit, sell or disseminate your personal information by any means. If any user of this application platform engages in the above activities, once found, this application has the right to immediately terminate the service agreement with that user. |
||||
(c) |
||||
For the purpose of serving users, this application may provide you with information that is of interest to you by using your personal information, including but not limited to sending you product and service information, or sharing information with this application partner so that they can send you Information about its products and services (the latter requires your prior consent). |
||||
3. Information disclosure |
||||
Under the following circumstances, this application will disclose your personal information in whole or in part according to your personal wishes or legal requirements: |
||||
(a) disclosure to third parties with your prior consent; |
||||
(b) in order to provide the products and services you have requested, your personal information must be shared with third parties; |
||||
(c) disclosure to third parties or administrative or judicial bodies in accordance with the relevant provisions of the law or the requirements of administrative or judicial bodies; |
||||
(d) if you have violated relevant Chinese laws, regulations or this application service agreement or related rules, you need to disclose it to a third party; |
||||
(e) If you are a qualified intellectual property complainant and have filed a complaint, you should disclose it to the respondent at the request of the respondent so that both parties can deal with possible disputes over rights; |
||||
(f) In a transaction created on the application platform, if any party to the transaction fulfills or partially fulfills the transaction obligations and requests for information disclosure, the application has the right to determine the necessary means to provide the user with the contact method of the counterparty Information to facilitate the completion of a transaction or the resolution of a dispute. |
||||
(g) Other disclosures that this application deems appropriate in accordance with laws, regulations or website policies. |
||||
4. Information storage and exchange |
||||
The information and data collected about you by this application will be stored on the server of this application and / or its affiliates. Such information and data may be transferred to your country, region or outside the country where the information and data are collected by this application and in Accessed, stored and displayed overseas. |
||||
5. Use of cookies |
||||
(a) If you do not refuse to accept cookies, this application will set or access cookies on your computer |
||||
So that you can log in or use the services or features of this application platform that rely on cookies. This application uses cookies to provide you with more thoughtful personalized services, including promotion services. |
||||
(b) |
||||
You have the right to choose to accept or decline cookies. You can refuse to accept cookies by modifying your browser settings. However, if you choose to decline cookies, you may not be able to log in or use the web services or features of this application that rely on cookies. |
||||
(c) The relevant information obtained through the cookies set by this application will apply this policy. |
||||
6. Information security |
||||
(a) |
||||
This application account has security protection functions, please keep your username and password information properly. This application will ensure that your information is not lost, misused and altered by security measures such as encrypting user passwords. Despite the aforementioned security measures, please also note that there are no "perfect security measures" on the information network. |
||||
(b) When using this application network service for online transactions, you must inevitably ask the counterparty or potential transaction pair |
||||
7. Changes to this privacy policy |
||||
(a) if we decide to change our privacy policy, we will post those changes in this policy, on our website, and where we deem appropriate, so that you understand how we collect and use your personal information and who can access it, And under what circumstances we will disclose this information. |
||||
(b) The company reserves the right to modify this policy at any time, so please check it frequently. If major changes are made to this policy, the company will notify through a website notification. |
||||
Party to disclose their personal information, such as contact information or postal address. Please protect your personal information and provide it to others only when necessary. If you find that your personal information has been leaked, especially the user name and password of this application, please contact the customer service of this application immediately so that this application can take corresponding measures. |
||||
</content> |
@ -0,0 +1,51 @@ |
||||
<!DOCTYPE html> |
||||
<html lang="en"> |
||||
<head> |
||||
<meta charset="UTF-8"> |
||||
<meta name="viewport" content="initial-scale=1.0, user-scalable=no"/> |
||||
</head> |
||||
|
||||
<style> |
||||
*{ |
||||
margin: 0; |
||||
padding: 0;} |
||||
#father { |
||||
position: absolute; |
||||
top: 0; |
||||
right: 0; |
||||
width: 100%; |
||||
height: 100%; |
||||
background-color: #fff; |
||||
display: flex; |
||||
justify-content: center; |
||||
align-items: center; |
||||
} |
||||
#son{ |
||||
text-align: center; |
||||
} |
||||
#son>img{ |
||||
color: #eee; |
||||
width: 128px; |
||||
height: 128px; |
||||
vertical-align: middle; |
||||
display:block; |
||||
margin:10px; |
||||
text-align: center; |
||||
} |
||||
#son>div{ |
||||
color: #888; |
||||
} |
||||
|
||||
</style> |
||||
<body> |
||||
<div id="father" onclick="window.android.refresh()"> |
||||
<div id="son"> |
||||
<img src="network_error.png" alt=""> |
||||
<div>点击刷新</div> |
||||
</div> |
||||
</div> |
||||
<script> |
||||
|
||||
</script> |
||||
</body> |
||||
</html> |
@ -0,0 +1,13 @@ |
||||
{ |
||||
"supplier": { |
||||
"vivo": { |
||||
"appid": "100215079" |
||||
}, |
||||
"xiaomi": { |
||||
}, |
||||
"huawei": { |
||||
}, |
||||
"oppo": { |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,93 @@ |
||||
[{ |
||||
"createDate": "Jan 27, 2021 9:37:42 AM", |
||||
"hor2C": 5.0, |
||||
"horCycleDirect2CDifference": 5.0, |
||||
"horCyclesDirect2CDifference": 5.0, |
||||
"horCyclesDirectValueDifference": 5.0, |
||||
"horHalfReturnZeroDifference": 5.0, |
||||
"horReadDifference": 5.0, |
||||
"id": "20210127093742841174", |
||||
"isTemplate": true, |
||||
"name": "限差模板0", |
||||
"singleSurveyor": true, |
||||
"slopeCycleDistanceDifference": 5.0, |
||||
"slopeLensDistanceDifference": 5.0, |
||||
"slopeReadDifference": 5.0, |
||||
"surveyorCycleCount": 2, |
||||
"verCheckWhenAngle3": true, |
||||
"verCycleDirectIDifference": 5.0, |
||||
"verCyclesAngleDifference": 5.0, |
||||
"verCyclesIDifference": 5.0, |
||||
"verIDifference": 5.0, |
||||
"verReadDifference": 5.0 |
||||
}, |
||||
{ |
||||
"createDate": "Jan 27, 2021 9:37:43 AM", |
||||
"hor2C": 5.0, |
||||
"horCycleDirect2CDifference": 5.0, |
||||
"horCyclesDirect2CDifference": 5.0, |
||||
"horCyclesDirectValueDifference": 5.0, |
||||
"horHalfReturnZeroDifference": 5.0, |
||||
"horReadDifference": 5.0, |
||||
"id": "20210127093743841174", |
||||
"isTemplate": true, |
||||
"name": "限差模板1", |
||||
"singleSurveyor": true, |
||||
"slopeCycleDistanceDifference": 5.0, |
||||
"slopeLensDistanceDifference": 5.0, |
||||
"slopeReadDifference": 5.0, |
||||
"surveyorCycleCount": 2, |
||||
"verCheckWhenAngle3": true, |
||||
"verCycleDirectIDifference": 5.0, |
||||
"verCyclesAngleDifference": 5.0, |
||||
"verCyclesIDifference": 5.0, |
||||
"verIDifference": 5.0, |
||||
"verReadDifference": 5.0 |
||||
}, |
||||
{ |
||||
"createDate": "Jan 27, 2021 9:37:44 AM", |
||||
"hor2C": 5.0, |
||||
"horCycleDirect2CDifference": 5.0, |
||||
"horCyclesDirect2CDifference": 5.0, |
||||
"horCyclesDirectValueDifference": 5.0, |
||||
"horHalfReturnZeroDifference": 5.0, |
||||
"horReadDifference": 5.0, |
||||
"id": "20210127093744841174", |
||||
"isTemplate": true, |
||||
"name": "限差模板2", |
||||
"singleSurveyor": true, |
||||
"slopeCycleDistanceDifference": 5.0, |
||||
"slopeLensDistanceDifference": 5.0, |
||||
"slopeReadDifference": 5.0, |
||||
"surveyorCycleCount": 2, |
||||
"verCheckWhenAngle3": true, |
||||
"verCycleDirectIDifference": 5.0, |
||||
"verCyclesAngleDifference": 5.0, |
||||
"verCyclesIDifference": 5.0, |
||||
"verIDifference": 5.0, |
||||
"verReadDifference": 5.0 |
||||
}, |
||||
{ |
||||
"createDate": "Jan 27, 2021 9:37:45 AM", |
||||
"hor2C": 5.0, |
||||
"horCycleDirect2CDifference": 5.0, |
||||
"horCyclesDirect2CDifference": 5.0, |
||||
"horCyclesDirectValueDifference": 5.0, |
||||
"horHalfReturnZeroDifference": 5.0, |
||||
"horReadDifference": 5.0, |
||||
"id": "20210127093745841174", |
||||
"isTemplate": true, |
||||
"name": "限差模板3", |
||||
"singleSurveyor": true, |
||||
"slopeCycleDistanceDifference": 5.0, |
||||
"slopeLensDistanceDifference": 5.0, |
||||
"slopeReadDifference": 5.0, |
||||
"surveyorCycleCount": 2, |
||||
"verCheckWhenAngle3": true, |
||||
"verCycleDirectIDifference": 5.0, |
||||
"verCyclesAngleDifference": 5.0, |
||||
"verCyclesIDifference": 5.0, |
||||
"verIDifference": 5.0, |
||||
"verReadDifference": 5.0 |
||||
} |
||||
] |
@ -0,0 +1,117 @@ |
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<agreements> |
||||
本协议是导线助手手机应用程序(以下简称导线助手或“本应用”)与应用使用人(以下简称“用户”或“您”)所达成的协议。为使用导线助手应用的服务,您应当阅读并遵守本《用户服务协议》(以下简称“本协议”)。请您使用本应用以前,务必审慎阅读、充分理解各条款内容,特别是免除或者限制责任的条款、管辖与法律适用条款,以及开通或使用某项服务的单独协议。限制、免责条款可能以黑体加粗或加下划线的形式提示您重点注意。 |
||||
您使用本应用的服务即视为您已仔细阅读并充分了解前述协议的内容,并同意接受上述协议的约束。除非您已阅读并接受本协议所有条款,否则您无权使用本应用所提供的服务。 |
||||
如果您未满18周岁,请在法定监护人的陪同下阅读本协议,并特别注意未成年人使用条款。 |
||||
我们的产品会传输用户已安装应用的相关信息。在使用这些信息之前,我们会先获取用户的授权,经许 可后,才会进行下一步。我们不会将这些信息用于任何其它非法用途。 |
||||
一、使用者非个人化信息 |
||||
我们将通过您的IP地址来收集使用者非个人化的信息,例如您的操作系统的版本、运行环境、运营商等,以优化在您手机屏幕上显示的页面。通过收集上述信息,我们亦进行客流量统计,从而改进本应用的管理和服务。 |
||||
这些无关个人身份的信息能帮助我们辨别导线助手最受欢迎的地区并确定我们推广活动的有效性。此外,我们也可能将这些信息披露给我们的客户,使他们知道点击他们广告的人数。 |
||||
二、个人资料 |
||||
当您在本用于进行用户注册登记、参加网上论坛等各种活动,或者在使用本应用特定服务时,本应用可能会通过注册表格等形式要求您提供一些个人资料。这些个人资料可能包括: |
||||
个人识别资料:如姓名、性别、年龄、出生日期、身份证号码(或护照号码)、电话、通信地址、住址、电子邮件地址等; |
||||
个人背景:如职业、教育程度、收入状况、家庭状况、征信记录等; |
||||
个人经历:如个人职业经历、社会履历等。 |
||||
特定情形下,需要您按照本应用的要求提供所需个人资料后才能继续使用本应用的全部或部分服务,请您务必按照要求提供个人资料。否则,可能无法继续 |
||||
使用本应用的全部或部分服务。在前述情形下,本应用会提前向您提醒并说明。除非适用法律法规、政府机关、司法机关或者其他第三方对本应用作出强制要 |
||||
求,本应用不会对您提供的信息进行实质审核,如果您提供的信息错误或者不准确,由此产生的责任由您自行承担。 |
||||
请了解,在未经您同意及确认之前,本应用不会将您为参加本应用之特定活动所提供的资料利用于经您同意的用途以外的其它目的。惟有按下列第六条规定按照政府及法律要求披露时不在此限。 |
||||
三、信息安全 |
||||
本应用将对您所提供的资料进行严格的管理及保护,本应用将使用相应的技术,防止您的个人资料丢失、被盗用或遭篡改。但因计算机系统和网络技术的限制,本应用可能会因受到第三方的攻击或破坏,导致用户的个人信息被恶意篡改、盗取或泄露,本应用将采取合理措施防止类似事件的发生,并将配合国家机关和第三方对类似事件进行调查或提起必要的行动(包括但不限于诉讼等)。对于非因本应用过错原因而导致的信息安全问题,您同意给予谅解并豁免本应用可能承担的任何责任。 |
||||
四、用户权利 |
||||
您对于自己的个人资料享有以下的权利: |
||||
随时查询及请求阅览; |
||||
随时请求补充或更正; |
||||
随时请求删除; |
||||
请求停止电脑处理及利用。 |
||||
五、限制利用原则 |
||||
本应用惟在符合下列条件之一,方对收集之个人资料进行必要范围以外之使用: |
||||
已取得您的书面同意; |
||||
为免除您在生命、身体或财产方面之急迫危险; |
||||
为防止他人权益之重大危害; |
||||
为增进公共利益,且无损于您的重大利益。 |
||||
六、披露个人资料 |
||||
当政府机关依照法定程序要求本应用披露个人资料时,本应用将根据执法单位之要求或为公共安全之目的提供个人资料。在此情况下之任何披露,本应用均得免责。 |
||||
七、Cookies |
||||
Cookies是指一种技术,当使用者使用没有Cookies装置的本应用时,本应用之服务器会自动发送Cookies至您的浏览器内,并存储到您的手机硬盘内, |
||||
此Cookies便负责记录日后您访问本应用的种种活动、个人资料、浏览习惯、消费习惯甚至信用记录。 |
||||
运用Cookies技术,本应用能够为您提供更加周到的服务,本应用将会运用Cookies追访您的喜好,从而向您提供感兴趣的信息资料或存储密码,以便您造访本应用时不必每次重复输入密码。 |
||||
八、未成年人隐私权的保护 |
||||
本应用将建立和维持合理的程序,以保护未成年人个人资料的保密性及安全性。本应用郑重声明:任何18岁以下的未成年人参加网上活动应事先 |
||||
得到家长或其法定监护人(以下统称为“监护人”)的可经查证的同意。 |
||||
监护人应该承担保护未成年人在网络环境下的隐私权的首要责任。 |
||||
本应用收集未成年人的个人资料,仅为回复未成年人特定要求的目的,一经回复完毕即从记录中删除,而不会保留这些资料做进一步的利用。 |
||||
未经监护人之同意,本应用将不会使用未成年人之个人资料,亦不会向任何第三方披露或传送可识别该未成年人的个人资料。本应用如收集监护人或未成年人的姓名或其它网络通讯资料之目的仅是为获得监护人同意,则在经过一段合理时间仍未获得同意时,将主动从记录中删除此类资料。 |
||||
若经未成年人之监护人同意,本应用可对未成年人之个人资料进行收集,本应用将向监护人提供: |
||||
审视自其子女或被监护人收集之资料的机会; |
||||
拒绝其子女或被监护人的个人资料被进一步的收集或利用的机会; |
||||
变更或删除其子女或被监护人个人资料的方式。 |
||||
监护人有权拒绝本应用与其子女或被监护人做进一步的联络。 |
||||
本应用收集未成年人的个人资料,这些资料只是单纯作为保护未成年人参与网络活动时的安全,而非是作为其它目的来利用。本应用保证不会要求未成年人提供额外的个人资料,以作为允许其参与网上活动的条件。 |
||||
九、用户违法行为 |
||||
您在使用本应用服务时须遵守法律法规,不得利用本应用服务从事任何违法违规行为,包括但不限于: |
||||
(1)发布、传送、传播、储存危害国家安全统一、破坏社会稳定、违反公序良俗、侮辱、诽谤、淫秽、暴力以及任何违反国家法律法规的内容; |
||||
(2)发布、传送、传播、储存侵害他人知识产权、商业秘密等合法权利的内容; |
||||
(3)虚构事实、隐瞒真相以误导、欺骗他人; |
||||
(4)发布、传送、传播广告信息及垃圾信息; |
||||
(5)其他法律法规禁止的行为。 |
||||
如果您违反本条之约定,有权国家机关可能会对您提起诉讼、罚款或采取其他制裁措施,并要求本应用给予协助或支持,由此产生的责任均应当由您自行承担。造成损害的,您应依法予以赔偿,本应用不承担任何责任。 |
||||
如果在您使用本应用服务时违反本条约定,本应用有权进行独立判断并采取技术手段予以删除、屏蔽或断开链接。同时,本应用有权视您的行为性质,采取包括但不限于暂停或终止服务,限制、冻结或终止注册账号等,追究法律责任等措施。 |
||||
如果您违反本条约定,导致任何第三方损害的,您应当独立承担责任;导致本应用遭受损失的,您也应当一并赔偿。 |
||||
十、遵守法律和监管政策 |
||||
您在使用本服务过程中应当遵守当地相关的法律法规和监管政策,并尊重当地的道德和风俗习惯。如果您的行为违反了当地法律法规或道德风俗,您应当为此独立承担责任。 |
||||
您应避免因使用本服务而使本应用卷入政治和公共事件,否则本应用有权暂停或终止对您的服务。 |
||||
十一、合法传播和第三方投诉处理 |
||||
您通过本服务发送或传播的内容(包括但不限于网页、文字、图片、音频、视频、图表等)均由您自行承担责任。 |
||||
您发送或传播的内容应有合法来源,相关内容为您所有或您已获得权利人的授权。 |
||||
您同意本应用可为履行本协议或提供本服务的目的而使用您发送或传播的内容。 |
||||
如果本应用收到权利人通知,主张您发送或传播的内容侵犯其相关权利的,您同意本应用有权进行独立判断并采取删除、屏蔽或断开链接等措施。 |
||||
您使用本服务时不得违反国家法律法规、侵害他人合法权益。您理解并同意,如您被他人投诉侵权或您投诉他人侵权,本应用有权将争议中相关方的主体、联系方式、 |
||||
投诉相关内容等必要信息提供给其他争议方或相关部门,以便及时解决投诉纠纷,保护他人合法权益。 |
||||
十二、免责 |
||||
除上述第六条规定属免责外,下列情况时本应用亦不需承担任何责任: |
||||
不可抗力或意外事件等风险因素,导致本应用服务发生中断。 |
||||
由于您将用户密码告知他人或与他人共享注册账户,或者您操作不当而导致的任何损失; |
||||
任何由于计算机问题、黑客攻击、计算机病毒侵入或发作、因政府管制而造成的暂时性关闭等影响网络正常经营之不可抗力而造成的个人资料泄露、丢失、被盗用或被篡改等; |
||||
用户或本应用的电脑软件、系统、硬件和通信线路出现故障; |
||||
本应用的网页上有与其他网站网页的链接,包括网页上的广告。本应用对其他任何网站的内容、隐私政策或运营,或经营这些网站的公司的行为概不负责。在向这些网与本应用链接的其他网站提供个人信息以前,请查阅它们的隐私政策。 |
||||
用户通过非本应用授权的方式使用本服务; |
||||
由于与本应用链接的其它网站所造成之个人资料泄露及由此而导致的任何法律争议。 |
||||
由于用户使用第三方服务而导致的损失或产生的任何争议。其他本应用无法控制或合理预见的情形。 |
||||
由于用户粗心、图纸错误、放样方法错误等个人原因或第三方原因导致的损失。 |
||||
由于用户上传具有保密级别数据而导致的泄密行为 |
||||
您理解并同意,在使用本服务的过程中,可能会遇到网络信息或其他用户行为带来的风险,本应用不对任何信息的真实性、适用性、合法性承担责任,也不对因侵权行为给您造成的损害负责。 |
||||
十三、第三方服务 |
||||
您在本应用平台上使用第三方提供的产品或服务时,除遵守本协议约定外,还应遵守第三方的用户协议。 |
||||
您已知悉并了解,本应用平台上所链接或嵌入的第三方服务并非本应用提供,如果您对第三方服务有异议,可以直接与第三方联系,也可以向本应用反馈。本应用将协助您联系第三方并转达您的需求和意见。 |
||||
您确认并同意,在您使用第三方服务时,除非适用法律有明确规定,您和第三方的纠纷应由您和第三方解决。根据适用法律的规定,本应用需要承担责任的,本应用和第三方对可能出现的纠纷在法律规定和约定的范围内各自承担责任。 |
||||
十四、协议的生效与变更 |
||||
您使用本应用的服务即视为您已阅读本协议并接受本协议的约束。 |
||||
本应用有权在必要时修改本协议条款。您可以在相关服务页面查阅最新版本的协议条款。 |
||||
本协议条款变更后,如果您继续使用本应用提供的软件或服务,即视为您已接受修改后的协议。如果您不接受修改后的协议,应当停止使用本应用提供的软件或服务。 |
||||
十五、服务的变更、中断、终止 |
||||
本应用可能会对服务内容进行变更,也可能会中断、中止或终止服务。您理解并同意,本应用有权自主决定经营策略。 |
||||
在本应用发生合并、分立、收购、资产转让时,本应用可向第三方转让本服务下相关资产;本应用也可在单方通知您后,将本协议下部分或全部服务转交由第三方运营或履行。具体受让主体以本应用通知的为准。 |
||||
如发生下列任何一种情形,本应用有权不经通知而中断或终止向您提供的服务: |
||||
(1)根据法律规定您应提交真实信息,而您提供的个人资料不真实、或与注册时信息不一致又未能提供合理证明; |
||||
(2)您违反相关法律法规或本协议的约定; |
||||
(3)按照法律规定或主管部门的要求; |
||||
(4)出于安全的原因或其他必要的情形。 |
||||
您有责任自行备份存储在本服务中的数据。如果您的服务被终止,本应用可以从服务器上永久地删除您的数据,但法律法规另有规定的除外。服务终止后,本应用没有义务向您返还数据。 |
||||
十六、管辖与法律适用 |
||||
本协议的成立、生效、履行、解释及纠纷解决,适用中华人民共和国大陆地区法律(不包括冲突法)。 |
||||
本协议签订地为中华人民共和国上海市静安区。 |
||||
若您和本应用之间发生任何纠纷或争议,首先应友好协商解决;协商不成的,您同意将纠纷或争议提交本协议签订地(即中国郑州市)有管辖权的人民法院管辖。 |
||||
本协议所有条款的标题仅为阅读方便,本身并无实际涵义,不能作为本协议涵义解释的依据。 |
||||
本协议条款无论因何种原因部分无效或不可执行,其余条款仍有效,对双方具有约束力。 |
||||
十七、激活许可 |
||||
导线助手内部有两种激活形式,激活后可以使用部分限制功能 |
||||
1.绑定手机硬件(主板)形式,软件里可以自助激活,或找客服人员索要,换手机或更换主板需要重新购买 |
||||
2.按服务周期购买形式,供购买的服务周期分为月、季、半年、年,分别对应30天、90天、180天和365天。服务到期后,部分功能将无法使用,您可以选择再次购买一个服务周期。 |
||||
本平台可能会对服务内容进行变更,也可能会中断、中止或终止服务。您理解并同意,本平台有权自主决定经营策略。 |
||||
如果发生本平台未能在服务周期内提供应许内容的情况,您有权申请退还剩余服务周期对应的款项。 |
||||
如您因发布广告等其他垃圾信息被注销账号,本平台将不对您购买的服务周期另做补偿。 |
||||
如果因安卓系统等第三方更新导致导线助手无法识别手机硬件信息而导致用户无法继续使用付费项目的,导线助手有权停止服务。当用户降级系统或撤销更新,手机回到购买时状态时,导线助手应继续免费提供相应的服务。 |
||||
|
||||
导线助手对以上条款保有最终解释权。 |
||||
</agreements> |
@ -0,0 +1,116 @@ |
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<agreements> |
||||
This agreement is an agreement reached between the surveyor's mobile application (hereinafter referred to as surveyor or "this application") and the application user (hereinafter referred to as "user" or "you"). In order to use the services of the Surveyor Application, you should read and abide by this User Service Agreement (hereinafter referred to as "this Agreement"). Before using this application, please read carefully and fully understand the content of each clause, especially the clauses of exemption or limitation of liability, the provisions of jurisdiction and law, and the separate agreement to open or use a service. Limitations and disclaimers may be highlighted in bold or underlined. |
||||
Your use of the services of this application shall be deemed that you have carefully read and fully understood the contents of the foregoing agreement, and agree to be bound by the foregoing agreement. Unless you have read and accepted all the terms of this agreement, you are not authorized to use the services provided by this application. |
||||
If you are under the age of 18, please read this agreement with your legal guardian and pay special attention to the terms of use for minors. |
||||
Our products transmit information about apps that users have installed. Before using this information, we will obtain authorization from the user, and then proceed to the next step after permission is obtained. We will not use this information for any other illegal purpose. |
||||
I. User non-personalized information |
||||
We will collect non-personalized information of users through your IP address, such as your operating system version, operating environment, operator, etc., to optimize the pages displayed on your mobile phone screen. By collecting the above information, we also perform passenger traffic statistics to improve the management and service of this application. |
||||
This non-personally identifiable information helps us identify the most popular areas for surveyors and determine the effectiveness of our promotional activities. In addition, we may disclose this information to our customers so that they know how many people click on their ads. |
||||
Personal data |
||||
When you are using this application for user registration, participating in online forums and other activities, or when using specific services of this application, this application may ask you to provide some personal information through registration forms and other forms. These personal data may include: |
||||
Personal identification information: such as name, gender, age, date of birth, ID number (or passport number), telephone, mailing address, residential address, email address, etc .; |
||||
Personal background: such as occupation, education, income status, family status, credit history, etc .; |
||||
Personal experience: such as personal professional experience, social resume, etc. |
||||
In certain situations, you need to provide the required personal information in accordance with the requirements of this application before you can continue to use all or part of the services of this application. Please be sure to provide personal information in accordance with the requirements. Otherwise, you may not be able to continue |
||||
Use all or part of the services of this application. In the aforementioned situation, this app will remind and explain to you in advance. Unless applicable laws and regulations, government agencies, judicial authorities, or other third parties mandate this application |
||||
Request, this application will not conduct a substantive review of the information you provide. If the information you provide is wrong or inaccurate, you will be responsible for the resulting responsibility. |
||||
Please understand that without your consent and confirmation, this app will not use the data you provide for participating in specific activities of this app for purposes other than those for which you have agreed. Except when the disclosure is required by the government and the law in accordance with Article 6 below. |
||||
Information security |
||||
This application will strictly manage and protect the information you provide. This application will use corresponding technology to prevent your personal data from being lost, stolen or tampered with. However, due to the limitations of computer systems and network technologies, this application may be attacked or damaged by third parties, resulting in the user's personal information being maliciously tampered with, stolen or leaked. This application will take reasonable measures to prevent similar incidents, and Will cooperate with national authorities and third parties to investigate similar matters or initiate necessary actions (including but not limited to litigation, etc.). For information security issues that are not caused by the fault of this application, you agree to understand and waive any responsibility that this application may assume. |
||||
User rights |
||||
You have the following rights regarding your personal data: |
||||
Enquiries and requests for viewing at any time; |
||||
Request supplements or corrections at any time; |
||||
Request deletion at any time; |
||||
Request to stop computer processing and use. |
||||
V. Restricted Use Principle |
||||
This application can only use the collected personal data beyond the necessary scope if it meets one of the following conditions: |
||||
Has obtained your written consent; |
||||
To relieve you of imminent danger in life, body or property; |
||||
To prevent major harm to the rights and interests of others; |
||||
To promote the public interest without prejudice to your major interests. |
||||
6. Disclosure of Personal Information |
||||
When government agencies require this application to disclose personal data in accordance with legal procedures, this application will provide personal data at the request of law enforcement agencies or for public safety purposes. Any disclosure in this case shall be exempt from this application. |
||||
7. Cookies |
||||
Cookies refer to a technology. When a user uses this application without a cookie device, the server of this application will automatically send cookies to your browser and store them on your mobile hard disk. |
||||
These cookies are responsible for recording your various activities, personal data, browsing habits, spending habits and even credit history of your future access to this application. |
||||
Using cookies technology, this application can provide you with more thoughtful services. This application will use cookies to follow your preferences, so as to provide you with interesting information or storage passwords so that you do not have to repeat each time you visit this application enter password. |
||||
Protection of the privacy of minors |
||||
This application will establish and maintain reasonable procedures to protect the confidentiality and security of minors' personal data. This application solemnly declares that any minor under 18 years of age should participate in online activities in advance |
||||
Obtain the verifiable consent of the parent or his legal guardian (collectively referred to as the "guardian"). |
||||
The guardian should bear the primary responsibility for protecting the privacy of minors in the online environment. |
||||
This application collects the personal data of minors for the purpose of responding to the specific requirements of the minors. Once the response is completed, it will be deleted from the records without retaining these data for further use. |
||||
Without the consent of the guardian, this application will not use the personal data of the minor, nor will it disclose or transmit to any third party personal data that can identify the minor. If this application collects the name of a guardian or a minor or other online communication materials for the sole purpose of obtaining the consent of the guardian, if no consent has been obtained after a reasonable period of time, such information will be actively deleted from the record. |
||||
With the consent of the guardian of the minor, this app can collect the personal data of the minor, and this app will provide the guardian with: |
||||
Opportunities to review information collected from their children or guardians; |
||||
Opportunities to deny the further collection or use of the personal data of their children or guardians; |
||||
How to change or delete personal information of their children or guardians. |
||||
The guardian has the right to refuse this application to make further contact with its children or ward. |
||||
This application collects personal data of minors. These data are only used to protect the safety of minors when they participate in online activities, and not for other purposes. This app guarantees that minors will not be required to provide additional personal information as a condition to allow them to participate in online activities. |
||||
Nine, user illegal behavior |
||||
You must abide by laws and regulations when using this application service, and you must not use this application service to engage in any illegal acts, including but not limited to: |
||||
(1) Publishing, transmitting, disseminating, and storing contents that endanger national security and unity, undermine social stability, violate public order and good customs, insult, defamation, obscenity, violence, and any content that violates national laws and regulations; |
||||
(2) Publishing, transmitting, disseminating, and storing content that infringes on the intellectual property rights, trade secrets, and other legal rights of others; |
||||
(3) Fictional facts, concealing the truth to mislead and deceive others; |
||||
(4) Publishing, transmitting, and disseminating advertising information and spam; |
||||
(5) Other acts prohibited by laws and regulations. |
||||
If you violate the provisions of this article, the competent state authority may file a lawsuit, fine or take other sanctions against you, and ask for assistance or support for this application, and the resulting responsibility should be borne by you. If it causes damage, you should compensate it according to law, and this application will not bear any responsibility. |
||||
If you violate this agreement when you use this application service, this application has the right to make independent judgment and take technical measures to delete, block or disconnect the link. At the same time, depending on the nature of your behavior, this application has the right to take measures including, but not limited to, suspending or terminating services, restricting, freezing, or terminating registered accounts, etc., and pursue legal responsibilities. |
||||
If you violate this agreement and cause damage to any third party, you shall be solely responsible; if you cause losses to this application, you shall also pay compensation. |
||||
X. Compliance with laws and regulatory policies |
||||
In using this service, you should abide by relevant local laws and regulations and regulatory policies, and respect local morals and customs. If your actions violate local laws and regulations or ethics, you are solely responsible for this. |
||||
You should avoid getting the app involved in political and public events as a result of using the service, otherwise the app has the right to suspend or terminate the service to you. |
||||
Eleven, legal dissemination and handling of third-party complaints |
||||
The content (including but not limited to web pages, text, pictures, audio, video, graphics, etc.) that you send or disseminate through this service is your responsibility. |
||||
The content you send or disseminate should be from a legitimate source, the content is owned by you or you have been authorized by the right holder. |
||||
You agree that this application may use the content you send or distribute for the purpose of fulfilling this agreement or providing this service. |
||||
If the app receives notification from the right holder that the content you sent or transmitted violates its related rights, you agree that the app has the right to make independent judgments and take measures such as removing, blocking or disconnecting the link. |
||||
When using this service, you must not violate national laws and regulations and infringe on the legal rights and interests of others. You understand and agree that if you are complained of infringement by others or you have complained of infringement by others, this app has the right to change the subject, contact information, |
||||
The necessary information such as the content of the complaint is provided to other dispute parties or relevant departments in order to resolve the complaint dispute in a timely manner and protect the legitimate rights and interests of others. |
||||
12. Disclaimer |
||||
In addition to the exemption provided in Article 6 above, this application does not need to bear any responsibility in the following situations: |
||||
Risk factors such as force majeure or accidents cause the application service to be interrupted. |
||||
Any loss caused by you telling your user password to others or sharing a registered account with others, or your improper operation; |
||||
Any personal data leakage, loss, theft or tampering caused by computer force, force majeure that affects the normal operation of the network due to computer problems, hacking attacks, computer virus intrusion or outbreak, temporary shutdown due to government control, etc. |
||||
The user or the application's computer software, system, hardware, and communication lines have failed; |
||||
The web pages of this application have links to the web pages of other websites, including advertisements on the web pages. This application is not responsible for the content, privacy policies, or operations of any other website, or the behavior of the company that operates those websites. Please review their privacy policies before providing personal information to these websites and other websites linked to this application. |
||||
Users use the service in ways not authorized by this application; |
||||
Personal data leakage caused by other websites linked to this application and any legal disputes arising therefrom. |
||||
Loss or any dispute arising from the use of third party services by the user. Other situations beyond the control of this application or reasonably foreseeable. |
||||
Loss due to personal care or user's carelessness, wrong drawing, wrong stakeout method, etc. |
||||
Leaks due to users uploading confidential data |
||||
You understand and agree that in the process of using this service, you may encounter risks brought by network information or other user behaviors. This application is not responsible for the authenticity, applicability, legality of any information, and is not responsible for infringement Liability for damage caused to you. |
||||
Thirteenth party services |
||||
When you use products or services provided by third parties on this application platform, in addition to complying with this agreement, you should also comply with the third party's user agreement. |
||||
You know and understand that the third-party services linked or embedded on this application platform are not provided by this application. If you have any objection to the third-party services, you can directly contact the third party or provide feedback to this application. This application will assist you in contacting third parties and communicating your needs and opinions. |
||||
You acknowledge and agree that when you use third-party services, unless you are clearly required by applicable law, your dispute with the third party shall be resolved by you and the third party. According to the provisions of applicable laws, if this application needs to bear responsibility, this application and the third party shall bear their own responsibility for possible disputes within the scope stipulated by law and agreement. |
||||
14. Effectiveness and changes of the agreement |
||||
Your use of the services of this application is deemed that you have read this agreement and are bound by this agreement. |
||||
This application reserves the right to modify the terms of this agreement if necessary. You can find the latest version of the agreement terms on the relevant service page. |
||||
After changing the terms of this agreement, if you continue to use the software or services provided by this application, you are deemed to have accepted the modified agreement. If you do not accept the modified agreement, you should stop using the software or services provided by this application. |
||||
15. Change, Interruption and Termination of Services |
||||
This application may change the content of the service, and may also interrupt, suspend or terminate the service. You understand and agree that this application has the right to determine its own business strategy. |
||||
When the application merges, splits, acquires, or transfers assets, the application can transfer the relevant assets under the service to a third party; the application can also transfer some or all of the services under this agreement to a third party for operation after the unilateral notification Or fulfill. The specific transferee is subject to the notification in this application. |
||||
This app reserves the right to interrupt or terminate the services provided to you without notice if any of the following situations occur: |
||||
(1) According to the law, you should submit true information, and the personal information you provided is not true, or is inconsistent with the information at the time of registration, and fails to provide reasonable proof; |
||||
(2) you violate the relevant laws and regulations or the agreement of this agreement; |
||||
(3) In accordance with legal regulations or requirements of competent authorities; |
||||
(4) For security reasons or other necessary situations. |
||||
You are responsible for backing up the data stored in the Service yourself. If your service is terminated, this application may permanently delete your data from the server, unless otherwise provided by laws and regulations. After the service is terminated, the app is not obliged to return data to you. |
||||
16.Jurisdiction and application of law |
||||
The establishment, entry into force, performance, interpretation and dispute resolution of this agreement shall be governed by the laws of the People's Republic of China (excluding conflict of laws). |
||||
This agreement was signed in Zhengzhou, People's Republic of China. |
||||
If there is any dispute or dispute between you and this application, it should be settled through friendly negotiation first; if the negotiation fails, you agree to submit the dispute or dispute to the jurisdiction of the people's court in the place where this agreement is signed (ie Zhengzhou, China). |
||||
The headings of all the terms of this agreement are for convenience only. They have no actual meaning and cannot be used as a basis for interpreting the meaning of this agreement. |
||||
No matter what the terms of this agreement are partially invalid or unenforceable, the remaining terms are still valid and binding on both parties. |
||||
Seventeen, pay |
||||
Charge for some functions in surveyor |
||||
Binding mobile phone hardware (motherboard), and automatically generate an activation code after payment, or ask for customer service personnel, you need to pay for a new phone or motherboard |
||||
This platform may change the content of the service, and may also interrupt, suspend or terminate the service. You understand and agree that the platform has the right to independently determine its business strategy. |
||||
In the event that the platform fails to provide the promised content during the service period, you have the right to apply for a refund of the amount corresponding to the remaining service period. |
||||
If your account is cancelled due to other spam information such as advertising, this platform will not make additional compensation for the service cycle you purchased. |
||||
If a third-party update such as the Android system prevents the surveyor from recognizing the hardware information of the phone and the user cannot continue to use the paid item, the surveyor has the right to stop the service. When the user downgrades the system or cancels the update, and the phone returns to the state it was in, the surveyor should continue to provide corresponding services for free. |
||||
|
||||
Surveyors reserve the right of final interpretation. |
||||
</agreements> |
Binary file not shown.
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,202 @@ |
||||
package com.bingce.controlnetwork; |
||||
|
||||
import static com.bingce.AppChannel.customChannel; |
||||
|
||||
import android.content.SharedPreferences; |
||||
import android.graphics.drawable.Drawable; |
||||
import android.net.Uri; |
||||
import android.text.TextUtils; |
||||
import android.util.Log; |
||||
import android.widget.ImageView; |
||||
|
||||
import androidx.preference.PreferenceManager; |
||||
|
||||
import com.bingce.AppChannel; |
||||
import com.bingce.RepositoryBaseApp; |
||||
import com.bingce.controlapphelper.datasource.database.SurveyorDataBase; |
||||
import com.bingce.controlapphelper.datasource.database.tolerance.load.ToleranceLoadUtil; |
||||
import com.bingce.controlapphelper.surveyor.surveyor.ISurveyorConstants; |
||||
import com.bingce.controlapphelper.util.SettingValueUtil; |
||||
import com.bingce.controlnetwork.activity.NotificationActivity; |
||||
import com.bingce.utils.DES; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
import com.bumptech.glide.Glide; |
||||
import com.mikepenz.materialdrawer.util.AbstractDrawerImageLoader; |
||||
import com.mikepenz.materialdrawer.util.DrawerImageLoader; |
||||
import com.umeng.commonsdk.UMConfigure; |
||||
|
||||
import net.tatans.tensorflowtts.tts.TtsManager; |
||||
|
||||
import org.polaric.colorful.Colorful; |
||||
|
||||
import blankj.utilcode.util.ActivityUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
import cn.leancloud.LCInstallation; |
||||
import cn.leancloud.LCLogger; |
||||
import cn.leancloud.LeanCloud; |
||||
import cn.leancloud.push.PushService; |
||||
import cn.liuyanbing.surveyor.AppConfig; |
||||
import io.reactivex.functions.Consumer; |
||||
import io.reactivex.plugins.RxJavaPlugins; |
||||
|
||||
public class App extends RepositoryBaseApp { |
||||
|
||||
/** |
||||
* 试用次数 |
||||
*/ |
||||
public int tryCount = 0; //非setting
|
||||
/** |
||||
* 上次手动点击跳过首屏广告的时间 |
||||
*/ |
||||
public long lastSplashShowTime = 0;//非setting
|
||||
/** |
||||
* 磁偏角,用于校正指南针 |
||||
*/ |
||||
public float magneticDeclination = 0; |
||||
/** |
||||
* 蓝牙是否连接 |
||||
*/ |
||||
public boolean isBluetoothConnected = false; |
||||
/** |
||||
* 蓝牙是否重连 |
||||
*/ |
||||
public boolean isBluetoothReconnect = false; |
||||
/** |
||||
* 退出软件后是否关闭设备 |
||||
*/ |
||||
public boolean isCloseInstrumentAfterExit = false; |
||||
/** |
||||
* 用户状态发生变化,例如登录 |
||||
*/ |
||||
public boolean isUserStatusChanged = false; |
||||
/** |
||||
* 注册码第二版 |
||||
*/ |
||||
public String registerCodeV2 = ""; |
||||
|
||||
public String wifiChatClientIp = ""; |
||||
public String lastPhoneLocation = ""; |
||||
|
||||
public String levelSurveyorTime; |
||||
|
||||
private static App app; |
||||
|
||||
@Override |
||||
public void onCreate() { |
||||
customChannel = AppChannel.CUSTOM_CONTROL_PUBLIC;//AppChannel.CUSTOM_PUBLIC;
|
||||
super.onCreate(); |
||||
app = this; |
||||
|
||||
initThemeDark(); |
||||
|
||||
RxJavaPlugins.setErrorHandler(new Consumer<Throwable>() { |
||||
@Override |
||||
public void accept(Throwable throwable) { |
||||
Log.e("rxThrowable", String.valueOf(throwable)); |
||||
} |
||||
}); |
||||
|
||||
UMConfigure.preInit(this, "62c2c24705844627b5d6f943", "public"); |
||||
|
||||
// 在 LeanCloud.initialize() 之前调用
|
||||
LeanCloud.setLogLevel(LCLogger.Level.DEBUG); |
||||
|
||||
LeanCloud.initialize(this |
||||
, DES.decryptIt("//HYY/P0uNjW2bvmcfWVsRqUZcBGI1mjKeLw17mtlc4poF3nDQzo0Q==")//id,BvjcpX3kNB69xP8N0fHxDQav-gzGzoHsz
|
||||
, DES.decryptIt("LBk6WfZhiDVIlf/vpesX6s8j4ik+d23atgE0QGuwyw8=") |
||||
, "https://leancloud.bingce.com"); |
||||
|
||||
PushService.setDefaultPushCallback(this, NotificationActivity.class); |
||||
PushService.setAutoWakeUp(true); |
||||
PushService.setDefaultChannelId(this, "normal"); |
||||
LCInstallation.getCurrentInstallation().saveInBackground().subscribe(); |
||||
|
||||
DrawerImageLoader.init(new AbstractDrawerImageLoader() { |
||||
@Override |
||||
public void set(ImageView imageView, Uri uri, Drawable placeholder) { |
||||
// Picasso.get().load(uri).placeholder(placeholder).into(imageView);
|
||||
Glide.with(App.this).load(uri).into(imageView); |
||||
} |
||||
|
||||
@Override |
||||
public void cancel(ImageView imageView) { |
||||
Glide.with(App.this).clear(imageView); |
||||
// Picasso.get().cancelRequest(imageView);
|
||||
} |
||||
}); |
||||
|
||||
restorePrefs(); |
||||
|
||||
if (customChannel == AppChannel.CUSTOM_CONTROL_PRO) { |
||||
Colorful.config(this).primaryColor(Colorful.ThemeColor.BROWN).apply(); |
||||
Colorful.config(this).accentColor(Colorful.ThemeColor.BROWN).apply(); |
||||
} |
||||
|
||||
|
||||
initControlApp(); |
||||
} |
||||
|
||||
private void initThemeDark() { |
||||
Colorful.defaults() |
||||
.primaryColor(Colorful.ThemeColor.BLUE) |
||||
.accentColor(Colorful.ThemeColor.BLUE) |
||||
.translucent(false) |
||||
.dark(SettingValueUtil.isThemeDark()); |
||||
Colorful.init(this); |
||||
} |
||||
|
||||
private void restorePrefs() { |
||||
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this); |
||||
registerCodeV2 = prefs.getString("registerCodeV2", ""); |
||||
lastSplashShowTime = prefs.getLong("lastSplashShowTime", 0); |
||||
wifiChatClientIp = prefs.getString("wifiChatClientIp", ""); |
||||
isCloseInstrumentAfterExit = prefs.getBoolean("isCloseInstrumentAfterExit", false); |
||||
magneticDeclination = prefs.getFloat("magneticDeclination", 0); |
||||
lastPhoneLocation = prefs.getString("lastPhoneLocation", ""); |
||||
levelSurveyorTime = prefs.getString("levelSurveyorTime", "1"); |
||||
if (TextUtils.isEmpty(levelSurveyorTime)) { |
||||
levelSurveyorTime = "1"; |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onTrimMemory(int level) { |
||||
super.onTrimMemory(level); |
||||
if (level == TRIM_MEMORY_MODERATE) { |
||||
//开始自杀,清场掉所有的activity
|
||||
ActivityUtils.finishAllActivities(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public String applicationId() { |
||||
return BuildConfig.APPLICATION_ID; |
||||
} |
||||
|
||||
@Override |
||||
public boolean isThemeDark() { |
||||
return false; |
||||
} |
||||
|
||||
@Override |
||||
public int angleNotNumber() { |
||||
return AppConfig.instance.angleDotNum(); |
||||
} |
||||
|
||||
public static App getApp() { |
||||
return app; |
||||
} |
||||
|
||||
@Override |
||||
protected void initTtsManager() { |
||||
TtsManager.getInstance().init(this); |
||||
} |
||||
|
||||
private void initControlApp() { |
||||
ISurveyorConstants.isOpenAtr = SettingValueUtil.isOpenAtr(); |
||||
Utils.init(this); |
||||
ThreadPoolUtil.execute(ToleranceLoadUtil::init); |
||||
//数据库
|
||||
SurveyorDataBase.getInstance(); |
||||
} |
||||
} |
@ -0,0 +1,83 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import android.annotation.SuppressLint; |
||||
import android.os.Bundle; |
||||
import android.view.Menu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.widget.FrameLayout; |
||||
import android.widget.TextView; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import com.bingce.controlapphelper.util.CheckStorageUtil; |
||||
import com.bingce.controlapphelper.util.Tools; |
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
|
||||
public class AboutActivity extends ColorfulActivity { |
||||
private Toolbar mToolbar; |
||||
|
||||
@SuppressLint("SourceLockedOrientationActivity") |
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
setContentView(R.layout.activity_about); |
||||
mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
final FrameLayout flHolder = findViewById(R.id.activity_about_frame); |
||||
View tianjinView = getTianjinView(); |
||||
flHolder.addView(tianjinView); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onCreateOptionsMenu(@NonNull Menu menu) { |
||||
getMenuInflater().inflate(R.menu.menu_activity_about, menu); |
||||
return super.onCreateOptionsMenu(menu); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
switch (item.getItemId()) { |
||||
case android.R.id.home: |
||||
finish(); |
||||
break; |
||||
case R.id.menu_debug_switch: |
||||
startOpenCloseMeasureDebug(); |
||||
break; |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
private View getTianjinView() { |
||||
View viewTianjin = View.inflate(this, R.layout.item_about_tj_one, null); |
||||
TextView tvUnit = viewTianjin.findViewById(R.id.tvUnit); |
||||
TextView tvVersion = viewTianjin.findViewById(R.id.tvVersion); |
||||
tvVersion.setText("版本:" + Tools.getVersionName()); |
||||
return viewTianjin; |
||||
} |
||||
|
||||
/** |
||||
* 开始打开或关闭调试 |
||||
*/ |
||||
private void startOpenCloseMeasureDebug() { |
||||
CheckStorageUtil.check(this, () -> { |
||||
Utils.isTest = !Utils.isTest; |
||||
if (Utils.isTest) { |
||||
ToastUtils.showShort(R.string.debug_on); |
||||
} else { |
||||
ToastUtils.showShort(R.string.debug_off); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
} |
@ -0,0 +1,55 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import android.os.Bundle; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
public abstract class BaseActivity extends ColorfulActivity { |
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
} |
||||
|
||||
@Override |
||||
public void setContentView(View view) { |
||||
super.setContentView(view); |
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
} |
||||
|
||||
@Override |
||||
public void setContentView(int layoutResID) { |
||||
super.setContentView(layoutResID); |
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
} |
||||
|
||||
@Override |
||||
public void setContentView(View view, ViewGroup.LayoutParams params) { |
||||
super.setContentView(view, params); |
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
finish(); |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
} |
@ -0,0 +1,38 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import android.annotation.SuppressLint; |
||||
import android.os.Bundle; |
||||
import android.view.MenuItem; |
||||
|
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
/** |
||||
* 更新日志 |
||||
*/ |
||||
public class ChangelogActivity extends ColorfulActivity { |
||||
private static final String TAG = "ChangelogActivity"; |
||||
private Toolbar mToolbar; |
||||
|
||||
@SuppressLint("SourceLockedOrientationActivity") |
||||
@Override |
||||
protected void onCreate(Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
setContentView(R.layout.activity_changelog); |
||||
mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
finish(); |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
} |
@ -0,0 +1,26 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
|
||||
import com.bingce.activity.AbstractLogCollectActivity; |
||||
|
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.BuildConfig; |
||||
|
||||
public class LogCollectActivity extends AbstractLogCollectActivity { |
||||
@Override |
||||
protected String applicationId() { |
||||
return BuildConfig.APPLICATION_ID; |
||||
} |
||||
|
||||
@Override |
||||
protected boolean isLandscape() { |
||||
return ((App) getApplication()).isLandscape(); |
||||
} |
||||
|
||||
public static void start(Context context) { |
||||
Intent intent = new Intent(context, LogCollectActivity.class); |
||||
context.startActivity(intent); |
||||
} |
||||
} |
@ -0,0 +1,997 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import android.annotation.SuppressLint; |
||||
import android.content.Intent; |
||||
import android.content.IntentFilter; |
||||
import android.content.SharedPreferences; |
||||
import android.graphics.Color; |
||||
import android.net.Uri; |
||||
import android.os.Build; |
||||
import android.os.Bundle; |
||||
import android.util.Log; |
||||
import android.view.KeyEvent; |
||||
import android.view.Menu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.view.WindowManager; |
||||
import android.widget.CheckBox; |
||||
import android.widget.CompoundButton; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.appcompat.app.AlertDialog; |
||||
import androidx.appcompat.app.AppCompatActivity; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
import androidx.core.content.ContextCompat; |
||||
import androidx.fragment.app.Fragment; |
||||
import androidx.fragment.app.FragmentManager; |
||||
import androidx.fragment.app.FragmentPagerAdapter; |
||||
import androidx.lifecycle.ViewModelProvider; |
||||
import androidx.preference.PreferenceManager; |
||||
import androidx.viewpager.widget.ViewPager; |
||||
|
||||
import com.afollestad.materialdialogs.DialogAction; |
||||
import com.afollestad.materialdialogs.MaterialDialog; |
||||
import com.bingce.AppChannel; |
||||
import com.bingce.BaseApp; |
||||
import com.bingce.activity.BaseMainActivity; |
||||
import com.bingce.controlapphelper.event.DatabaseReadyEvent; |
||||
import com.bingce.controlapphelper.event.SwitchPageEvent; |
||||
import com.bingce.controlapphelper.util.InterfaceUtil; |
||||
import com.bingce.controlapphelper.util.SettingValueUtil; |
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.activity.backup.launch.BackupImportHelper; |
||||
import com.bingce.controlnetwork.activity.user.LoginActivity; |
||||
import com.bingce.controlnetwork.activity.user.RegisterActivity; |
||||
import com.bingce.controlnetwork.activity.user.UserInfoActivity; |
||||
import com.bingce.controlnetwork.bean.MainUserBean; |
||||
import com.bingce.controlnetwork.fragment.MainSurveyFragment; |
||||
import com.bingce.controlnetwork.fragment.ProjectListFragment; |
||||
import com.bingce.controlnetwork.newui.configfragment.ConfigFragment; |
||||
import com.bingce.controlnetwork.newui.mefragment.MeFragment; |
||||
import com.bingce.controlnetwork.util.CheckControlUpdateUtil; |
||||
import com.bingce.controlnetwork.viewmodel.MainActivityViewModel; |
||||
import com.bingce.data.sync.GlobalFlowCenter; |
||||
import com.bingce.data.sync.utils.LeanCloudConfigLoader; |
||||
import com.bingce.device.Device; |
||||
import com.bingce.device.ui.manager.DeviceConnectManager; |
||||
import com.bingce.device.ui.manager.DeviceRemindManager; |
||||
import com.bingce.device.ui.manager.DeviceRequestManager; |
||||
import com.bingce.event.CountDownEvent; |
||||
import com.bingce.event.OpenShortUrlEvent; |
||||
import com.bingce.surveyor.agentweb.AgentWebActivity; |
||||
import com.bingce.totalstation.TotalStation; |
||||
import com.bingce.ui.TabEntity; |
||||
import com.bingce.utils.ColorUtil; |
||||
import com.bingce.utils.CrashCollector; |
||||
import com.bingce.utils.DateUtils; |
||||
import com.bingce.utils.LCDeviceUtil; |
||||
import com.bingce.utils.SdkUtils; |
||||
import com.bingce.utils.ServiceDateUtils; |
||||
import com.bingce.utils.SoundPoolUtil; |
||||
import com.bingce.utils.StringUtil; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
import com.bingce.utils.Util; |
||||
import com.bingce.utils.VipManager; |
||||
import com.daimajia.numberprogressbar.NumberProgressBar; |
||||
import com.flyco.tablayout.CommonTabLayout; |
||||
import com.flyco.tablayout.listener.CustomTabEntity; |
||||
import com.flyco.tablayout.listener.OnTabSelectListener; |
||||
import com.jkyeo.splashview.SplashView; |
||||
import com.mikepenz.iconics.IconicsDrawable; |
||||
import com.mikepenz.material_design_iconic_typeface_library.MaterialDesignIconic; |
||||
import com.tencent.mm.opensdk.openapi.IWXAPI; |
||||
import com.tencent.mm.opensdk.openapi.WXAPIFactory; |
||||
import com.umeng.commonsdk.UMConfigure; |
||||
|
||||
import net.tatans.tensorflowtts.tts.TtsManager; |
||||
|
||||
import org.greenrobot.eventbus.EventBus; |
||||
import org.greenrobot.eventbus.Subscribe; |
||||
import org.greenrobot.eventbus.ThreadMode; |
||||
import org.jetbrains.annotations.NotNull; |
||||
import org.polaric.colorful.Colorful; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.Date; |
||||
import java.util.List; |
||||
|
||||
import blankj.utilcode.util.ActivityUtils; |
||||
import blankj.utilcode.util.ServiceUtils; |
||||
import blankj.utilcode.util.StringUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
import cn.leancloud.LCException; |
||||
import cn.leancloud.LCFile; |
||||
import cn.leancloud.LCObject; |
||||
import cn.leancloud.LCQuery; |
||||
import cn.leancloud.LCUser; |
||||
import io.reactivex.Observer; |
||||
import io.reactivex.disposables.Disposable; |
||||
|
||||
public class MainActivity extends BaseMainActivity implements Device.IDeviceConnectListener, Device.IDeviceRequestListener, Device.IDeviceRemindListener { |
||||
public MainActivityUtils mainActivityUtils = new MainActivityUtils(this, () -> this); |
||||
private final DeviceConnectManager deviceConnectManager = new DeviceConnectManager(this, this); |
||||
public final DeviceRequestManager deviceRequestManager = new DeviceRequestManager(this, this); |
||||
public final DeviceRemindManager deviceRemindManager = new DeviceRemindManager(this, this); |
||||
public final static String MAIN_IN_ACTION_NAME = "cn.liuyanbing.surveyor.main_activity_local_receiver"; |
||||
private Toolbar mToolbar; |
||||
// private AccountHeader accountHeader = null;
|
||||
// private Drawer drawerLeft = null;
|
||||
private NumberProgressBar cutDownProgressBar; |
||||
private CheckBox powerOffCheckbox; |
||||
private final List<Fragment> mFragments = new ArrayList<>(); |
||||
private String[] mTitles; |
||||
private final int[] mIconUnSelectIds = new int[]{R.drawable.ic_tab_project_unselect, R.drawable.ic_ruler_unselected, R.mipmap.tab_home_unselect, R.mipmap.tab_me_unselect}; |
||||
private final int[] mIconSelectIds = new int[]{R.drawable.ic_tab_project_selected, R.drawable.ic_ruler_selected, R.mipmap.tab_home_select, R.mipmap.tab_me_select}; |
||||
private final ArrayList<CustomTabEntity> mTabEntities = new ArrayList<>(); |
||||
private ViewPager mViewPager; |
||||
private CommonTabLayout mTabLayout; |
||||
private BackupImportHelper backupImportUtil = new BackupImportHelper(this); |
||||
private MaterialDialog langDialog, unbindDeviceDialog; |
||||
|
||||
private MainActivityViewModel mainActivityViewModel; |
||||
|
||||
@SuppressLint("SourceLockedOrientationActivity") |
||||
@Override |
||||
public void onCreate(Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
mainActivityViewModel = new ViewModelProvider(this).get(MainActivityViewModel.class); |
||||
EventBus.getDefault().register(this); |
||||
|
||||
if (isThemeDark()) { |
||||
setTheme(R.style.CustomThemeDark); |
||||
} |
||||
Colorful.applyTheme(this); |
||||
setContentView(R.layout.activity_main); |
||||
initWidgetListener(savedInstanceState);//初始化组件和监听器
|
||||
|
||||
((App) Utils.getApp()).tryCount = 0; |
||||
IntentFilter filter = new IntentFilter(); |
||||
filter.addAction(MAIN_IN_ACTION_NAME); |
||||
|
||||
if (LCUser.getCurrentUser() != null && LCUser.getCurrentUser().isAuthenticated()) { |
||||
VipManager.getInstance().controlSdkRefresh(this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
updateHeaderResult(); |
||||
|
||||
LCDeviceUtil.updateDeviceInfo("controlnetwork", ((App) Utils.getApp()).registerCodeV2, null); |
||||
|
||||
checkAgreementPermission(); |
||||
|
||||
//解决某个版本的bug:
|
||||
//由于升级数据库,导致限差方案丢失,所以启动的时候检测所有project,为没有限差的项目重新添加限差
|
||||
// DatabaseFixUtils.changeDefaultTolerance();
|
||||
//尝试上传crashLog
|
||||
ThreadPoolUtil.execute(() -> CrashCollector.tryUploadCrashLogInWorkerThread(this, CrashCollector.APP_LABEL_CONTROL)); |
||||
LeanCloudConfigLoader.loadLeanCloudConfig(); |
||||
} |
||||
|
||||
/** |
||||
* 初始化组件和监听器,屏幕方向发生改变时执行一次 |
||||
*/ |
||||
private void initWidgetListener(Bundle savedInstanceState) { |
||||
mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
setTitle(R.string.app_name); |
||||
//set the back arrow in the toolbar
|
||||
if (getSupportActionBar() != null) { |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(false); |
||||
getSupportActionBar().setDisplayShowTitleEnabled(true); |
||||
} |
||||
cutDownProgressBar = findViewById(R.id.cut_down_progressbar); |
||||
mViewPager = findViewById(R.id.activity_main_viewpager); |
||||
mTabLayout = findViewById(R.id.activity_main_tab_layout); |
||||
if (isThemeDark()) { |
||||
if (mTabLayout != null) { |
||||
mTabLayout.setBackgroundColor(Color.DKGRAY); |
||||
mTabLayout.setTextUnselectColor(Color.LTGRAY); |
||||
mTabLayout.setUnderlineColor(Color.BLACK); |
||||
} |
||||
} |
||||
mTitles = new String[]{getString(R.string.project), getString(R.string.survey), getString(R.string.label_manager), getString(R.string.me)}; |
||||
mFragments.add(new ProjectListFragment()); |
||||
mFragments.add(new MainSurveyFragment()); |
||||
mFragments.add(new ConfigFragment()); |
||||
// mFragments.add(new ServiceFragment());
|
||||
mFragments.add(new MeFragment()); |
||||
for (int i = 0; i < mTitles.length; i++) { |
||||
mTabEntities.add(new TabEntity(mTitles[i], mIconSelectIds[i], mIconUnSelectIds[i])); |
||||
} |
||||
|
||||
mTabLayout.setTabData(mTabEntities); |
||||
mTabLayout.setOnTabSelectListener(new OnTabSelectListener() { |
||||
@Override |
||||
public void onTabSelect(int position) { |
||||
mViewPager.setCurrentItem(position); |
||||
} |
||||
|
||||
@Override |
||||
public void onTabReselect(int position) { |
||||
if (position == 0) { |
||||
// mTabLayout.showMsg(0, mRandom.nextInt(100) + 1);
|
||||
// UnreadMsgUtils.show(mTabLayout_2.getMsgView(0), mRandom.nextInt(100) + 1);
|
||||
} |
||||
} |
||||
}); |
||||
|
||||
mViewPager.setAdapter(new MyPagerAdapter(getSupportFragmentManager())); |
||||
mViewPager.setCurrentItem(0); |
||||
mViewPager.setOffscreenPageLimit(4); |
||||
|
||||
mViewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() { |
||||
@Override |
||||
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onPageSelected(int position) { |
||||
setCurrentTab(position); |
||||
} |
||||
|
||||
@Override |
||||
public void onPageScrollStateChanged(int state) { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
public void setCurrentTab(int position) { |
||||
mTabLayout.setCurrentTab(position); |
||||
} |
||||
|
||||
|
||||
private void updateSplashLog(final boolean autoDismiss, final boolean skipDismiss, final boolean clickImageDismiss) { |
||||
if (AppChannel.customChannel != AppChannel.CUSTOM_CONTROL_PUBLIC) |
||||
return;//只统计公版
|
||||
final Date today = DateUtils.reverse2Date(DateUtils.getTodayStartTime()); |
||||
new LCQuery<>("SplashLog") |
||||
.whereEqualTo("date", today) |
||||
.findInBackground().subscribe(new Observer<List<LCObject>>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(List<LCObject> avObjects) { |
||||
if (avObjects != null && !avObjects.isEmpty()) { |
||||
avObjects.get(0).increment("showTimes"); |
||||
if (autoDismiss) |
||||
avObjects.get(0).increment("autoDismissTimes"); |
||||
if (skipDismiss) |
||||
avObjects.get(0).increment("skipTimes"); |
||||
if (clickImageDismiss) |
||||
avObjects.get(0).increment("clickTimes"); |
||||
avObjects.get(0).saveInBackground().subscribe(); |
||||
} else { |
||||
LCObject splashLog = new LCObject("SplashLog"); |
||||
splashLog.put("date", today); |
||||
splashLog.saveInBackground().subscribe(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
/** |
||||
* 读取项目文件 |
||||
*/ |
||||
@Override |
||||
public void initialize() { |
||||
//友盟统计
|
||||
UMConfigure.init(this, "62c2c24705844627b5d6f943", "public", UMConfigure.DEVICE_TYPE_PHONE, ""); |
||||
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.Q) {//安卓10以下,请求读取硬件信息
|
||||
mainActivityUtils.requestPhonePermission(); |
||||
} |
||||
try {//微信插件实例化
|
||||
if (Utils.getApp() instanceof BaseApp) { |
||||
IWXAPI wxApi = WXAPIFactory.createWXAPI(this, "wx8b41ad369eba83a9"); |
||||
wxApi.registerApp("wx8b41ad369eba83a9"); |
||||
((BaseApp) Utils.getApp()).setWxApi(wxApi); |
||||
} |
||||
} catch (Exception ignored) { |
||||
} |
||||
// CheckControlUpdateUtil.checkUpdate(this, false);
|
||||
EventBus.getDefault().post(new DatabaseReadyEvent()); |
||||
|
||||
if (LCUser.getCurrentUser() == null) { |
||||
VipManager.getInstance().controlSdkRefresh(this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
Log.d("controlSdkRefresh", "onRefreshSuccess"); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
Log.d("controlSdkRefresh", "onRefreshFailed--errorCode--" + errorCode); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
GlobalFlowCenter.Companion.getInstance().onMainActivityInitial(); |
||||
} |
||||
|
||||
// this piece of code is show how to press twice back button to exit App
|
||||
private long exitTime = 0; |
||||
|
||||
public void ExitApp() { |
||||
if ((System.currentTimeMillis() - exitTime) > 2000) { |
||||
ToastUtils.showShort(getString(R.string.press_again_exit)); |
||||
exitTime = System.currentTimeMillis(); |
||||
} else { |
||||
if (((App) Utils.getApp()).isBluetoothConnected) { |
||||
if (TotalStation.getInstance().isSupportPowerOff()) { |
||||
showPowerOffDialog(); |
||||
} else { |
||||
finish(); |
||||
} |
||||
} else { |
||||
finish(); |
||||
} |
||||
} |
||||
} |
||||
|
||||
public void showPowerOffDialog() { |
||||
MaterialDialog dialog = new MaterialDialog.Builder(this) |
||||
.title(R.string.hint) |
||||
.customView(R.layout.dialog_power_off, false) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
if (((App) Utils.getApp()).isCloseInstrumentAfterExit) { |
||||
TotalStation.getInstance().powerOff(); |
||||
} |
||||
finish(); |
||||
} |
||||
}) |
||||
.positiveText(getString(R.string.confirm)) |
||||
.negativeText(getString(R.string.cancel)).build(); |
||||
|
||||
powerOffCheckbox = dialog.getCustomView().findViewById(R.id.dialog_power_off_checkbox); |
||||
powerOffCheckbox.setChecked(((App) Utils.getApp()).isCloseInstrumentAfterExit); |
||||
powerOffCheckbox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() { |
||||
@Override |
||||
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { |
||||
((App) Utils.getApp()).isCloseInstrumentAfterExit = isChecked; |
||||
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(Utils.getApp()); |
||||
SharedPreferences.Editor editor = prefs.edit(); |
||||
editor.putBoolean("isCloseInstrumentAfterExit", ((App) Utils.getApp()).isCloseInstrumentAfterExit); |
||||
editor.apply(); |
||||
} |
||||
}); |
||||
dialog.show(); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onKeyDown(int keyCode, KeyEvent event) { |
||||
if (keyCode == KeyEvent.KEYCODE_BACK) { |
||||
// if (drawerLeft != null && drawerLeft.isDrawerOpen()) {
|
||||
// drawerLeft.closeDrawer();
|
||||
// return true;
|
||||
// }
|
||||
|
||||
if (mViewPager != null) { |
||||
Fragment viewPagerFragment = getViewPagerFragment(this, mViewPager.getId(), mViewPager.getCurrentItem()); |
||||
if (viewPagerFragment instanceof InterfaceUtil.ICustomGroup) { |
||||
if (((InterfaceUtil.ICustomGroup) viewPagerFragment).isEditModel()) { |
||||
((InterfaceUtil.ICustomGroup) viewPagerFragment).cancelEditModel(); |
||||
return true; |
||||
} |
||||
} |
||||
} |
||||
ExitApp(); |
||||
return true; |
||||
} |
||||
return super.onKeyDown(keyCode, event); |
||||
} |
||||
|
||||
public static Fragment getViewPagerFragment(AppCompatActivity activity, int viewId, int index) { |
||||
String tag = "android:switcher:" + viewId + ":" + index; |
||||
return activity.getSupportFragmentManager().findFragmentByTag(tag); |
||||
} |
||||
|
||||
@Override |
||||
protected void onSaveInstanceState(Bundle outState) { |
||||
// //add the values which need to be saved from the drawer to the bundle
|
||||
// if (drawerLeft != null)
|
||||
// outState = drawerLeft.saveInstanceState(outState);
|
||||
// //add the values which need to be saved from the accountHeader to the bundle
|
||||
// if (accountHeader != null)
|
||||
// outState = accountHeader.saveInstanceState(outState);
|
||||
super.onSaveInstanceState(outState); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onCreateOptionsMenu(Menu menu) { |
||||
getMenuInflater().inflate(R.menu.menu_activity_main, menu); |
||||
menu.findItem(R.id.menu_activity_main_bluetooth).setIcon( |
||||
new IconicsDrawable(Utils.getApp()).icon(MaterialDesignIconic.Icon.gmi_bluetooth).color(Color.WHITE).sizeDp(20)); |
||||
menu.findItem(R.id.menu_activity_main_bound_device_activate).setTitle(R.string.bound_device_activate); |
||||
return super.onCreateOptionsMenu(menu); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
switch (item.getItemId()) { |
||||
case android.R.id.home: |
||||
onBackPressed(); |
||||
case R.id.menu_activity_main_bluetooth: |
||||
mainActivityUtils.requestBluetoothPermission(); |
||||
break; |
||||
case R.id.menu_activity_main_bound_device_activate: |
||||
showActivateType(); |
||||
break; |
||||
case R.id.menu_activity_main_settings: |
||||
Intent intent4 = new Intent(Utils.getApp(), SettingsActivity.class); |
||||
startActivityForResult(intent4, 331); |
||||
break; |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
/** |
||||
* 选择激活方式 |
||||
*/ |
||||
private void showActivateType() { |
||||
if (AppChannel.customChannel == AppChannel.CUSTOM_CONTROL_PUBLIC) { |
||||
if (LCUser.getCurrentUser() == null) { |
||||
Intent intent = new Intent(Utils.getApp(), LoginActivity.class); |
||||
intent.putExtra("finishTo", UserInfoActivity.class.getName()); |
||||
startActivity(intent); |
||||
} else { |
||||
startActivity(new Intent(MainActivity.this, UserInfoActivity.class)); |
||||
} |
||||
} else { |
||||
startActivity(new Intent(MainActivity.this, RegisterActivity.class)); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onResume() { |
||||
super.onResume(); |
||||
//如果是从其他Activity返回到MainActivity时,不显示广告,如果是从后台切换出来,检查并显示广告;
|
||||
//一定放到super.onResume前,否则TopActivity始终是MainActivity,因为App的onActivityResumed在super.onResume内执行
|
||||
|
||||
if (((App) Utils.getApp()).isUserStatusChanged) { |
||||
((App) Utils.getApp()).isUserStatusChanged = false; |
||||
// if (drawerLeft != null)
|
||||
// drawerLeft.openDrawer();
|
||||
// if (accountHeader != null)
|
||||
// accountHeader.toggleSelectionList(MainActivity.this);
|
||||
updateHeaderResult(); |
||||
} |
||||
//按照设置选项,保持屏幕常亮,放在onResume而不放在onCreate里是因为,用户更改设置后返回主页就要开始常亮了
|
||||
boolean isWakeLock = PreferenceManager.getDefaultSharedPreferences(this).getBoolean("key_is_wake_lock", false); |
||||
if (isWakeLock) { |
||||
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); |
||||
} else { |
||||
getWindow().clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); |
||||
} |
||||
|
||||
SdkUtils.tick(); |
||||
EventBus.getDefault().post(new CountDownEvent()); |
||||
} |
||||
|
||||
@Override |
||||
public void onPause() { |
||||
super.onPause(); |
||||
} |
||||
|
||||
@Override |
||||
protected void onDestroy() { |
||||
super.onDestroy(); |
||||
EventBus.getDefault().unregister(this); |
||||
|
||||
TtsManager.getInstance().stopTts(); |
||||
VipManager.getInstance().destroy(); |
||||
|
||||
SoundPoolUtil.getInstance().onDestroy(); |
||||
((App) Utils.getApp()).isBluetoothReconnect = false; |
||||
TotalStation.getInstance().stopAll(); |
||||
Device.getInstance().requestDisconnect(); |
||||
for (String serviceName : ServiceUtils.getAllRunningServices()) { |
||||
ServiceUtils.stopService(serviceName); |
||||
} |
||||
ActivityUtils.finishAllActivities(); |
||||
|
||||
GlobalFlowCenter.Companion.getInstance().onMainActivityDestroy(); |
||||
} |
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN) |
||||
public void onMessageEvent(SwitchPageEvent event) { |
||||
int type = event.getType(); |
||||
try { |
||||
int index = 1; |
||||
if (type == SwitchPageEvent.TYPE_SWITCH_TO_MEASURE_PAGE_AND_DATA) { |
||||
mViewPager.setCurrentItem(index); |
||||
} |
||||
} catch (Exception e) { |
||||
e.printStackTrace(); |
||||
} |
||||
} |
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN) |
||||
public void onMessageEvent(OpenShortUrlEvent event) { |
||||
if (event.getShortUrl() != null) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", event.getShortUrl());
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2(MainActivity.this, event.getShortUrl()); |
||||
} |
||||
} |
||||
|
||||
public void showTryVipDialog() { |
||||
if (TotalStation.getInstance().isSupportMotor() && !VipManager.getInstance().checkReg()) { |
||||
LeanCloudConfigLoader.findInBackground("android_control_network_pro_try_switch", instance -> { |
||||
if (instance != null && "true".equals(instance.value)) { |
||||
if (LCUser.getCurrentUser() != null) { |
||||
ServiceDateUtils.getServerDate(new DateUtils.OnServerDateCallBack() { |
||||
@Override |
||||
public void get(Date serverDate) { |
||||
if (VipManager.getInstance().controlLevel == 0) { |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.congratulations) |
||||
.content("你获得了3天的专业版试用机会,可以驱动马达进行自动观测") |
||||
.positiveText("马上试用") |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull @NotNull MaterialDialog dialog, @NonNull @NotNull DialogAction which) { |
||||
Date newExpireDate = DateUtils.addDayOfMonth(serverDate, 3, false, true);//多1天是为了显示
|
||||
LCUser.getCurrentUser().put("controlLevel", 1); |
||||
LCUser.getCurrentUser().put("controlExpireDate", newExpireDate); |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(new Observer<LCObject>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCObject avObject) { |
||||
VipManager.getInstance().controlSdkRefresh(MainActivity.this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.success) |
||||
.content("开通成功,当前到期时间为" + DateUtils.toFull(newExpireDate)) |
||||
.positiveText(R.string.confirm) |
||||
.show(); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
ToastUtils.showShort("开通失败,错误码:" + new LCException(e).getCode()); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
}) |
||||
.negativeText("取消") |
||||
.show(); |
||||
} else if (VipManager.getInstance().controlLevel == 1) { |
||||
if (!VipManager.getInstance().isControlInExpireDate) |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.congratulations) |
||||
.content("你获得了7天的专业版试用机会,可以驱动马达自动观测,请联系客服申请开通") |
||||
.positiveText("马上申请") |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull @NotNull MaterialDialog dialog, @NonNull @NotNull DialogAction which) { |
||||
Intent intent = new Intent(); |
||||
intent.setClass(Utils.getApp(), AgentWebActivity.class); |
||||
intent.putExtra("short_url", "android_url_business_manager"); |
||||
startActivity(intent); |
||||
} |
||||
}) |
||||
.negativeText("取消") |
||||
.show(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void error(Throwable throwable) { |
||||
ToastUtils.showShort(R.string.get_server_date_failed); |
||||
} |
||||
}); |
||||
} else { |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.log_in_to_try) |
||||
.content("登录后,您将获取3-7天的试用机会,请登录") |
||||
.positiveText("登录") |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull @NotNull MaterialDialog dialog, @NonNull @NotNull DialogAction which) { |
||||
Intent intent = new Intent(); |
||||
intent.setClass(Utils.getApp(), LoginActivity.class); |
||||
intent.putExtra("finishTo", UserInfoActivity.class.getName()); |
||||
startActivity(intent); |
||||
} |
||||
}) |
||||
.negativeText("取消") |
||||
.show(); |
||||
} |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN) |
||||
public void onMessageEvent(CountDownEvent event) { |
||||
if (cutDownProgressBar != null) { |
||||
cutDownProgressBar.setVisibility(View.VISIBLE); |
||||
if (!SdkUtils.isRegCodeValidate() && SdkUtils.isVipValidate()) { |
||||
int maxProgress = (int) (SdkUtils.availableTimeMax() / 60 / 1000L); |
||||
cutDownProgressBar.setMax(maxProgress); |
||||
int progress = Math.max((int) (SdkUtils.availableTime() / 60 / 1000L), 0);//可用时间可能小于0
|
||||
cutDownProgressBar.setProgress(progress); |
||||
if (progress < 60) { |
||||
cutDownProgressBar.setPrefix(getString(R.string.remaining_offline_time) + progress + getString(R.string.minute) + " "); |
||||
} else { |
||||
cutDownProgressBar.setPrefix(getString(R.string.remaining_offline_time) + progress / 60 + getString(R.string.hour) + progress % 60 + getString(R.string.minute) + " "); |
||||
} |
||||
if (event.isNeedRefresh()) { |
||||
VipManager.getInstance().controlSdkRefresh(this, ((App) Utils.getApp()).registerCodeV2, null); |
||||
} |
||||
if (progress == 240 || progress == 180 || progress == 120 || progress == 60 || (progress > 0 && progress < 60 && progress % 10 == 0)) { |
||||
new AlertDialog.Builder(this) |
||||
.setTitle(R.string.warning) |
||||
.setMessage(getString(R.string.remaining_offline_time) + progress + getString(R.string.minute) + "," + getString(R.string.the_network_reboot_software_can_reset_the_remaining_time_offline)) |
||||
.setPositiveButton(R.string.i_know, null) |
||||
.show(); |
||||
} |
||||
if (progress > 240) {//离线时间大于4小时,主题色显示
|
||||
cutDownProgressBar.setProgressTextColor(ColorUtil.getColorPrimary(this)); |
||||
cutDownProgressBar.setReachedBarColor(ColorUtil.getColorPrimary(this)); |
||||
cutDownProgressBar.setUnreachedBarColor(ColorUtil.getColorPrimary(this)); |
||||
} else if (progress > 120) {//离线时间2-5小时间显示橙色警告
|
||||
cutDownProgressBar.setProgressTextColor(ContextCompat.getColor(this, R.color.md_orange_800)); |
||||
cutDownProgressBar.setReachedBarColor(ContextCompat.getColor(this, R.color.md_orange_800)); |
||||
cutDownProgressBar.setUnreachedBarColor(ContextCompat.getColor(this, R.color.md_orange_800)); |
||||
} else {//离线时间小于2小时红色警告
|
||||
cutDownProgressBar.setProgressTextColor(Color.RED); |
||||
cutDownProgressBar.setReachedBarColor(Color.RED); |
||||
cutDownProgressBar.setUnreachedBarColor(Color.RED); |
||||
} |
||||
Log.d("cutdownProgressBar", "setProgress" + progress); |
||||
} else { |
||||
cutDownProgressBar.setVisibility(View.GONE); |
||||
} |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 教程列表 |
||||
*/ |
||||
public void showTutorialListDialog() { |
||||
new MaterialDialog.Builder(this) |
||||
.title(R.string.video_tutorial) |
||||
.items(new String[]{getString(R.string.bilibili) |
||||
, getString(R.string.tencent_video) |
||||
, getString(R.string.baidudisk) |
||||
, getString(R.string.surveyor_home)}) |
||||
.itemsCallback(new MaterialDialog.ListCallback() { |
||||
@Override |
||||
public void onSelection(MaterialDialog dialog, View itemView, int which, CharSequence text) { |
||||
switch (which) { |
||||
case 0: |
||||
// Intent intent1 = new Intent();
|
||||
// intent1.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent1.putExtra("short_url", "android_url_bilibili_tutorial");
|
||||
// startActivity(intent1);
|
||||
AgentWebActivity.navigation2( |
||||
MainActivity.this, "android_url_bilibili_tutorial" |
||||
); |
||||
break; |
||||
case 1: |
||||
// Intent intent2 = new Intent();
|
||||
// intent2.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent2.putExtra("short_url", "android_url_tencent_video_tutorial");
|
||||
// startActivity(intent2);
|
||||
AgentWebActivity.navigation2( |
||||
MainActivity.this, "android_url_tencent_video_tutorial" |
||||
); |
||||
break; |
||||
case 2: |
||||
// Intent intent3 = new Intent();
|
||||
// intent3.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent3.putExtra("short_url", "android_url_baidu_pan_tutorial");
|
||||
// startActivity(intent3);
|
||||
AgentWebActivity.navigation2( |
||||
MainActivity.this, "android_url_baidu_pan_tutorial" |
||||
); |
||||
break; |
||||
case 3: |
||||
// Intent intent4 = new Intent();
|
||||
// intent4.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent4.putExtra("short_url", "android_url_surveyor_home");
|
||||
// startActivity(intent4);
|
||||
AgentWebActivity.navigation2( |
||||
MainActivity.this, "android_url_surveyor_home" |
||||
); |
||||
break; |
||||
} |
||||
} |
||||
}).show(); |
||||
} |
||||
|
||||
/** |
||||
* 刷新左侧用户信息 |
||||
*/ |
||||
public void updateHeaderResult() { |
||||
Log.d("updateHeaderResult", "updateHeaderResult"); |
||||
// if (drawerLeft == null || accountHeader == null)
|
||||
// return;
|
||||
// for (int i = accountHeader.getProfiles().size() - 1; i >= 0; i--) {
|
||||
// accountHeader.removeProfile(accountHeader.getProfiles().get(i));
|
||||
// }
|
||||
|
||||
// if (LCUser.getCurrentUser() == null || !LCUser.getCurrentUser().isAuthenticated()) {
|
||||
// accountHeader.addProfiles(
|
||||
// new ProfileSettingDrawerItem().withName(getString(R.string.log_in))
|
||||
// .withIcon(new IconicsDrawable(this).icon(MaterialDesignIconic.Icon.gmi_sign_in).paddingDp(5))
|
||||
// .withIdentifier(1000).withOnDrawerItemClickListener(new Drawer.OnDrawerItemClickListener() {
|
||||
// @Override
|
||||
// public boolean onItemClick(View view, int position, IDrawerItem drawerItem) {
|
||||
// Intent intent = new Intent(Utils.getApp(), LoginActivity.class);
|
||||
// intent.putExtra("finishTo", UserInfoActivity.class.getName());
|
||||
// startActivity(intent);
|
||||
// return false;
|
||||
// }
|
||||
// }));
|
||||
// } else {
|
||||
// accountHeader.addProfiles(new ProfileSettingDrawerItem().withName(getString(R.string.user_info)).withIcon(new IconicsDrawable(this).icon(MaterialDesignIconic.Icon.gmi_account).paddingDp(5)).withIdentifier(1000).withOnDrawerItemClickListener(new Drawer.OnDrawerItemClickListener() {
|
||||
// @Override
|
||||
// public boolean onItemClick(View view, int position, IDrawerItem drawerItem) {
|
||||
// startActivity(new Intent(MainActivity.this, UserInfoActivity.class));
|
||||
// return false;
|
||||
// }
|
||||
// }));
|
||||
// }
|
||||
|
||||
|
||||
updateProfileItem(); |
||||
} |
||||
|
||||
private void updateProfileItem() { |
||||
if (LCUser.getCurrentUser() != null) { |
||||
String nickname = LCUser.getCurrentUser().getString("nickname"); |
||||
LCFile avatarFile = LCUser.getCurrentUser().getLCFile("avatar"); |
||||
if (!StringUtils.isEmpty(nickname)) { |
||||
// ProfileDrawerItem item = new ProfileDrawerItem().withName(nickname).withEmail(LCUser.getCurrentUser().getUsername()).withIdentifier(1003);
|
||||
// if (avatarFile == null) {
|
||||
// item.withIcon(R.drawable.app_logo);
|
||||
// } else {
|
||||
// item.withIcon(avatarFile.getUrl());
|
||||
// }
|
||||
// accountHeader.addProfiles(item);
|
||||
|
||||
String avatarUrl = null; |
||||
if (avatarFile != null) { |
||||
avatarUrl = avatarFile.getUrl(); |
||||
} |
||||
|
||||
mainActivityViewModel.getRefreshLoginUserLiveData().setValue( |
||||
new MainUserBean(LCUser.getCurrentUser().getUsername(), |
||||
nickname, avatarUrl)); |
||||
} else { |
||||
LCObject userProfile = LCUser.getCurrentUser().getLCObject("profile"); |
||||
if (userProfile != null) { |
||||
userProfile.fetchInBackground().subscribe(new Observer<LCObject>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCObject avObject) { |
||||
if (isFinishing()) return; |
||||
String nickname = avObject.getString("nickname"); |
||||
LCFile avatarFile = avObject.getLCFile("avatar"); |
||||
if (!StringUtils.isEmpty(nickname)) { |
||||
// ProfileDrawerItem item = new ProfileDrawerItem().withName(nickname).withEmail(LCUser.getCurrentUser().getUsername()).withIdentifier(1003);
|
||||
// if (avatarFile == null) {
|
||||
// item.withIcon(R.drawable.app_logo);
|
||||
// } else {
|
||||
// item.withIcon(avatarFile.getUrl());
|
||||
// }
|
||||
// accountHeader.addProfiles(item);
|
||||
|
||||
//保存到_User,下次不再查Profile
|
||||
LCUser.getCurrentUser().put("nickname", nickname); |
||||
|
||||
String avatarUrl = null; |
||||
if (avatarFile != null) { |
||||
LCUser.getCurrentUser().put("avatar", avatarFile); |
||||
avatarUrl = avatarFile.getUrl(); |
||||
} |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(); |
||||
|
||||
|
||||
mainActivityViewModel.getRefreshLoginUserLiveData().setValue( |
||||
new MainUserBean(LCUser.getCurrentUser().getUsername(), |
||||
nickname, avatarUrl)); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} else { |
||||
new LCQuery<>("Profile") |
||||
.whereEqualTo("creatorId", LCUser.getCurrentUser().getObjectId()) |
||||
.findInBackground() |
||||
.subscribe(new Observer<List<LCObject>>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(List<LCObject> list) { |
||||
if (isFinishing()) return; |
||||
if (list != null && !list.isEmpty()) { |
||||
String nickname = list.get(0).getString("nickname"); |
||||
LCFile avatarFile = list.get(0).getLCFile("avatar"); |
||||
if (!StringUtils.isEmpty(nickname)) { |
||||
// ProfileDrawerItem item = new ProfileDrawerItem().withName(nickname).withEmail(LCUser.getCurrentUser().getUsername()).withIdentifier(1003);
|
||||
// if (avatarFile == null) {
|
||||
// item.withIcon(R.drawable.app_logo);
|
||||
// } else {
|
||||
// item.withIcon(avatarFile.getUrl());
|
||||
// }
|
||||
// accountHeader.addProfiles(item);
|
||||
|
||||
String avatarUrl = null; |
||||
|
||||
//保存到_User,下次不再查Profile
|
||||
LCUser.getCurrentUser().put("nickname", nickname); |
||||
|
||||
if (avatarFile != null) { |
||||
LCUser.getCurrentUser().put("avatar", avatarFile); |
||||
avatarUrl = avatarFile.getUrl(); |
||||
} |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(); |
||||
|
||||
mainActivityViewModel.getRefreshLoginUserLiveData().setValue( |
||||
new MainUserBean(LCUser.getCurrentUser().getUsername(), |
||||
nickname, avatarUrl)); |
||||
} |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
} |
||||
} else { |
||||
// accountHeader.addProfiles(new ProfileDrawerItem().withEmail(getString(R.string.click_avatar_to_log_in)).withIcon(R.drawable.app_logo).withIdentifier(1003));
|
||||
mainActivityViewModel.getRefreshLoginUserLiveData().setValue( |
||||
new MainUserBean(null, |
||||
null, null)); |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 开启左侧菜单 |
||||
*/ |
||||
public void openLeftDrawer() { |
||||
// if (drawerLeft != null)
|
||||
// drawerLeft.openDrawer();
|
||||
} |
||||
|
||||
@Override |
||||
public void onDeviceConnectLost() { |
||||
mainActivityUtils.onDeviceConnectLost(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDeviceConnectFailed() { |
||||
mainActivityUtils.onDeviceConnectFailed(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDeviceConnectSucceed() { |
||||
mainActivityUtils.onDeviceConnectSucceed(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDeviceConnectNeedOpenBT() { |
||||
} |
||||
|
||||
@Override |
||||
public void onDeviceRequestConnect() { |
||||
mainActivityUtils.onRequestConnect(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDeviceRequestDisconnect() { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onDeviceRequestSetupChat() { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onRemindConnectDevice() { |
||||
mainActivityUtils.showRemindConnectDeviceDialog(); |
||||
} |
||||
|
||||
private class MyPagerAdapter extends FragmentPagerAdapter { |
||||
public MyPagerAdapter(@NonNull FragmentManager fm) { |
||||
super(fm); |
||||
} |
||||
|
||||
public MyPagerAdapter(@NonNull FragmentManager fm, int behavior) { |
||||
super(fm, behavior); |
||||
} |
||||
|
||||
@NonNull |
||||
@Override |
||||
public Fragment getItem(int position) { |
||||
return mFragments.get(position); |
||||
} |
||||
|
||||
@Override |
||||
public int getCount() { |
||||
return mFragments.size(); |
||||
} |
||||
} |
||||
|
||||
private void restartApplication() { |
||||
android.os.Process.killProcess(android.os.Process.myPid()); |
||||
} |
||||
|
||||
private boolean isThemeDark() { |
||||
return SettingValueUtil.isThemeDark(); |
||||
} |
||||
|
||||
} |
@ -0,0 +1,464 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import android.Manifest; |
||||
import android.content.ComponentName; |
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.content.pm.PackageManager; |
||||
import android.location.Location; |
||||
import android.location.LocationManager; |
||||
import android.os.Build; |
||||
import android.provider.Settings; |
||||
import android.view.View; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.appcompat.app.AppCompatActivity; |
||||
import androidx.core.app.ActivityCompat; |
||||
import androidx.lifecycle.Lifecycle; |
||||
import androidx.lifecycle.LifecycleEventObserver; |
||||
import androidx.lifecycle.LifecycleOwner; |
||||
|
||||
import com.afollestad.materialdialogs.DialogAction; |
||||
import com.afollestad.materialdialogs.MaterialDialog; |
||||
import com.bingce.AppChannel; |
||||
import com.bingce.BaseApp; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.device.Device; |
||||
import com.bingce.device.enums.ConnectTypeEnum; |
||||
import com.bingce.device.enums.DeviceTypeEnum; |
||||
import com.bingce.device.service.comm.ble.BleService; |
||||
import com.bingce.device.service.comm.emulator.EmulatorService; |
||||
import com.bingce.device.service.comm.localgps.LocationService; |
||||
import com.bingce.device.service.comm.localgps.NativePositioningService; |
||||
import com.bingce.device.service.comm.otg.OTGCommService; |
||||
import com.bingce.device.service.comm.socket.TsSocketService; |
||||
import com.bingce.device.service.comm.spp.BTService; |
||||
import com.bingce.device.ui.ConnectLevelActivity; |
||||
import com.bingce.device.ui.ConnectRtkActivity; |
||||
import com.bingce.device.ui.ConnectTSActivity; |
||||
import com.bingce.device.ui.utils.DeviceUtil; |
||||
import com.bingce.device.ui.widget.BCProgressDialog; |
||||
import com.bingce.level.Level; |
||||
import com.bingce.rtk.event.RtkSpeechEvent; |
||||
import com.bingce.totalstation.TotalStation; |
||||
import com.bingce.totalstation.TsConfig; |
||||
import com.bingce.utils.AppCompatActivityProviderUtils; |
||||
import com.bingce.utils.IProvider; |
||||
import com.bingce.utils.RomUtil; |
||||
import com.bingce.utils.SoundPoolUtil; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
import com.bingce.utils.Util; |
||||
import com.bingce.utils.ValidateUtil; |
||||
import com.hjq.permissions.OnPermissionCallback; |
||||
import com.hjq.permissions.OnPermissionPageCallback; |
||||
import com.hjq.permissions.Permission; |
||||
import com.hjq.permissions.XXPermissions; |
||||
|
||||
import net.tatans.tensorflowtts.tts.TtsManager; |
||||
|
||||
import org.greenrobot.eventbus.EventBus; |
||||
import org.greenrobot.eventbus.Subscribe; |
||||
import org.greenrobot.eventbus.ThreadMode; |
||||
|
||||
import java.util.List; |
||||
|
||||
import blankj.utilcode.util.ActivityUtils; |
||||
import blankj.utilcode.util.ServiceUtils; |
||||
import blankj.utilcode.util.StringUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
|
||||
public class MainActivityUtils extends AppCompatActivityProviderUtils { |
||||
private BCProgressDialog deviceConnectingProgressDialog; |
||||
|
||||
public MainActivityUtils(AppCompatActivity activity, IProvider<AppCompatActivity> activityIProvider) { |
||||
super(activityIProvider); |
||||
activity.getLifecycle().addObserver(new LifecycleEventObserver() { |
||||
@Override |
||||
public void onStateChanged(@NonNull LifecycleOwner source, @NonNull Lifecycle.Event event) { |
||||
switch (event) { |
||||
case ON_CREATE: |
||||
EventBus.getDefault().register(MainActivityUtils.this); |
||||
SoundPoolUtil.getInstance().initHintSing(activity, SoundPoolUtil.TEST, R.raw.savedone); |
||||
break; |
||||
case ON_DESTROY: |
||||
EventBus.getDefault().unregister(MainActivityUtils.this); |
||||
SoundPoolUtil.getInstance().onDestroy(); |
||||
break; |
||||
} |
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN) |
||||
public void onMessageEvent(RtkSpeechEvent event) { |
||||
if (!StringUtils.isEmpty(event.getText())) TtsManager.getInstance().speak(event.getText()); |
||||
} |
||||
|
||||
/** |
||||
* 连接设备成功后,启动相关服务,因为Ntrip与SN无关,可以在此执行,与SN相关的服务在RtkReceivedSerialNumberEvent事件后执行 |
||||
*/ |
||||
public void onDeviceConnectSucceed() { |
||||
if (deviceConnectingProgressDialog != null && deviceConnectingProgressDialog.isShowing()) { |
||||
deviceConnectingProgressDialog.dismiss(); |
||||
} |
||||
|
||||
if (Device.getInstance().deviceType == DeviceTypeEnum.DEVICE_TYPE_TS) { |
||||
TotalStation.getInstance().runnableStart(); |
||||
TotalStation.getInstance().init(); |
||||
} else if (Device.getInstance().deviceType == DeviceTypeEnum.DEVICE_TYPE_LEVEL) { |
||||
Level.getInstance().init(); |
||||
} |
||||
//记录用户联机时手机定位的大概位置
|
||||
if (ActivityCompat.checkSelfPermission(/*this*/context(), Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) { |
||||
LocationManager mLocationManager = ((LocationManager) context().getSystemService(Context.LOCATION_SERVICE)); |
||||
if (mLocationManager != null) { |
||||
List<String> providers = mLocationManager.getProviders(true); |
||||
if (providers.contains(LocationManager.GPS_PROVIDER)) { |
||||
Location location = mLocationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER); |
||||
if (location != null) { |
||||
((BaseApp) Utils.getApp()).lastPhoneLocation = location.getLatitude() + "," + location.getLongitude(); |
||||
Util.putPreference("lastPhoneLocation", ((BaseApp) Utils.getApp()).lastPhoneLocation); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
|
||||
public void onDeviceConnectFailed() { |
||||
if (deviceConnectingProgressDialog != null && deviceConnectingProgressDialog.isShowing()) { |
||||
deviceConnectingProgressDialog.dismiss(); |
||||
ToastUtils.showShort(R.string.device_connect_failed); |
||||
} |
||||
} |
||||
|
||||
public void onDeviceConnectLost() { |
||||
ToastUtils.showShort(R.string.device_connect_lost); |
||||
} |
||||
|
||||
public void onRequestConnect() { |
||||
if (deviceConnectingProgressDialog == null || !deviceConnectingProgressDialog.isShowing()) { |
||||
deviceConnectingProgressDialog = new BCProgressDialog.Builder(ActivityUtils.getTopActivity()).title(R.string.connect_device).build(); |
||||
deviceConnectingProgressDialog.show(); |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 连接蓝牙先请求打开定位权限 |
||||
*/ |
||||
public void requestBluetoothPermission() { |
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S && XXPermissions.isGranted(ActivityUtils.getTopActivity(), Permission.BLUETOOTH_CONNECT)) {//S及以后不需要位置权限
|
||||
checkConnectLast(); |
||||
} else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {//S及以后不需要位置权限,此时只需请求connect权限
|
||||
if (XXPermissions.isGranted(ActivityUtils.getTopActivity(), Permission.BLUETOOTH_CONNECT)) { |
||||
checkConnectLast(); |
||||
} else { |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.location_permission) |
||||
.content(R.string.bluetooth_need_location_permission) |
||||
.canceledOnTouchOutside(false) |
||||
.positiveText(R.string.to_allow) |
||||
.negativeText(R.string.refuse) |
||||
.onPositive((dialog, which) -> { |
||||
XXPermissions.with(ActivityUtils.getTopActivity()) |
||||
.permission(Permission.BLUETOOTH_CONNECT) |
||||
.request(new OnPermissionCallback() { |
||||
@Override |
||||
public void onGranted(List<String> permissions, boolean all) { |
||||
checkConnectLast(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDenied(List<String> permissions, boolean never) { |
||||
if (never) { |
||||
ToastUtils.showLong(R.string.bluetooth_connect_need_permission); |
||||
XXPermissions.startPermissionActivity(ActivityUtils.getTopActivity(), permissions, new OnPermissionPageCallback() { |
||||
@Override |
||||
public void onGranted() { |
||||
requestBluetoothPermission(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDenied() { |
||||
ToastUtils.showLong(R.string.bluetooth_connect_need_permission); |
||||
} |
||||
}); |
||||
} else { |
||||
requestBluetoothPermission(); |
||||
} |
||||
} |
||||
}); |
||||
}) |
||||
.onNegative((dialog, which) -> { |
||||
|
||||
}).show(); |
||||
} |
||||
} else {//S以下,需要请求两个权限,位置和Connect权限
|
||||
if (XXPermissions.isGranted(ActivityUtils.getTopActivity(), Permission.ACCESS_FINE_LOCATION, Permission.BLUETOOTH_CONNECT)) { |
||||
checkConnectLast(); |
||||
} else { |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.location_permission) |
||||
.content(R.string.bluetooth_need_location_permission) |
||||
.canceledOnTouchOutside(false) |
||||
.positiveText(R.string.to_allow) |
||||
.negativeText(R.string.refuse) |
||||
.onPositive((dialog, which) -> { |
||||
XXPermissions.with(ActivityUtils.getTopActivity()) |
||||
.permission(Permission.ACCESS_FINE_LOCATION, Permission.BLUETOOTH_CONNECT) |
||||
.request(new OnPermissionCallback() { |
||||
@Override |
||||
public void onGranted(List<String> permissions, boolean all) { |
||||
if (all) { |
||||
checkConnectLast(); |
||||
} else { |
||||
requestBluetoothPermission(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onDenied(List<String> permissions, boolean never) { |
||||
if (never) { |
||||
ToastUtils.showLong(R.string.bluetooth_connection_requires_positioning_permission_please_turn_it_on_manually); |
||||
XXPermissions.startPermissionActivity(ActivityUtils.getTopActivity(), permissions, new OnPermissionPageCallback() { |
||||
@Override |
||||
public void onGranted() { |
||||
requestBluetoothPermission(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDenied() { |
||||
ToastUtils.showLong(R.string.bluetooth_connect_need_permission); |
||||
} |
||||
}); |
||||
} else { |
||||
requestBluetoothPermission(); |
||||
} |
||||
} |
||||
}); |
||||
}) |
||||
.onNegative((dialog, which) -> { |
||||
|
||||
}).show(); |
||||
} |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 检查权限 |
||||
*/ |
||||
public void requestPhonePermission() { |
||||
if (!XXPermissions.isGranted(ActivityUtils.getTopActivity(), Permission.READ_PHONE_STATE)) { |
||||
long lastReadPhoneStateDeniedTime = Util.getLongPreference("lastReadPhoneStateDeniedTime", 0L); |
||||
if (System.currentTimeMillis() - lastReadPhoneStateDeniedTime > 48 * 60 * 60 * 1000L) {//每48小时提示一次
|
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.mobile_phone_permissions) |
||||
.content(R.string.verify_imei_imsi_code_to_prevent_account_theft) |
||||
.canceledOnTouchOutside(false) |
||||
.positiveText(R.string.to_allow) |
||||
.negativeText(R.string.refuse) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
XXPermissions.with(ActivityUtils.getTopActivity()) |
||||
.permission(Permission.READ_PHONE_STATE) |
||||
.request(new OnPermissionCallback() { |
||||
@Override |
||||
public void onGranted(List<String> permissions, boolean all) { |
||||
} |
||||
|
||||
@Override |
||||
public void onDenied(List<String> permissions, boolean never) { |
||||
if (never) { |
||||
ToastUtils.showShort(R.string.manually_enable_the_phone_state_permission_to_bind_hardware_devices); |
||||
} |
||||
Util.putPreference("lastReadPhoneStateDeniedTime", System.currentTimeMillis()); |
||||
} |
||||
}); |
||||
} |
||||
}) |
||||
.onNegative(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
Util.putPreference("lastReadPhoneStateDeniedTime", System.currentTimeMillis()); |
||||
} |
||||
}).show(); |
||||
} |
||||
} |
||||
} |
||||
|
||||
public void showRemindConnectDeviceDialog() { |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.hint) |
||||
.content(R.string.no_instrument_connected) |
||||
.positiveText(R.string.connect) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
checkConnectLast(); |
||||
} |
||||
}) |
||||
.negativeText(R.string.cancel) |
||||
.show(); |
||||
} |
||||
|
||||
|
||||
public void checkConnectLast() { |
||||
if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_SPP) { |
||||
if (!ServiceUtils.isServiceRunning(BTService.class.getName())) { |
||||
ServiceUtils.startService(BTService.class); |
||||
} |
||||
} else if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_BLE) { |
||||
if (!ServiceUtils.isServiceRunning(BleService.class.getName())) { |
||||
ServiceUtils.startService(BleService.class); |
||||
} |
||||
} else if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_QXBT) { |
||||
//千寻RTK需要GnssServer连接蓝牙
|
||||
} else if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_HOTSPOT) { |
||||
if (!ServiceUtils.isServiceRunning(TsSocketService.class.getName())) { |
||||
ServiceUtils.startService(TsSocketService.class); |
||||
} |
||||
} else if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_OTG) { |
||||
if (!ServiceUtils.isServiceRunning(OTGCommService.class.getName())) { |
||||
ServiceUtils.startService(OTGCommService.class); |
||||
} |
||||
} else if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_TPCOM) { |
||||
if (!ServiceUtils.isServiceRunning(TsSocketService.class.getName())) { |
||||
ServiceUtils.startService(TsSocketService.class); |
||||
} |
||||
} else if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_PHONE_LOCATION) { |
||||
if (!ServiceUtils.isServiceRunning(NativePositioningService.class.getName())) { |
||||
ServiceUtils.startService(NativePositioningService.class); |
||||
} |
||||
} else if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_EMULATOR) { |
||||
if (!ServiceUtils.isServiceRunning(EmulatorService.class.getName())) { |
||||
ServiceUtils.startService(EmulatorService.class); |
||||
} |
||||
} |
||||
if (!Device.getInstance().isDeviceConnected()) { |
||||
if (!"".equals(Device.getInstance().deviceBlueName)) { |
||||
String instrumentInfo = ActivityUtils.getTopActivity().getString(R.string.instrument_name) + ":" + Device.getInstance().deviceBlueName + "\n" + ActivityUtils.getTopActivity().getString(R.string.instrument_type_name) + ":" + Device.getInstance().deviceBrand; |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.quick_connect) |
||||
.content(instrumentInfo) |
||||
.positiveText(R.string.connect) |
||||
.negativeText(R.string.config) |
||||
.neutralText(R.string.switch_instrument) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_HOTSPOT) { |
||||
startHotspotComm(); |
||||
} else { |
||||
Device.getInstance().requestConnect(); |
||||
ToastUtils.showShort(R.string.connecting_please_wait); |
||||
} |
||||
} |
||||
}).onNegative(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
Intent intent; |
||||
if (Device.getInstance().deviceType == DeviceTypeEnum.DEVICE_TYPE_TS) { |
||||
intent = new Intent(ActivityUtils.getTopActivity(), ConnectTSActivity.class); |
||||
} else if (Device.getInstance().deviceType == DeviceTypeEnum.DEVICE_TYPE_LEVEL) { |
||||
intent = new Intent(ActivityUtils.getTopActivity(), ConnectLevelActivity.class); |
||||
} else { |
||||
intent = new Intent(ActivityUtils.getTopActivity(), ConnectRtkActivity.class); |
||||
} |
||||
intent.putExtra("customChannel", AppChannel.customChannel); |
||||
ActivityUtils.getTopActivity().startActivity(intent); |
||||
} |
||||
}).onNeutral(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
chooseInstrumentType(); |
||||
} |
||||
}).show(); |
||||
} else { |
||||
chooseInstrumentType(); |
||||
} |
||||
} else { |
||||
if (Device.getInstance().connectType == ConnectTypeEnum.CONNECT_TYPE_PHONE_LOCATION) { |
||||
ToastUtils.showShort(R.string.native_rtk_is_running); |
||||
} else { |
||||
Intent intent; |
||||
if (Device.getInstance().deviceType == DeviceTypeEnum.DEVICE_TYPE_TS) { |
||||
intent = new Intent(ActivityUtils.getTopActivity(), ConnectTSActivity.class); |
||||
} else if (Device.getInstance().deviceType == DeviceTypeEnum.DEVICE_TYPE_LEVEL) { |
||||
intent = new Intent(ActivityUtils.getTopActivity(), ConnectLevelActivity.class); |
||||
} else { |
||||
intent = new Intent(ActivityUtils.getTopActivity(), ConnectRtkActivity.class); |
||||
} |
||||
intent.putExtra("customChannel", AppChannel.customChannel); |
||||
ActivityUtils.getTopActivity().startActivity(intent); |
||||
} |
||||
} |
||||
} |
||||
|
||||
private void chooseInstrumentType() { |
||||
new MaterialDialog.Builder(ActivityUtils.getTopActivity()) |
||||
.title(R.string.choose_instrument_type) |
||||
.items(new String[]{ActivityUtils.getTopActivity().getString(R.string.total_station), ActivityUtils.getTopActivity().getString(R.string.device_type_level)}) |
||||
.itemsCallback(new MaterialDialog.ListCallback() { |
||||
@Override |
||||
public void onSelection(MaterialDialog dialog, View itemView, int which, CharSequence text) { |
||||
switch (which) { |
||||
case 0: |
||||
Intent intent = new Intent(ActivityUtils.getTopActivity(), ConnectTSActivity.class); |
||||
intent.putExtra("customChannel", AppChannel.customChannel); |
||||
ActivityUtils.getTopActivity().startActivity(intent); |
||||
break; |
||||
case 1: |
||||
Intent intent2 = new Intent(ActivityUtils.getTopActivity(), ConnectLevelActivity.class); |
||||
intent2.putExtra("customChannel", AppChannel.customChannel); |
||||
ActivityUtils.getTopActivity().startActivity(intent2); |
||||
break; |
||||
} |
||||
} |
||||
}).show(); |
||||
} |
||||
|
||||
|
||||
/** |
||||
* 开启wifi通信 |
||||
*/ |
||||
private void startHotspotComm() { |
||||
if (!ValidateUtil.isIPAddress(TsConfig.getInstance().getIp())) { |
||||
ToastUtils.showShort(R.string.please_input_correct_ip); |
||||
return; |
||||
} |
||||
if (TsConfig.getInstance().getPort() < 1024 || TsConfig.getInstance().getPort() > 65535) { |
||||
ToastUtils.showShort(R.string.please_input_correct_port); |
||||
return; |
||||
} |
||||
if (DeviceUtil.isWifiApOpen()) { |
||||
ServiceUtils.stopService(EmulatorService.class); |
||||
ServiceUtils.stopService(LocationService.class); |
||||
ServiceUtils.stopService(NativePositioningService.class); |
||||
ServiceUtils.stopService(BTService.class); |
||||
ServiceUtils.stopService(BleService.class); |
||||
ServiceUtils.startService(TsSocketService.class); |
||||
ThreadPoolUtil.execute(new Runnable() { |
||||
@Override |
||||
public void run() { |
||||
Device.getInstance().requestConnect(); |
||||
} |
||||
}, 200); |
||||
} else { |
||||
ToastUtils.showShort(R.string.please_open_hotspot_first); |
||||
//打开网络共享与热点设置页面
|
||||
if (RomUtil.isOppo() || RomUtil.isLenove() || RomUtil.isGionee()) { |
||||
//OPPO系统系统特殊,会让在Manifest.xml声明Settings$TetherSettingsActivity,现在让用户自己找热点界面,并开启
|
||||
ToastUtils.showShort(R.string.find_tether_setting_and_open); |
||||
ActivityUtils.getTopActivity().startActivity(new Intent(Settings.ACTION_SETTINGS)); |
||||
} else { |
||||
Intent intent = new Intent(); |
||||
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); |
||||
ComponentName comp = new ComponentName("com.android.settings", "com.android.settings.Settings$TetherSettingsActivity"); |
||||
intent.setComponent(comp); |
||||
ActivityUtils.getTopActivity().startActivity(intent); |
||||
} |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,250 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import android.annotation.SuppressLint; |
||||
import android.content.Intent; |
||||
import android.graphics.Bitmap; |
||||
import android.net.Uri; |
||||
import android.os.Bundle; |
||||
import android.text.TextUtils; |
||||
import android.util.Log; |
||||
import android.view.KeyEvent; |
||||
import android.view.Menu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.webkit.WebResourceRequest; |
||||
import android.webkit.WebView; |
||||
import android.widget.LinearLayout; |
||||
import android.widget.TextView; |
||||
|
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import com.bingce.data.sync.utils.LeanCloudConfigLoader; |
||||
import com.bingce.utils.ClipboardUtils; |
||||
import com.bingce.utils.StringUtil; |
||||
import com.just.agentweb.AgentWeb; |
||||
import com.just.agentweb.DefaultWebClient; |
||||
import com.just.agentweb.WebChromeClient; |
||||
import com.just.agentweb.WebViewClient; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
/** |
||||
* Created by cenxiaozhong on 2017/5/26. |
||||
* <p> |
||||
* source code https://github.com/Justson/AgentWeb
|
||||
*/ |
||||
|
||||
public class NotificationActivity extends ColorfulActivity { |
||||
protected AgentWeb mAgentWeb; |
||||
private LinearLayout mLinearLayout; |
||||
private Toolbar mToolbar; |
||||
private TextView mTitleTextView; |
||||
|
||||
@SuppressLint("SourceLockedOrientationActivity") |
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
setContentView(R.layout.activity_agentweb_base); |
||||
|
||||
mLinearLayout = this.findViewById(R.id.container); |
||||
mToolbar = this.findViewById(R.id.toolbar); |
||||
mToolbar.setTitle(""); |
||||
mToolbar.setNavigationIcon(R.mipmap.icon_close_x); |
||||
mTitleTextView = this.findViewById(R.id.toolbar_title); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
mToolbar.setNavigationOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
finish(); |
||||
} |
||||
}); |
||||
|
||||
mAgentWeb = AgentWeb.with(this) |
||||
.setAgentWebParent(mLinearLayout, new LinearLayout.LayoutParams(-1, -1)) |
||||
.useDefaultIndicator() |
||||
.setWebChromeClient(mWebChromeClient) |
||||
.setWebViewClient(mWebViewClient) |
||||
.setMainFrameErrorView(R.layout.agentweb_error_page, -1) |
||||
.setSecurityType(AgentWeb.SecurityType.STRICT_CHECK) |
||||
.setOpenOtherPageWays(DefaultWebClient.OpenOtherPageWays.ASK)//打开其他应用时,弹窗咨询用户是否前往其他应用
|
||||
.interceptUnkownUrl() //拦截找不到相关页面的Scheme
|
||||
.createAgentWeb() |
||||
.ready() |
||||
.go(getUrl()); |
||||
|
||||
mAgentWeb.getWebCreator().getWebView().getSettings().setSupportZoom(true); |
||||
mAgentWeb.getWebCreator().getWebView().getSettings().setBuiltInZoomControls(true); |
||||
mAgentWeb.getWebCreator().getWebView().getSettings().setDisplayZoomControls(false); |
||||
mAgentWeb.getWebCreator().getWebView().getSettings().setUseWideViewPort(true); |
||||
|
||||
LeanCloudConfigLoader.findInBackground("notificationUrl", instance -> { |
||||
// new LCQuery<>("Configuration")
|
||||
// .whereEqualTo("name", "notificationUrl")
|
||||
// .limit(1)
|
||||
// .findInBackground().subscribe(new Observer<List<LCObject>>() {
|
||||
// @Override
|
||||
// public void onSubscribe(Disposable d) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onNext(List<LCObject> avObjects) {
|
||||
if (isFinishing()) return; |
||||
if (/*avObjects != null && !avObjects.isEmpty() && avObjects.get(0).getString("value") != null*/instance != null && StringUtil.isNotEmpty(instance.value)) { |
||||
String url = /*avObjects.get(0).getString("value")*/instance.value; |
||||
mAgentWeb.getUrlLoader().loadUrl(url); |
||||
} else { |
||||
mAgentWeb.getUrlLoader().loadUrl("https://www.bingce.com"); |
||||
} |
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onError(Throwable e) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onComplete() {
|
||||
//
|
||||
// }
|
||||
}); |
||||
} |
||||
|
||||
private final WebViewClient mWebViewClient = new WebViewClient() { |
||||
@Override |
||||
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) { |
||||
return super.shouldOverrideUrlLoading(view, request); |
||||
} |
||||
|
||||
@Override |
||||
public void onPageStarted(WebView view, String url, Bitmap favicon) { |
||||
//do you work
|
||||
Log.i("Info", "AgentWebActivity onPageStarted"); |
||||
} |
||||
}; |
||||
private final WebChromeClient mWebChromeClient = new WebChromeClient() { |
||||
@Override |
||||
public void onReceivedTitle(WebView view, String title) { |
||||
super.onReceivedTitle(view, title); |
||||
if (mTitleTextView != null) { |
||||
mTitleTextView.setText(title); |
||||
} |
||||
} |
||||
}; |
||||
|
||||
public String getUrl() { |
||||
return null; |
||||
} |
||||
|
||||
@Override |
||||
public boolean onCreateOptionsMenu(Menu menu) { |
||||
getMenuInflater().inflate(R.menu.menu_activity_agentweb, menu); |
||||
return super.onCreateOptionsMenu(menu); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
switch (item.getItemId()) { |
||||
case android.R.id.home: |
||||
// true表示AgentWeb处理了该事件
|
||||
if (!mAgentWeb.back()) { |
||||
finish(); |
||||
} |
||||
break; |
||||
case R.id.refresh: |
||||
if (mAgentWeb != null) { |
||||
mAgentWeb.getUrlLoader().reload(); // 刷新
|
||||
} |
||||
break; |
||||
case R.id.copy_url: |
||||
if (mAgentWeb != null) { |
||||
ClipboardUtils.copyText(mAgentWeb.getWebCreator().getWebView().getUrl()); |
||||
ToastUtils.showShort(R.string.copy_success); |
||||
} |
||||
break; |
||||
case R.id.clean: |
||||
toCleanWebCache(); |
||||
break; |
||||
case R.id.open_with_broswer: |
||||
if (mAgentWeb != null) { |
||||
openBrowser(mAgentWeb.getWebCreator().getWebView().getUrl()); |
||||
} |
||||
break; |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onKeyDown(int keyCode, KeyEvent event) { |
||||
if (mAgentWeb.handleKeyEvent(keyCode, event)) { |
||||
return true; |
||||
} |
||||
return super.onKeyDown(keyCode, event); |
||||
} |
||||
|
||||
@Override |
||||
protected void onPause() { |
||||
mAgentWeb.getWebLifeCycle().onPause(); |
||||
super.onPause(); |
||||
|
||||
} |
||||
|
||||
@Override |
||||
protected void onResume() { |
||||
mAgentWeb.getWebLifeCycle().onResume(); |
||||
super.onResume(); |
||||
} |
||||
|
||||
@Override |
||||
protected void onActivityResult(int requestCode, int resultCode, Intent data) { |
||||
Log.i("Info", "onResult:" + requestCode + " onResult:" + resultCode); |
||||
super.onActivityResult(requestCode, resultCode, data); |
||||
} |
||||
|
||||
|
||||
@Override |
||||
protected void onDestroy() { |
||||
super.onDestroy(); |
||||
//mAgentWeb.destroy();
|
||||
mAgentWeb.getWebLifeCycle().onDestroy(); |
||||
} |
||||
|
||||
/** |
||||
* 清除 WebView 缓存 |
||||
*/ |
||||
private void toCleanWebCache() { |
||||
if (this.mAgentWeb != null) { |
||||
//清理所有跟WebView相关的缓存 ,数据库, 历史记录 等。
|
||||
this.mAgentWeb.clearWebCache(); |
||||
ToastUtils.showShort("已清理缓存"); |
||||
//清空所有 AgentWeb 硬盘缓存,包括 WebView 的缓存 , AgentWeb 下载的图片 ,视频 ,apk 等文件。
|
||||
// AgentWebConfig.clearDiskCache(this.getContext());
|
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 打开浏览器 |
||||
* |
||||
* @param targetUrl 外部浏览器打开的地址 |
||||
*/ |
||||
private void openBrowser(String targetUrl) { |
||||
if (TextUtils.isEmpty(targetUrl) || targetUrl.startsWith("file://")) { |
||||
ToastUtils.showShort(targetUrl + " 该链接无法使用浏览器打开。"); |
||||
return; |
||||
} |
||||
Intent intent = new Intent(); |
||||
intent.setAction("android.intent.action.VIEW"); |
||||
Uri mUri = Uri.parse(targetUrl); |
||||
intent.setData(mUri); |
||||
startActivity(intent); |
||||
} |
||||
|
||||
} |
@ -0,0 +1,198 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
|
||||
import android.annotation.SuppressLint; |
||||
import android.content.DialogInterface; |
||||
import android.content.Intent; |
||||
import android.content.pm.ActivityInfo; |
||||
import android.os.Bundle; |
||||
import android.view.MenuItem; |
||||
import android.view.WindowManager; |
||||
|
||||
import androidx.appcompat.app.AlertDialog; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
import androidx.fragment.app.Fragment; |
||||
import androidx.preference.ListPreference; |
||||
import androidx.preference.PreferenceFragmentCompat; |
||||
import androidx.preference.SwitchPreferenceCompat; |
||||
|
||||
import com.bingce.AppChannel; |
||||
import com.bingce.controlapphelper.surveyor.surveyor.ISurveyorConstants; |
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.controller.KeyEventAction; |
||||
|
||||
import org.polaric.colorful.ColorPickerPreference; |
||||
import org.polaric.colorful.Colorful; |
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
/** |
||||
* 设置页面 |
||||
*/ |
||||
public class SettingsActivity extends ColorfulActivity { |
||||
private Toolbar mToolbar; |
||||
|
||||
@SuppressLint("SourceLockedOrientationActivity") |
||||
@Override |
||||
protected void onCreate(Bundle savedInstanceState) { |
||||
App app = App.getApp(); |
||||
if (app.isLandscape()) { |
||||
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR_LANDSCAPE); |
||||
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN); |
||||
} else { |
||||
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); |
||||
getWindow().clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); |
||||
} |
||||
super.onCreate(savedInstanceState); |
||||
setContentView(R.layout.activity_settings); |
||||
mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
if (savedInstanceState == null) { |
||||
getSupportFragmentManager().beginTransaction() |
||||
.add(R.id.activity_settings_content, createSettingFragment()) |
||||
.commit(); |
||||
} |
||||
} |
||||
|
||||
private Fragment createSettingFragment() { |
||||
return new SettingsFragment(); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
finish(); |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
public static class SettingsFragment extends PreferenceFragmentCompat { |
||||
private SwitchPreferenceCompat nightModePrefs; |
||||
private SwitchPreferenceCompat isOpenAtr; |
||||
private ColorPickerPreference themePrimaryColor, themeAccentColor; |
||||
|
||||
private ListPreference volume_plus_prefs, volume_minus_prefs; |
||||
|
||||
@Override |
||||
public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { |
||||
setPreferencesFromResource(R.xml.prefs, rootKey); |
||||
|
||||
nightModePrefs = findPreference("key_is_night_mode"); |
||||
themePrimaryColor = findPreference("key_theme_primary_color"); |
||||
themeAccentColor = findPreference("key_theme_accent_color"); |
||||
|
||||
|
||||
volume_plus_prefs = findPreference("key_volume_plus_function"); |
||||
volume_minus_prefs = findPreference("key_volume_minus_function"); |
||||
|
||||
volume_plus_prefs.setSummary(volume_plus_prefs.getEntry()); |
||||
volume_minus_prefs.setSummary(volume_minus_prefs.getEntry()); |
||||
|
||||
isOpenAtr = findPreference("key_is_open_atr"); |
||||
|
||||
nightModePrefs.setOnPreferenceChangeListener((preference, newValue) -> { |
||||
Colorful.config(App.getApp()).dark((Boolean) newValue).apply(); |
||||
new AlertDialog.Builder(getActivity()) |
||||
.setMessage(R.string.please_restart_to_apply_new_theme) |
||||
.setPositiveButton(R.string.confirm, null) |
||||
.setOnDismissListener(dialogInterface -> { |
||||
Intent intent = new Intent(); |
||||
intent.putExtra("isThemeChanged", true); |
||||
getActivity().setResult(RESULT_OK, intent); |
||||
getActivity().finish(); |
||||
}).show(); |
||||
return true; |
||||
}); |
||||
|
||||
|
||||
//主色
|
||||
themePrimaryColor.setOnPreferenceChangeListener((preference, newValue) -> { |
||||
new AlertDialog.Builder(getActivity()) |
||||
.setMessage(R.string.please_restart_to_apply_new_theme) |
||||
.setPositiveButton(R.string.confirm, null) |
||||
.setOnDismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialogInterface) { |
||||
Intent intent = new Intent(); |
||||
intent.putExtra("isThemeChanged", true); |
||||
getActivity().setResult(RESULT_OK, intent); |
||||
getActivity().finish(); |
||||
} |
||||
}).show(); |
||||
return true; |
||||
}); |
||||
//配色
|
||||
themeAccentColor.setOnPreferenceChangeListener((preference, newValue) -> { |
||||
new AlertDialog.Builder(getActivity()) |
||||
.setMessage(R.string.please_restart_to_apply_new_theme) |
||||
.setPositiveButton(R.string.confirm, null) |
||||
.setOnDismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialogInterface) { |
||||
Intent intent = new Intent(); |
||||
intent.putExtra("isThemeChanged", true); |
||||
getActivity().setResult(RESULT_OK, intent); |
||||
getActivity().finish(); |
||||
} |
||||
}).show(); |
||||
return true; |
||||
}); |
||||
|
||||
volume_plus_prefs.setOnPreferenceChangeListener((preference, newValue) -> { |
||||
setKeyEvent(newValue, volume_plus_prefs); |
||||
return true; |
||||
}); |
||||
volume_minus_prefs.setOnPreferenceChangeListener((preference, newValue) -> { |
||||
setKeyEvent(newValue, volume_minus_prefs); |
||||
return true; |
||||
}); |
||||
|
||||
isOpenAtr.setOnPreferenceChangeListener((preference, newValue) -> { |
||||
ISurveyorConstants.isOpenAtr = (boolean) newValue; |
||||
return true; |
||||
}); |
||||
|
||||
if (AppChannel.customChannel != AppChannel.CUSTOM_CONTROL_PUBLIC) { |
||||
//主配色隐藏
|
||||
themePrimaryColor.setVisible(false); |
||||
themeAccentColor.setVisible(false); |
||||
} |
||||
|
||||
} |
||||
|
||||
private void setKeyEvent(Object newValue, ListPreference volume_minus_prefs) { |
||||
switch (String.valueOf(newValue)) { |
||||
case KeyEventAction.NONE: |
||||
volume_minus_prefs.setSummary("无"); |
||||
break; |
||||
case KeyEventAction.CAL: |
||||
volume_minus_prefs.setSummary("计算"); |
||||
break; |
||||
case KeyEventAction.SURVEY: |
||||
volume_minus_prefs.setSummary("观测"); |
||||
break; |
||||
case KeyEventAction.RECORD: |
||||
volume_minus_prefs.setSummary("记录"); |
||||
break; |
||||
case KeyEventAction.LAST: |
||||
volume_minus_prefs.setSummary("上一点"); |
||||
break; |
||||
case KeyEventAction.NEXT: |
||||
volume_minus_prefs.setSummary("下一点"); |
||||
break; |
||||
case KeyEventAction.SURVEY_NO_SEND: |
||||
volume_minus_prefs.setSummary("观测后不发送结果"); |
||||
break; |
||||
case KeyEventAction.SURVEY_AND_RECORD: |
||||
volume_minus_prefs.setSummary("观测并记录"); |
||||
break; |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
|
||||
} |
@ -0,0 +1,231 @@ |
||||
package com.bingce.controlnetwork.activity; |
||||
|
||||
import static com.king.app.updater.util.AppUtils.getPackageInfo; |
||||
|
||||
import android.annotation.SuppressLint; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.util.Log; |
||||
|
||||
import androidx.annotation.Nullable; |
||||
|
||||
import com.bingce.file.FileOperator; |
||||
import com.bingce.path.PathManager; |
||||
import com.bingce.utils.NetworkUtil; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
import com.bingce.zip.ZipUtil; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.io.File; |
||||
import java.io.FileNotFoundException; |
||||
import java.text.SimpleDateFormat; |
||||
import java.util.ArrayList; |
||||
import java.util.Arrays; |
||||
import java.util.Date; |
||||
import java.util.List; |
||||
import java.util.Locale; |
||||
|
||||
import cn.leancloud.LCFile; |
||||
import cn.leancloud.LCObject; |
||||
import cn.leancloud.LCQuery; |
||||
|
||||
import com.bingce.controlnetwork.databinding.ActivitySplashBinding; |
||||
|
||||
/** |
||||
* 欢迎页 |
||||
*/ |
||||
@SuppressLint("CustomSplashScreen") |
||||
public class SplashActivity extends ColorfulActivity { |
||||
|
||||
private static final String CODE_NO_UPLOAD = "0"; |
||||
private static final String CODE_UPLOAD_COMPARE_SMALL_WITH_FIRST = "1"; |
||||
private static final String CODE_UPLOAD_COMPARE_SMALL_WITHOUT_FIRST = "2"; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
// getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
|
||||
ActivitySplashBinding binding = ActivitySplashBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
startCopyDbFileToCache(); |
||||
} |
||||
|
||||
private void startCopyDbFileToCache() { |
||||
ThreadPoolUtil.execute(() -> { |
||||
try { |
||||
File copyFolder = PathManager.appDocumentFolder(); |
||||
File[] files = copyFolder.listFiles(); |
||||
List<File> collectFileList = null; |
||||
if (files != null) { |
||||
collectFileList = new ArrayList<>(Arrays.asList(files)); |
||||
} |
||||
|
||||
if (collectFileList != null && !collectFileList.isEmpty()) { |
||||
|
||||
SimpleDateFormat simple = new SimpleDateFormat("yyyyMMddHHmmss", Locale.getDefault()); |
||||
String fileName = "导线助手数据备份_" + "_" + getVersionName() + "_" + simple.format(new Date()); |
||||
File zipTartFile = new File(copyFolder, fileName + ".zip"); |
||||
boolean zip = ZipUtil.zip(zipTartFile, collectFileList); |
||||
|
||||
if (zip) { |
||||
//获取上一次备份的文件
|
||||
File lastFile = getBeforeTargetFile(targetFolder()); |
||||
//备份文件
|
||||
File targetFile = new File(targetFolder().getAbsolutePath(), fileName); |
||||
boolean isCopySuccess = FileOperator.copyFile(zipTartFile.getAbsolutePath(), targetFile.getAbsolutePath()); |
||||
//无论备份成功或者失败都删除压缩后的文件
|
||||
zipTartFile.delete(); |
||||
if (isCopySuccess) { |
||||
//delete多余文件
|
||||
deleteRemainCacheFile(lastFile, targetFile); |
||||
|
||||
if (NetworkUtil.isNetworkAvailable(SplashActivity.this)) { |
||||
String code = queryUploadConfig(); |
||||
checkUpload(code, lastFile, targetFile); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
} catch (Exception e) { |
||||
e.printStackTrace(); |
||||
} finally { |
||||
goMainActivity(); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
/** |
||||
* 文件个数大于3就删除 |
||||
* |
||||
* @param lastFile |
||||
* @param targetFile |
||||
*/ |
||||
private void deleteRemainCacheFile(File lastFile, File targetFile) { |
||||
File file = targetFolder(); |
||||
if (file != null) { |
||||
File[] files = file.listFiles(); |
||||
if (files != null && files.length > 3) { |
||||
File deleteFile = null; |
||||
for (File fileEach : files) { |
||||
String eachName = fileEach.getName(); |
||||
if (eachName.equals(getFileName(lastFile)) || eachName.equals(getFileName(targetFile))) { |
||||
continue; |
||||
} |
||||
if (deleteFile != null && deleteFile.lastModified() > fileEach.lastModified()) { |
||||
deleteFile = fileEach; |
||||
} |
||||
if (deleteFile == null) { |
||||
deleteFile = fileEach; |
||||
} |
||||
} |
||||
if (deleteFile != null) { |
||||
deleteFile.delete(); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
private String getFileName(File file) { |
||||
if (file != null) { |
||||
return file.getName(); |
||||
} |
||||
return null; |
||||
} |
||||
|
||||
/** |
||||
* 导线助手是否自动上传可能错误的数据库 |
||||
* 0.不上传 |
||||
* 1.比上次小就上传上次备份数据;但是如果是首次备份,也将该备份上传 |
||||
* 2.比上次小就上传上次备份数据;如果是首次备份,不会将该备份上传 |
||||
*/ |
||||
private void checkUpload(String code, File lastFile, File targetFile) throws FileNotFoundException { |
||||
if (CODE_NO_UPLOAD.equals(code)) { |
||||
//不上传
|
||||
} else if (CODE_UPLOAD_COMPARE_SMALL_WITH_FIRST.equals(code)) { |
||||
if (compareSmall(lastFile, targetFile)) { |
||||
uploadFile(lastFile); |
||||
} else if (lastFile == null) { |
||||
uploadFile(targetFile); |
||||
} |
||||
} else if (CODE_UPLOAD_COMPARE_SMALL_WITHOUT_FIRST.equals(code) && compareSmall(lastFile, targetFile)) { |
||||
uploadFile(lastFile); |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 是否比上次小 |
||||
* |
||||
* @param lastFile |
||||
* @param targetFile |
||||
* @return |
||||
*/ |
||||
private boolean compareSmall(File lastFile, File targetFile) { |
||||
return lastFile != null && targetFile.length() < lastFile.length() / 2; |
||||
} |
||||
|
||||
/** |
||||
* 获取上次备份的文件 |
||||
* |
||||
* @param fileFolder |
||||
* @return |
||||
*/ |
||||
private File getBeforeTargetFile(File fileFolder) { |
||||
File targetFile = null; |
||||
if (fileFolder != null) { |
||||
File[] files = fileFolder.listFiles(); |
||||
if (files != null) { |
||||
for (File eachFile : files) { |
||||
if (targetFile == null || targetFile.lastModified() < eachFile.lastModified()) { |
||||
targetFile = eachFile; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
return targetFile; |
||||
} |
||||
|
||||
/** |
||||
* 上传leanCloud文件 |
||||
*/ |
||||
private void uploadFile(File zipTartFile) throws FileNotFoundException { |
||||
Log.d("hwhw", "数据库备份文件上传LeanCloud"); |
||||
LCFile lcFile = LCFile.withAbsoluteLocalPath(zipTartFile.getName(), zipTartFile.getAbsolutePath()); |
||||
lcFile.save(); |
||||
} |
||||
|
||||
private void goMainActivity() { |
||||
startActivity(new Intent(this, MainActivity.class)); |
||||
finish(); |
||||
} |
||||
|
||||
|
||||
public File targetFolder() { |
||||
File cacheFolder = getCacheDir(); |
||||
File targetFolder = new File(cacheFolder, "dbBackUp"); |
||||
if (!targetFolder.exists()) { |
||||
targetFolder.mkdirs(); |
||||
} |
||||
return targetFolder; |
||||
} |
||||
|
||||
private String getVersionName() { |
||||
try { |
||||
return getPackageInfo(this).versionName; |
||||
} catch (Exception e) { |
||||
e.printStackTrace(); |
||||
} |
||||
return ""; |
||||
} |
||||
|
||||
private String queryUploadConfig() { |
||||
List<LCObject> avObjects = new LCQuery<>("Configuration").whereEqualTo("name", "ControlAppAutoUploadErrorDatabase") |
||||
.limit(1).find(); |
||||
if (avObjects != null && !avObjects.isEmpty() && avObjects.get(0).getString("value") != null) { |
||||
return avObjects.get(0).getString("value"); |
||||
} |
||||
return CODE_NO_UPLOAD; |
||||
} |
||||
|
||||
} |
@ -0,0 +1,266 @@ |
||||
package com.bingce.controlnetwork.activity.backup; |
||||
|
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Build; |
||||
import android.os.Bundle; |
||||
import android.util.Log; |
||||
import android.view.View; |
||||
import android.view.WindowManager; |
||||
import android.widget.Button; |
||||
|
||||
import androidx.annotation.Nullable; |
||||
import androidx.annotation.WorkerThread; |
||||
import androidx.appcompat.widget.AppCompatTextView; |
||||
|
||||
import com.afollestad.materialdialogs.MaterialDialog; |
||||
import com.bingce.controlapphelper.datasource.database.SurveyorDataBase; |
||||
import com.bingce.controlapphelper.util.CheckStorageUtil; |
||||
import com.bingce.controlapphelper.util.Tools; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityExportLayoutBinding; |
||||
import com.bingce.file.DownloadFileWriter; |
||||
import com.bingce.file.FileOperator; |
||||
import com.bingce.path.PathManager; |
||||
import com.bingce.utils.AsynchronousHelper; |
||||
import com.bingce.utils.FileUtil; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
import com.bingce.zip.ZipUtil; |
||||
import com.github.ybq.android.spinkit.SpinKitView; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.io.File; |
||||
import java.text.SimpleDateFormat; |
||||
import java.util.ArrayList; |
||||
import java.util.Date; |
||||
import java.util.List; |
||||
import java.util.Locale; |
||||
|
||||
import blankj.utilcode.util.StringUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
public abstract class AbstractBackupExportActivity extends ColorfulActivity implements AsynchronousHelper.IDelegate { |
||||
|
||||
public static final String BACKUP_NAME = "导线助手数据"; |
||||
public static final String FOLDER_DADA_DATABASES = "dada_databases"; |
||||
public static final String FOLDER_DATA_FILE_PROJECT = "data_file_project"; |
||||
public static final String FOLDER_ANDROID = "android"; |
||||
public static final String FOLDER_SDCARD = "sdcard"; |
||||
public static final String BACKUP_TXT = "backup.txt"; |
||||
|
||||
|
||||
private final AsynchronousHelper asynchronousHelper = new AsynchronousHelper(this); |
||||
private File zipFile = null; |
||||
|
||||
protected abstract String tipsString(); |
||||
|
||||
private ActivityExportLayoutBinding binding; |
||||
|
||||
@Override |
||||
final protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityExportLayoutBinding.inflate(getLayoutInflater()); |
||||
getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS); |
||||
setContentView(binding.getRoot()); |
||||
binding.shareButton.setOnClickListener(v -> doCollect()); |
||||
binding.progressText.setText(tipsString()); |
||||
} |
||||
|
||||
protected abstract String applicationId(); |
||||
|
||||
protected abstract String zipFileName(String dateString, String projectName); |
||||
|
||||
private void doCollect() { |
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { //如果是>=Q版本,不需要申请权限
|
||||
doExport(); |
||||
} else { //如果是低于Q版本,则先申请存储权限
|
||||
//检测是否有写权限
|
||||
requestStoragePermission(); |
||||
} |
||||
} |
||||
|
||||
public void requestStoragePermission() { |
||||
CheckStorageUtil.check(this, this::doExport); |
||||
} |
||||
|
||||
private void doExport() { |
||||
if (zipFile == null) { |
||||
startCollect(); |
||||
} else { |
||||
FileOperator.shareFile(this, zipFile, /*BuildConfig.APPLICATION_ID*/applicationId()); |
||||
} |
||||
} |
||||
|
||||
private void startCollect() { |
||||
//
|
||||
binding.progressText.setText(""); |
||||
asynchronousHelper.start(); |
||||
binding.shareButton.setEnabled(false); |
||||
binding.spinKit.setVisibility(View.VISIBLE); |
||||
binding.tvCompleted.setVisibility(View.GONE); |
||||
ThreadPoolUtil.execute(() -> { |
||||
|
||||
File packageFile = getFilesDir().getParentFile(); |
||||
|
||||
//1
|
||||
File database1 = new File(packageFile, "databases"); |
||||
File[] files = database1.listFiles(); |
||||
List<File> dataDatabasesFiles = getDbListFiles(files); |
||||
//2
|
||||
File file2 = new File(PathManager.appFolder(), "NOPROJECT"); |
||||
File[] files2 = file2.listFiles(); |
||||
List<File> dataProjectFiles = getDbListFiles(files2); |
||||
//3
|
||||
File file3 = PathManager.appDocumentFolder(); |
||||
File[] files3 = file3.listFiles(); |
||||
List<File> androidFiles = getDbListFiles(files3); |
||||
//4
|
||||
File file4 = new File(FileUtil.getSDPath(), "导线助手"); |
||||
File[] files4 = file4.listFiles(); |
||||
List<File> sdFiles = getDbListFiles(files4); |
||||
|
||||
File fileTargetP = new File(PathManager.appCacheFolder(this), BACKUP_NAME); |
||||
FileUtil.deleteDir(fileTargetP); |
||||
|
||||
File fileTxt = new File(fileTargetP, "backup.txt"); |
||||
FileUtil.writeString(FOLDER_ANDROID, fileTxt); |
||||
|
||||
copyFile(dataDatabasesFiles, new File(fileTargetP, FOLDER_DADA_DATABASES)); |
||||
copyFile(dataProjectFiles, new File(fileTargetP, FOLDER_DATA_FILE_PROJECT)); |
||||
copyFile(androidFiles, new File(fileTargetP, FOLDER_ANDROID)); |
||||
copyFile(sdFiles, new File(fileTargetP, FOLDER_SDCARD)); |
||||
|
||||
SimpleDateFormat simple = new SimpleDateFormat("yyyyMMddHHmmss", Locale.getDefault()); |
||||
String fileName = zipFileName(simple.format(new Date()), ""); |
||||
File target = new File(fileTargetP, fileName + ".zip"); |
||||
List<File> list = new ArrayList<>(); |
||||
list.add(fileTargetP); |
||||
boolean zip = ZipUtil.zip(target, list); |
||||
Log.d("hwhw", "备份是否ok" + zip); |
||||
if (zip) { |
||||
zipFile = target; |
||||
} |
||||
asynchronousHelper.completed(); |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onBackPressed() { |
||||
if (asynchronousHelper.isWorking()) { |
||||
ToastUtils.showShort("数据收集中,请稍候。"); |
||||
return; |
||||
} |
||||
super.onBackPressed(); |
||||
} |
||||
|
||||
public static void start(Context context, Class<? extends AbstractBackupExportActivity> clz) { |
||||
start(context, clz, null); |
||||
} |
||||
|
||||
private static final String KEY_PROJECT_NAME = "key_project_name"; |
||||
|
||||
public static void start(Context context, Class<? extends AbstractBackupExportActivity> clz, String projectName) { |
||||
Intent intent = new Intent(context, clz); |
||||
if (!StringUtils.isEmpty(projectName)) { |
||||
intent.putExtra(KEY_PROJECT_NAME, projectName); |
||||
} |
||||
context.startActivity(intent); |
||||
} |
||||
|
||||
@Override |
||||
public void onUpdateProgress(String msg) { |
||||
String string = binding.progressText.getText().toString(); |
||||
binding.progressText.setText(string + "\n" + msg); |
||||
binding.scrollView.post(() -> binding.scrollView.fullScroll(View.FOCUS_DOWN)); |
||||
} |
||||
|
||||
@Override |
||||
public void onCompleted() { |
||||
if (zipFile == null) { |
||||
return; |
||||
} |
||||
if (isDestroyed() || isFinishing()) { |
||||
return; |
||||
} |
||||
Button shareButton = findViewById(R.id.share_button); |
||||
if (shareButton != null) { |
||||
shareButton.setEnabled(true); |
||||
shareButton.setText(R.string.share); |
||||
} |
||||
SpinKitView spinKitView = findViewById(R.id.spin_kit); |
||||
if (spinKitView != null) { |
||||
spinKitView.setVisibility(View.INVISIBLE); |
||||
} |
||||
AppCompatTextView completeTv = findViewById(R.id.tv_completed); |
||||
if (completeTv != null) { |
||||
completeTv.setText(Tools.getString(R.string.collection_completed)); |
||||
completeTv.setVisibility(View.VISIBLE); |
||||
} |
||||
//将文件存储到download中
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { |
||||
String tipsString; |
||||
if (DownloadFileWriter.writeHigherQ(this, zipFile)) { |
||||
tipsString = "数据备份完毕,存储在根目录「Download\\" + zipFile.getName() + "」压缩包中."; |
||||
} else { |
||||
tipsString = "数据备份完毕,请存放到安全位置以便日后恢复."; |
||||
} |
||||
//弾框提示
|
||||
showDialog(this, applicationId(), tipsString, zipFile); |
||||
} else { |
||||
File resultFile = DownloadFileWriter.writeLowerQ(zipFile); |
||||
String tipsString; |
||||
if (resultFile != null) { |
||||
tipsString = "数据备份完毕,存储在「" + resultFile.getAbsolutePath() + "」压缩包中."; |
||||
} else { |
||||
tipsString = "数据备份完毕,请存放到安全位置以便日后恢复."; |
||||
} |
||||
showDialog(this, applicationId(), tipsString, zipFile); |
||||
} |
||||
} |
||||
|
||||
private static void showDialog(Context context, String applicationId, String title, File zipFile) { |
||||
//弾框提示
|
||||
new MaterialDialog.Builder(context).title(Tools.getString(R.string.notice)) |
||||
.content(title) |
||||
.positiveText(R.string.send_to) |
||||
.negativeText(R.string.cancel) |
||||
.cancelable(false) |
||||
.onPositive((dialog, which) -> FileOperator.shareFile(context, zipFile, /*BuildConfig.APPLICATION_ID*/applicationId)) |
||||
.show(); |
||||
} |
||||
|
||||
|
||||
/** |
||||
* 筛选出需要的db文件 |
||||
* |
||||
* @param files |
||||
* @return |
||||
*/ |
||||
@WorkerThread |
||||
private List<File> getDbListFiles(File[] files) { |
||||
List<File> fileList = new ArrayList<>(); |
||||
if (files != null) { |
||||
for (File file : files) { |
||||
if (file.getName().contains(SurveyorDataBase.DB_NAME)) { |
||||
fileList.add(file); |
||||
} |
||||
} |
||||
} |
||||
return fileList; |
||||
} |
||||
|
||||
@WorkerThread |
||||
private void copyFile(List<File> files, File targetFile) { |
||||
if (files != null && !files.isEmpty()) { |
||||
if (!targetFile.exists()) { |
||||
targetFile.mkdirs(); |
||||
} |
||||
|
||||
for (File file : files) { |
||||
FileOperator.copyFile(file.getAbsolutePath(), targetFile.getAbsolutePath() + File.separator + file.getName()); |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
@ -0,0 +1,30 @@ |
||||
package com.bingce.controlnetwork.activity.backup; |
||||
|
||||
import blankj.utilcode.util.StringUtils; |
||||
|
||||
import com.bingce.controlnetwork.BuildConfig; |
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
public class BackupExportActivity extends AbstractBackupExportActivity { |
||||
@Override |
||||
protected String tipsString() { |
||||
return getString(R.string.back_up_data_tips); |
||||
} |
||||
|
||||
@Override |
||||
protected String applicationId() { |
||||
return BuildConfig.APPLICATION_ID; |
||||
} |
||||
|
||||
@Override |
||||
protected String zipFileName(String dateString, String projectName) { |
||||
StringBuilder stringBuilder = new StringBuilder(BACKUP_NAME); |
||||
if (!StringUtils.isEmpty(projectName)) { |
||||
stringBuilder.append("[") |
||||
.append(projectName) |
||||
.append("]"); |
||||
} |
||||
stringBuilder.append(dateString); |
||||
return stringBuilder.toString(); |
||||
} |
||||
} |
@ -0,0 +1,45 @@ |
||||
package com.bingce.controlnetwork.activity.backup.launch; |
||||
|
||||
import android.app.Activity; |
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
|
||||
import androidx.activity.result.ActivityResultLauncher; |
||||
import androidx.activity.result.contract.ActivityResultContracts; |
||||
import androidx.appcompat.app.AppCompatActivity; |
||||
import androidx.fragment.app.Fragment; |
||||
|
||||
public class BackupImportHelper { |
||||
private ICallback callback; |
||||
private final ActivityResultLauncher<Intent> importLauncher; |
||||
|
||||
public BackupImportHelper(AppCompatActivity activity) { |
||||
importLauncher = activity.registerForActivityResult(new ActivityResultContracts.StartActivityForResult(), result -> { |
||||
if (callback == null) { |
||||
return; |
||||
} |
||||
boolean success = result != null && Activity.RESULT_OK == result.getResultCode(); |
||||
callback.onImported(success); |
||||
}); |
||||
} |
||||
|
||||
public BackupImportHelper(Fragment fragment) { |
||||
importLauncher = fragment.registerForActivityResult(new ActivityResultContracts.StartActivityForResult(), result -> { |
||||
if (callback == null) { |
||||
return; |
||||
} |
||||
boolean success = result != null && Activity.RESULT_OK == result.getResultCode(); |
||||
callback.onImported(success); |
||||
}); |
||||
} |
||||
|
||||
public void doImport(Context context, ICallback callback) { |
||||
this.callback = callback; |
||||
Intent intent = MigrationFolder2PrivateRoomActivity.intent(context, true); |
||||
importLauncher.launch(intent); |
||||
} |
||||
|
||||
public interface ICallback { |
||||
void onImported(boolean success); |
||||
} |
||||
} |
@ -0,0 +1,124 @@ |
||||
package com.bingce.controlnetwork.activity.backup.launch; |
||||
|
||||
import android.app.Activity; |
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.view.View; |
||||
import android.view.WindowManager; |
||||
|
||||
import androidx.annotation.Nullable; |
||||
|
||||
import com.bingce.file.DownloadFilePicker; |
||||
import com.bingce.utils.AsynchronousHelper; |
||||
import com.bingce.utils.IntentUtil; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import com.bingce.controlnetwork.databinding.ActivityMigration2PrivateFolderLayoutBinding; |
||||
|
||||
public class MigrationFolder2PrivateRoomActivity extends ColorfulActivity implements AsynchronousHelper.IDelegate { |
||||
private final DownloadFilePicker downloadFilePicker = new DownloadFilePicker(this); |
||||
private final AsynchronousHelper migrationHelper = new AsynchronousHelper(this); |
||||
private ActivityMigration2PrivateFolderLayoutBinding binding; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS); |
||||
binding = ActivityMigration2PrivateFolderLayoutBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
//从备份文件导入
|
||||
binding.backupFromZip.setOnClickListener(v -> { |
||||
binding.layout2.setVisibility(View.INVISIBLE); |
||||
ZipMigrationUtils.importFromZip(MigrationFolder2PrivateRoomActivity.this, |
||||
"导线助手数据+日期", |
||||
migrationHelper, |
||||
downloadFilePicker, |
||||
new ZipMigrationUtils.IMigrationListener() { |
||||
@Override |
||||
public void onMigrationStart() { |
||||
showWorkLayout(); |
||||
} |
||||
|
||||
@Override |
||||
public void onMigrationInterrupt() { |
||||
back2Layout2(); |
||||
} |
||||
}); |
||||
}); |
||||
boolean fromMainActivity = IntentUtil.boolExtra(this, KEY_FROM_MAIN_ACTIVITY); |
||||
if (fromMainActivity) { |
||||
binding.enterAppDirect.setVisibility(View.GONE); |
||||
} else { |
||||
binding.enterAppDirect.setOnClickListener(v -> { |
||||
binding.backupFromZip.setEnabled(false); |
||||
binding.enterAppDirect.setEnabled(false); |
||||
enterApp(MigrationFolder2PrivateRoomActivity.this); |
||||
}); |
||||
} |
||||
} |
||||
|
||||
private void showWorkLayout() { |
||||
binding.workLayout.setVisibility(View.VISIBLE); |
||||
binding.back.setEnabled(false); |
||||
binding.back.setOnClickListener(v -> back2Layout2()); |
||||
binding.next.setEnabled(false); |
||||
binding.next.setOnClickListener(v -> { |
||||
binding.back.setEnabled(false); |
||||
binding.next.setEnabled(false); |
||||
enterApp(MigrationFolder2PrivateRoomActivity.this); |
||||
}); |
||||
binding.tvCompleted.setVisibility(View.INVISIBLE); |
||||
binding.spinKit.setVisibility(View.VISIBLE); |
||||
binding.progressText.setText(""); |
||||
} |
||||
|
||||
private void back2Layout2() { |
||||
binding.workLayout.setVisibility(View.INVISIBLE); |
||||
binding.layout2.setVisibility(View.VISIBLE); |
||||
} |
||||
|
||||
private static void enterApp(Activity activity) { |
||||
boolean fromMainActivity = IntentUtil.boolExtra(activity, KEY_FROM_MAIN_ACTIVITY); |
||||
if (fromMainActivity) { |
||||
activity.setResult(Activity.RESULT_OK); |
||||
activity.finish(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onBackPressed() { |
||||
boolean fromMainActivity = IntentUtil.boolExtra(this, KEY_FROM_MAIN_ACTIVITY); |
||||
if (fromMainActivity) { |
||||
super.onBackPressed(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onUpdateProgress(String msg) { |
||||
binding.progressText.setText(binding.progressText.getText() + "\n" + msg); |
||||
binding.scrollView.post(() -> binding.scrollView.fullScroll(View.FOCUS_DOWN)); |
||||
} |
||||
|
||||
@Override |
||||
public void onCompleted() { |
||||
binding.next.setEnabled(true); |
||||
binding.back.setEnabled(true); |
||||
binding.tvCompleted.setVisibility(View.VISIBLE); |
||||
binding.spinKit.setVisibility(View.INVISIBLE); |
||||
} |
||||
|
||||
private static final String KEY_FROM_MAIN_ACTIVITY = "from_main_activity"; |
||||
|
||||
public static void start(Context context) { |
||||
context.startActivity(intent(context, false)); |
||||
} |
||||
|
||||
public static Intent intent(Context context, boolean fromMainActivity) { |
||||
Intent intent = new Intent(context, MigrationFolder2PrivateRoomActivity.class); |
||||
intent.putExtra(KEY_FROM_MAIN_ACTIVITY, fromMainActivity); |
||||
return intent; |
||||
} |
||||
} |
@ -0,0 +1,124 @@ |
||||
package com.bingce.controlnetwork.activity.backup.launch; |
||||
|
||||
import android.content.Context; |
||||
import android.text.TextUtils; |
||||
|
||||
import com.bingce.controlnetwork.activity.backup.AbstractBackupExportActivity; |
||||
import com.bingce.file.DownloadFilePicker; |
||||
import com.bingce.file.FileOperator; |
||||
import com.bingce.path.PathManager; |
||||
import com.bingce.utils.AsynchronousHelper; |
||||
import com.bingce.utils.FileUtil; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
import com.bingce.zip.ZipHelper; |
||||
|
||||
import java.io.File; |
||||
|
||||
import blankj.utilcode.util.FileUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
import com.bingce.controlnetwork.activity.backup.AbstractBackupExportActivity; |
||||
|
||||
public class ZipMigrationUtils { |
||||
|
||||
public static void importFromZip(Context context, String backupName, AsynchronousHelper asynchronousHelper, DownloadFilePicker downloadFilePicker, IMigrationListener listener) { |
||||
downloadFilePicker.doPick(duplicate -> { |
||||
String errorString = "请选择正确的备份数据,位于根目录Download文件夹内,名称样式为「" + backupName + ".zip」"; |
||||
if (duplicate == null || !duplicate.exists()) { |
||||
ToastUtils.showShort(errorString); |
||||
if (listener != null) { |
||||
listener.onMigrationInterrupt(); |
||||
} |
||||
return; |
||||
} |
||||
if (!duplicate.getName().endsWith(".zip")) { |
||||
ToastUtils.showShort(errorString); |
||||
if (listener != null) { |
||||
listener.onMigrationInterrupt(); |
||||
} |
||||
return; |
||||
} |
||||
asynchronousHelper.start(); |
||||
if (listener != null) { |
||||
listener.onMigrationStart(); |
||||
} |
||||
//切换线路执行数据解压
|
||||
ThreadPoolUtil.execute(() -> { |
||||
//解压缩
|
||||
|
||||
File unzipFolder = new File(context.getExternalCacheDir(), duplicate.getName().replace(".zip", "")); |
||||
File[] prjFolders = unzipBackupFile(duplicate, unzipFolder, errorString); |
||||
if (prjFolders == null) { |
||||
return; |
||||
} |
||||
|
||||
for (File file : prjFolders) { |
||||
File[] folder = file.listFiles(); |
||||
String backUpType = null; |
||||
for (File fileBackup : folder) { |
||||
if (!fileBackup.isDirectory()) { |
||||
if (fileBackup.getName().equals(AbstractBackupExportActivity.BACKUP_TXT)) { |
||||
FileUtil.ReadFileResult readFileResult = FileUtil.readStringFrom(fileBackup); |
||||
if (readFileResult.success) { |
||||
backUpType = readFileResult.string; |
||||
} |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
|
||||
for (File fileBackup : folder) { |
||||
if (fileBackup.isDirectory()) { |
||||
String name = fileBackup.getName(); |
||||
if (TextUtils.equals(name, backUpType)) { |
||||
File[] dbFileList = fileBackup.listFiles(); |
||||
for (File dbFile : dbFileList) { |
||||
FileOperator.copy(dbFile, PathManager.appDocumentFolder()); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
|
||||
//完成数据导入
|
||||
asynchronousHelper.completed(); |
||||
}); |
||||
}); |
||||
} |
||||
|
||||
private static File[] unzipBackupFile(File duplicate, File unzipFolder, String errorString) { |
||||
if (!unzipFolder.exists()) { |
||||
if (!unzipFolder.mkdirs()) { |
||||
ToastUtils.showShort("解压备份文件失败"); |
||||
return null; |
||||
} |
||||
} else { |
||||
//先删除,再创建
|
||||
try { |
||||
FileUtils.delete(unzipFolder); |
||||
} catch (Exception e) { |
||||
e.printStackTrace(); |
||||
ToastUtils.showShort("解压备份文件失败"); |
||||
return null; |
||||
} |
||||
if (!unzipFolder.mkdirs()) { |
||||
ToastUtils.showShort("解压备份文件失败"); |
||||
return null; |
||||
} |
||||
} |
||||
if (!ZipHelper.unZipFile(unzipFolder.getAbsolutePath(), duplicate.getAbsolutePath())) { |
||||
ToastUtils.showShort(errorString); |
||||
return null; |
||||
} |
||||
//解析文件内容
|
||||
return unzipFolder.listFiles(); |
||||
} |
||||
|
||||
|
||||
public interface IMigrationListener { |
||||
void onMigrationStart(); |
||||
|
||||
void onMigrationInterrupt(); |
||||
} |
||||
} |
@ -0,0 +1,92 @@ |
||||
package com.bingce.controlnetwork.activity.fragmentcontainer; |
||||
|
||||
import android.os.Bundle; |
||||
|
||||
import androidx.fragment.app.Fragment; |
||||
|
||||
import com.bingce.controlnetwork.fragment.PickPointFragment; |
||||
import com.bingce.controlnetwork.fragment.PointListFragment; |
||||
import com.bingce.controlnetwork.fragment.PrismManageFragment; |
||||
import com.bingce.controlnetwork.fragment.ProjectToleranceSettingFragment; |
||||
import com.bingce.controlnetwork.fragment.SelectExportHeightTraverseFragment; |
||||
import com.bingce.controlnetwork.fragment.SelectExportSurveyorRecordFragment; |
||||
import com.bingce.controlnetwork.fragment.SelectExportSurveyorRecordWireFileFragment; |
||||
import com.bingce.controlnetwork.fragment.SurveyorSettingsFragment; |
||||
import com.bingce.controlnetwork.fragment.ToleranceDetailFragment; |
||||
import com.bingce.controlnetwork.fragment.ToleranceManageFragment; |
||||
import com.bingce.controlnetwork.fragment.ToleranceSelectFragment; |
||||
import com.bingce.controlnetwork.fragment.projectdetail.ProjectDetailHeightTraverseFragment; |
||||
import com.bingce.controlnetwork.fragment.projectdetail.ProjectDetailTriangleFragment; |
||||
import com.bingce.controlnetwork.fragment.station.defaultstation.DefaultStationSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.station.heighttraverse.CreateStationForHeightTraverseFragment; |
||||
import com.bingce.controlnetwork.fragment.station.line.attached.LineStationAttachedSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.station.line.close.LineStationCloseSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.station.line.random.LineStationRandomSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.station.line.single.LineStationSingleSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.station.line.well.LineStationWellDoubleGroundSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.station.line.well.LineStationWellDoubleUnderGroundSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.station.line.well.LineStationWellSetupFragment; |
||||
import com.bingce.controlnetwork.fragment.stationdetail.SingleStationDetailAndEditFragment; |
||||
import com.bingce.controlnetwork.fragment.stationsetting.StationSettingHeightTraverseFragment; |
||||
import com.bingce.controlnetwork.fragment.stationsetting.StationSettingsFragment; |
||||
import com.bingce.controlnetwork.fragment.stationsurvey.StationSurveyorFragment; |
||||
import com.bingce.controlnetwork.fragment.stationsurvey.angledistance.MeasureFragment; |
||||
import com.bingce.controlnetwork.fragment.stationsurvey.heighttraverse.MeasureHeightTraverseFragment; |
||||
import com.bingce.controlnetwork.func.level.fragment.LevelRouteCreateEditFragment; |
||||
import com.bingce.controlnetwork.func.level.fragment.LevelSelectExportFragment; |
||||
import com.bingce.controlnetwork.func.level.fragment.LevelSurveyFragment; |
||||
import com.bingce.controlnetwork.func.level.fragment.ProjectDetailLevelFragment; |
||||
|
||||
import java.util.HashMap; |
||||
import java.util.Map; |
||||
|
||||
public class FragmentContainer { |
||||
private interface IBuilder { |
||||
Fragment newInstance(Bundle args); |
||||
} |
||||
|
||||
private static final Map<String, IBuilder> factory = new HashMap<>(); |
||||
|
||||
static { |
||||
factory.put(ProjectDetailHeightTraverseFragment.TAG, ProjectDetailHeightTraverseFragment::newInstance); |
||||
factory.put(ProjectDetailTriangleFragment.TAG, ProjectDetailTriangleFragment::newInstance); |
||||
factory.put(ProjectToleranceSettingFragment.TAG, ProjectToleranceSettingFragment::newInstance); |
||||
factory.put(ToleranceSelectFragment.TAG, ToleranceSelectFragment::newInstance); |
||||
factory.put(PointListFragment.TAG, PointListFragment::newInstance); |
||||
factory.put(SingleStationDetailAndEditFragment.TAG, SingleStationDetailAndEditFragment::newInstance); |
||||
factory.put(DefaultStationSetupFragment.TAG, DefaultStationSetupFragment::newInstance); |
||||
factory.put(PickPointFragment.TAG, PickPointFragment::newInstance); |
||||
factory.put(StationSurveyorFragment.TAG, StationSurveyorFragment::newInstance); |
||||
factory.put(StationSettingsFragment.TAG, StationSettingsFragment::newInstance); |
||||
factory.put(ToleranceManageFragment.TAG, ToleranceManageFragment::newInstance); |
||||
factory.put(ToleranceDetailFragment.TAG, ToleranceDetailFragment::newInstance); |
||||
factory.put(SelectExportSurveyorRecordFragment.TAG, SelectExportSurveyorRecordFragment::newInstance); |
||||
factory.put(SelectExportSurveyorRecordWireFileFragment.TAG, SelectExportSurveyorRecordWireFileFragment::newInstance); |
||||
factory.put(SurveyorSettingsFragment.TAG, SurveyorSettingsFragment::newInstance); |
||||
factory.put(LineStationSingleSetupFragment.TAG, LineStationSingleSetupFragment::newInstance); |
||||
factory.put(LineStationAttachedSetupFragment.TAG, LineStationAttachedSetupFragment::newInstance); |
||||
factory.put(LineStationCloseSetupFragment.TAG, LineStationCloseSetupFragment::newInstance); |
||||
factory.put(LineStationRandomSetupFragment.TAG, LineStationRandomSetupFragment::newInstance); |
||||
factory.put(LineStationWellSetupFragment.TAG, LineStationWellSetupFragment::newInstance); |
||||
factory.put(LineStationWellDoubleGroundSetupFragment.TAG, LineStationWellDoubleGroundSetupFragment::newInstance); |
||||
factory.put(LineStationWellDoubleUnderGroundSetupFragment.TAG, LineStationWellDoubleUnderGroundSetupFragment::newInstance); |
||||
factory.put(PrismManageFragment.TAG, PrismManageFragment::newInstance); |
||||
factory.put(MeasureFragment.TAG, MeasureFragment::newInstance); |
||||
factory.put(CreateStationForHeightTraverseFragment.TAG, CreateStationForHeightTraverseFragment::newInstance); |
||||
factory.put(MeasureHeightTraverseFragment.TAG, MeasureHeightTraverseFragment::newInstance); |
||||
factory.put(SelectExportHeightTraverseFragment.TAG, SelectExportHeightTraverseFragment::newInstance); |
||||
factory.put(StationSettingHeightTraverseFragment.TAG, StationSettingHeightTraverseFragment::newInstance); |
||||
factory.put(ProjectDetailLevelFragment.TAG, ProjectDetailLevelFragment::newInstance); |
||||
factory.put(LevelSurveyFragment.TAG, LevelSurveyFragment::newInstance); |
||||
factory.put(LevelSelectExportFragment.TAG, LevelSelectExportFragment::newInstance); |
||||
factory.put(LevelRouteCreateEditFragment.TAG, LevelRouteCreateEditFragment::newInstance); |
||||
} |
||||
|
||||
public static Fragment getFragment(String tag, Bundle bundle) { |
||||
IBuilder builder = factory.get(tag); |
||||
if (builder == null) { |
||||
return null; |
||||
} |
||||
return builder.newInstance(bundle); |
||||
} |
||||
} |
@ -0,0 +1,138 @@ |
||||
package com.bingce.controlnetwork.activity.fragmentcontainer; |
||||
|
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.view.MenuItem; |
||||
|
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
import androidx.fragment.app.Fragment; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
public class FragmentContainerActivity extends ColorfulActivity { |
||||
private static final String KEY_TAG = "_TAG_"; |
||||
private static final String KEY_TITLE_STRING_ID = "__title_res"; |
||||
private static final String KEY_TITLE_STRING = "__title__"; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
//设置view
|
||||
setContentView(R.layout.activity_fragment_container_layout); |
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
//设置fragment
|
||||
if (savedInstanceState == null) { |
||||
Intent intent = getIntent(); |
||||
if (intent == null) { |
||||
finish(); |
||||
return; |
||||
} |
||||
int title = intent.getIntExtra(KEY_TITLE_STRING_ID, -1); |
||||
if (title > 0) { |
||||
setTitle(title); |
||||
} else { |
||||
String string = intent.getStringExtra(KEY_TITLE_STRING); |
||||
setTitle(string); |
||||
} |
||||
String tag = intent.getStringExtra(KEY_TAG); |
||||
Bundle bundle = intent.getExtras(); |
||||
Fragment fragment = FragmentContainer.getFragment(tag, bundle); |
||||
if (fragment == null) { |
||||
finish(); |
||||
return; |
||||
} |
||||
getSupportFragmentManager().beginTransaction() |
||||
.replace(R.id.container, fragment) |
||||
.commitAllowingStateLoss(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
if (!isCancelBack()) { |
||||
finish(); |
||||
} |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
@Override |
||||
public void onBackPressed() { |
||||
if (isCancelBack()) { |
||||
return; |
||||
} |
||||
super.onBackPressed(); |
||||
} |
||||
|
||||
private boolean isCancelBack() { |
||||
List<Fragment> fragmentList = getSupportFragmentManager() |
||||
.getFragments(); |
||||
boolean cancelBack = false; |
||||
for (Fragment fragment : fragmentList) { |
||||
if (fragment instanceof IOnBackFilter) { |
||||
if (((IOnBackFilter) fragment).cancelBack()) { |
||||
cancelBack = true; |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
return cancelBack; |
||||
} |
||||
|
||||
public static void start(Context context, String tag, int titleRes, Bundle bundle) { |
||||
Intent intent = new Intent(context, FragmentContainerActivity.class); |
||||
if (bundle != null) { |
||||
intent.putExtras(bundle); |
||||
} |
||||
intent.putExtra(KEY_TAG, tag); |
||||
intent.putExtra(KEY_TITLE_STRING_ID, titleRes); |
||||
context.startActivity(intent); |
||||
} |
||||
|
||||
public static void start(Context context, String tag, String title, Bundle bundle) { |
||||
Intent intent = new Intent(context, FragmentContainerActivity.class); |
||||
if (bundle != null) { |
||||
intent.putExtras(bundle); |
||||
} |
||||
intent.putExtra(KEY_TAG, tag); |
||||
intent.putExtra(KEY_TITLE_STRING, title); |
||||
context.startActivity(intent); |
||||
} |
||||
|
||||
public static Intent startIntent(Context context, |
||||
String tag, |
||||
int titleRes, |
||||
Bundle bundle) { |
||||
Intent intent = new Intent(context, FragmentContainerActivity.class); |
||||
if (bundle != null) { |
||||
intent.putExtras(bundle); |
||||
} |
||||
intent.putExtra(KEY_TAG, tag); |
||||
intent.putExtra(KEY_TITLE_STRING_ID, titleRes); |
||||
return intent; |
||||
} |
||||
|
||||
public static Intent startIntent(Context context, |
||||
String tag, |
||||
String title, |
||||
Bundle bundle) { |
||||
Intent intent = new Intent(context, FragmentContainerActivity.class); |
||||
if (bundle != null) { |
||||
intent.putExtras(bundle); |
||||
} |
||||
intent.putExtra(KEY_TAG, tag); |
||||
intent.putExtra(KEY_TITLE_STRING, title); |
||||
return intent; |
||||
} |
||||
} |
@ -0,0 +1,11 @@ |
||||
package com.bingce.controlnetwork.activity.fragmentcontainer; |
||||
|
||||
public class FragmentItem { |
||||
public final int titleId; |
||||
public final String tag; |
||||
|
||||
public FragmentItem(int title, String tag) { |
||||
titleId = title; |
||||
this.tag = tag; |
||||
} |
||||
} |
@ -0,0 +1,5 @@ |
||||
package com.bingce.controlnetwork.activity.fragmentcontainer; |
||||
|
||||
public interface IOnBackFilter { |
||||
boolean cancelBack(); |
||||
} |
@ -0,0 +1,143 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.text.Editable; |
||||
import android.text.InputType; |
||||
import android.text.TextWatcher; |
||||
import android.view.MenuItem; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import blankj.utilcode.util.StringUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
import cn.leancloud.LCUser; |
||||
|
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityEditUserNicknamePasswordBinding; |
||||
|
||||
public class EditNicknamePasswordActivity extends ColorfulActivity { |
||||
|
||||
private ActivityEditUserNicknamePasswordBinding binding; |
||||
private boolean isShowPassword01, isShowPassword02; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityEditUserNicknamePasswordBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
//隐藏显示按钮01(输入密码)
|
||||
binding.llPassword01.setOnClickListener(v -> { |
||||
if (isShowPassword01) { |
||||
// 明文显示密码
|
||||
binding.etPassword01.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_NORMAL); |
||||
binding.ivPassword01.setImageDrawable(getDrawable(R.drawable.icon_password_open_eyes)); |
||||
} else { |
||||
// 隐藏密码
|
||||
binding.etPassword01.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD); |
||||
binding.ivPassword01.setImageDrawable(getDrawable(R.drawable.icon_password_close_eyes)); |
||||
} |
||||
isShowPassword01 = !isShowPassword01; |
||||
}); |
||||
|
||||
//隐藏显示按钮02(确认密码)
|
||||
binding.llPassword02.setOnClickListener(v -> { |
||||
if (isShowPassword02) { |
||||
// 明文显示密码
|
||||
binding.etPassword02.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_NORMAL); |
||||
binding.ivPassword02.setImageDrawable(getDrawable(R.drawable.icon_password_open_eyes)); |
||||
} else { |
||||
// 隐藏密码
|
||||
binding.etPassword02.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD); |
||||
binding.ivPassword02.setImageDrawable(getDrawable(R.drawable.icon_password_close_eyes)); |
||||
} |
||||
isShowPassword02 = !isShowPassword02; |
||||
}); |
||||
|
||||
binding.etPassword01.addTextChangedListener(new TextWatcher() { |
||||
@Override |
||||
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void afterTextChanged(Editable editable) { |
||||
checkPw(); |
||||
} |
||||
}); |
||||
binding.etPassword02.addTextChangedListener(new TextWatcher() { |
||||
@Override |
||||
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void afterTextChanged(Editable editable) { |
||||
checkPw(); |
||||
} |
||||
}); |
||||
|
||||
//完成
|
||||
binding.tvComplete.setOnClickListener(v -> { |
||||
String nickName = binding.etNickName.getText().toString(); |
||||
String password = binding.etPassword01.getText().toString(); |
||||
if (LCUser.getCurrentUser() != null) { |
||||
LCUser.getCurrentUser().setPassword(password); |
||||
LCUser.getCurrentUser().put("nickname", nickName); |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(); |
||||
((App) Utils.getApp()).isUserStatusChanged = true; |
||||
} |
||||
finish(); |
||||
}); |
||||
} |
||||
|
||||
private void checkPw() { |
||||
String nickName = binding.etNickName.getText().toString(); |
||||
String pw1 = binding.etPassword01.getText().toString(); |
||||
String pw2 = binding.etPassword02.getText().toString(); |
||||
boolean isEmptyNickName = StringUtils.isEmpty(nickName); |
||||
boolean isEmptyPw01 = StringUtils.isEmpty(pw1); |
||||
boolean isEmptyPw02 = StringUtils.isEmpty(pw2); |
||||
if (!isEmptyNickName && !isEmptyPw01 && !isEmptyPw02 && pw1.equals(pw2)) { |
||||
binding.tvComplete.setEnabled(true); |
||||
binding.tvComplete.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvComplete.setEnabled(false); |
||||
binding.tvComplete.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(@NonNull MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
finish(); |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
public static void start(Context context) { |
||||
context.startActivity(new Intent(context, EditNicknamePasswordActivity.class)); |
||||
} |
||||
} |
@ -0,0 +1,107 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.text.Editable; |
||||
import android.text.TextWatcher; |
||||
|
||||
import androidx.activity.result.ActivityResultLauncher; |
||||
import androidx.activity.result.contract.ActivityResultContracts; |
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import com.bingce.utils.IntentUtil; |
||||
import com.bingce.utils.ValidateUtil; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityInputEmailBinding; |
||||
|
||||
public class InputEmailActivity extends ColorfulActivity { |
||||
public static final String KEY_EMAIL = "email"; |
||||
public static final String KEY_TODO = "todo"; |
||||
private ActivityInputEmailBinding binding; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityInputEmailBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
getSupportActionBar().setTitle(R.string.email_verify); |
||||
if (getEmail() != null) { |
||||
binding.etEmail.setText(getEmail()); |
||||
binding.etEmail.setEnabled(false); |
||||
if (checkEmail()) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
} |
||||
} |
||||
|
||||
binding.etEmail.addTextChangedListener(new TextWatcher() { |
||||
@Override |
||||
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void afterTextChanged(Editable editable) { |
||||
if (checkEmail()) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
} |
||||
} |
||||
}); |
||||
|
||||
ActivityResultLauncher<Intent> verifyCodeLauncher = registerForActivityResult(new ActivityResultContracts.StartActivityForResult(), result -> { |
||||
Intent data = result.getData(); |
||||
if (data != null) { |
||||
setResult(RESULT_OK, data); |
||||
finish(); |
||||
} |
||||
}); |
||||
//下一步
|
||||
binding.tvNextPage.setOnClickListener(v -> { |
||||
String email = binding.etEmail.getText().toString(); |
||||
VerifyEmailCodeActivity.start(this, email, getToDo(), verifyCodeLauncher); |
||||
}); |
||||
} |
||||
|
||||
private boolean checkEmail() { |
||||
return ValidateUtil.isEmail(binding.etEmail.getText().toString()); |
||||
} |
||||
|
||||
public static void start(Context context, String email, int todo, ActivityResultLauncher<Intent> launcher) { |
||||
Intent intent = new Intent(context, InputEmailActivity.class); |
||||
intent.putExtra(KEY_EMAIL, email); |
||||
intent.putExtra(KEY_TODO, todo); |
||||
launcher.launch(intent); |
||||
} |
||||
|
||||
|
||||
private String getEmail() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_EMAIL); |
||||
} |
||||
|
||||
|
||||
private int getToDo() { |
||||
return IntentUtil.intExtra(getIntent(), KEY_TODO); |
||||
} |
||||
} |
@ -0,0 +1,93 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
|
||||
import androidx.activity.result.ActivityResultLauncher; |
||||
import androidx.activity.result.contract.ActivityResultContracts; |
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import com.bingce.utils.IntentUtil; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityInputPhoneNumberBinding; |
||||
|
||||
public class InputPhoneNumberActivity extends ColorfulActivity { |
||||
public static final String KEY_PHONE = "phone_number"; |
||||
public static final String KEY_EMAIL = "email"; |
||||
public static final String KEY_UNION_ID = "unionid"; |
||||
public static final String KEY_TODO = "todo"; |
||||
private ActivityInputPhoneNumberBinding binding; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityInputPhoneNumberBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
getSupportActionBar().setTitle(R.string.mobile_phone_verify); |
||||
|
||||
binding.ccp.registerCarrierNumberEditText(binding.etPhoneNumber); |
||||
binding.ccp.setPhoneNumberValidityChangeListener(isValidNumber -> { |
||||
if (isValidNumber) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
} |
||||
}); |
||||
if (getPhoneNumber() != null) { |
||||
binding.etPhoneNumber.setText(getPhoneNumber().replaceFirst("\\+86", "")); |
||||
binding.etPhoneNumber.setEnabled(false); |
||||
binding.ccp.setCcpClickable(false); |
||||
} |
||||
|
||||
ActivityResultLauncher<Intent> verifyCodeLauncher = registerForActivityResult(new ActivityResultContracts.StartActivityForResult(), result -> { |
||||
Intent data = result.getData(); |
||||
if (data != null && data.hasExtra("isMail") && data.hasExtra("phoneNumberOrEmail")) { |
||||
setResult(RESULT_OK, data); |
||||
finish(); |
||||
} |
||||
}); |
||||
//下一步
|
||||
binding.tvNextPage.setOnClickListener(v -> { |
||||
String phoneNumber = binding.ccp.getFullNumberWithPlus(); |
||||
VerifySMSCodeActivity.start(this, phoneNumber, getEmail(), getUnionId(), getToDo(), verifyCodeLauncher); |
||||
}); |
||||
} |
||||
|
||||
public static void start(Context context, String phoneNumber, String email, String unionid, int todo, ActivityResultLauncher<Intent> launcher) { |
||||
Intent intent = new Intent(context, InputPhoneNumberActivity.class); |
||||
intent.putExtra(KEY_PHONE, phoneNumber); |
||||
intent.putExtra(KEY_EMAIL, email); |
||||
intent.putExtra(KEY_UNION_ID, unionid); |
||||
intent.putExtra(KEY_TODO, todo); |
||||
launcher.launch(intent); |
||||
} |
||||
|
||||
private String getPhoneNumber() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_PHONE); |
||||
} |
||||
|
||||
|
||||
private String getEmail() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_EMAIL); |
||||
} |
||||
|
||||
private String getUnionId() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_UNION_ID); |
||||
} |
||||
|
||||
private int getToDo() { |
||||
return IntentUtil.intExtra(getIntent(), KEY_TODO); |
||||
} |
||||
} |
@ -0,0 +1,579 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.app.Activity; |
||||
import android.app.ProgressDialog; |
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.text.Editable; |
||||
import android.text.TextWatcher; |
||||
import android.view.View; |
||||
|
||||
import androidx.activity.result.ActivityResultLauncher; |
||||
import androidx.activity.result.contract.ActivityResultContracts; |
||||
import androidx.annotation.Nullable; |
||||
|
||||
import com.bingce.AppChannel; |
||||
import com.bingce.BaseApp; |
||||
import com.bingce.activity.UserCloudFunction; |
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityLoginBinding; |
||||
import com.bingce.controlnetwork.wxapi.MD5; |
||||
import com.bingce.data.sync.utils.LeanCloudUserLoginStateUtils; |
||||
import com.bingce.event.WxRespCodeEvent; |
||||
import com.bingce.ui.TabEntity; |
||||
import com.bingce.utils.ActivityUtils; |
||||
import com.bingce.utils.ValidateUtil; |
||||
import com.bingce.utils.VipManager; |
||||
import com.flyco.tablayout.listener.CustomTabEntity; |
||||
import com.flyco.tablayout.listener.OnTabSelectListener; |
||||
import com.hbb20.CountryCodePicker; |
||||
import com.tencent.mm.opensdk.modelmsg.SendAuth; |
||||
|
||||
import org.greenrobot.eventbus.EventBus; |
||||
import org.greenrobot.eventbus.Subscribe; |
||||
import org.greenrobot.eventbus.ThreadMode; |
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.Random; |
||||
|
||||
import alibaba.fastjson.JSON; |
||||
import alibaba.fastjson.JSONObject; |
||||
import blankj.utilcode.util.StringUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
import cn.leancloud.LCException; |
||||
import cn.leancloud.LCUser; |
||||
import io.reactivex.Observer; |
||||
import io.reactivex.disposables.Disposable; |
||||
|
||||
public class LoginActivity extends ColorfulActivity { |
||||
|
||||
private ActivityLoginBinding binding; |
||||
private final String[] mTitles = new String[]{Utils.getApp().getString(R.string.phone_number), Utils.getApp().getString(R.string.e_mail)}; |
||||
private final ArrayList<CustomTabEntity> tabEntityList = new ArrayList<>(); |
||||
private boolean isLoginPassword = true, isLoginByEmail = false; |
||||
|
||||
private ProgressDialog progressDialog; |
||||
private String wxRespCode; |
||||
private String finishTo; |
||||
private ActivityResultLauncher<Intent> signUpOrLoginLauncher; |
||||
|
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityLoginBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
setSupportActionBar(binding.getRoot().findViewById(R.id.toolbar)); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
EventBus.getDefault().register(this); |
||||
|
||||
finishTo = getIntent().getStringExtra("finishTo"); |
||||
|
||||
//绑定Tab数据
|
||||
for (String mTitle : mTitles) { |
||||
tabEntityList.add(new TabEntity(mTitle)); |
||||
} |
||||
binding.tabLoginMode.setTabData(tabEntityList); |
||||
|
||||
//切换手机号、邮箱
|
||||
binding.tabLoginMode.setOnTabSelectListener(new OnTabSelectListener() { |
||||
@Override |
||||
public void onTabSelect(int position) { |
||||
isLoginByEmail = position != 0; |
||||
onSelectTabPhoneEmail(); |
||||
} |
||||
|
||||
@Override |
||||
public void onTabReselect(int position) { |
||||
|
||||
} |
||||
}); |
||||
|
||||
//切换验证码、密码
|
||||
binding.tvLoginPasswordCode.setOnClickListener(v -> { |
||||
onClickBtnPassword(); |
||||
}); |
||||
|
||||
binding.ccp.registerCarrierNumberEditText(binding.etPhoneNumber); |
||||
binding.ccp.setPhoneNumberValidityChangeListener(new CountryCodePicker.PhoneNumberValidityChangeListener() { |
||||
@Override |
||||
public void onValidityChanged(boolean isValidNumber) { |
||||
if (isValidNumber) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
} |
||||
} |
||||
}); |
||||
//下一步
|
||||
binding.tvNextPage.setOnClickListener(v -> { |
||||
if (checkValid()) { |
||||
if (isLoginByEmail) { |
||||
String email = binding.etEmail.getText().toString().trim(); |
||||
if (!isLoginPassword) {//验证码登录
|
||||
VerifyEmailCodeActivity.start(this, email, VerifyEmailCodeActivity.TO_SIGNUP_OR_LOGIN_BY_EMAIL, signUpOrLoginLauncher); |
||||
} else { |
||||
String password = binding.etPassword.getText().toString(); |
||||
loginByEmailPassword(email, password); |
||||
} |
||||
} else { |
||||
String phoneNumber = binding.ccp.getFullNumberWithPlus(); |
||||
if (!isLoginPassword) {//验证码登录
|
||||
VerifySMSCodeActivity.start(this, phoneNumber, null, null, VerifySMSCodeActivity.TO_SIGNUP_OR_LOGIN_BY_PHONE_NUMBER, signUpOrLoginLauncher); |
||||
} else { |
||||
String password = binding.etPassword.getText().toString(); |
||||
if (phoneNumber.startsWith("+86")) { |
||||
phoneNumber = phoneNumber.replaceFirst("\\+86", ""); |
||||
} |
||||
loginByPhonePassword(phoneNumber, password); |
||||
} |
||||
} |
||||
} |
||||
}); |
||||
|
||||
binding.ivWechatLogin.setOnClickListener(v -> { |
||||
wxLogin(); |
||||
}); |
||||
signUpOrLoginLauncher = registerForActivityResult(new ActivityResultContracts.StartActivityForResult(), result -> { |
||||
if (result.getResultCode() == Activity.RESULT_OK) { |
||||
Intent data = result.getData(); |
||||
if (data != null) { |
||||
if (data.hasExtra("sessionToken") && data.hasExtra("newUser")) { |
||||
String sessionToken = data.getStringExtra("sessionToken"); |
||||
boolean newUser = data.getBooleanExtra("newUser", false); |
||||
progressDialog = new ProgressDialog(LoginActivity.this); |
||||
progressDialog.setMessage(getString(R.string.logging)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
LCUser.becomeWithSessionTokenInBackground(sessionToken, true).subscribe(new Observer<LCUser>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCUser lcUser) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
loginSuccess(); |
||||
if (newUser) { |
||||
EditNicknamePasswordActivity.start(LoginActivity.this); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
ToastUtils.showShort(getString(R.string.error_code) + new LCException(e).getCode()); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
} |
||||
} |
||||
}); |
||||
|
||||
binding.etPassword.addTextChangedListener(new TextWatcher() { |
||||
@Override |
||||
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void afterTextChanged(Editable editable) { |
||||
checkValid(); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
public static void start(Context context) { |
||||
context.startActivity(new Intent(context, LoginActivity.class)); |
||||
} |
||||
|
||||
public void onSelectTabPhoneEmail() { |
||||
binding.etPassword.setText(""); |
||||
if (!isLoginByEmail) {//手机号登录
|
||||
binding.llPhoneNumber.setVisibility(View.VISIBLE); |
||||
binding.llEmail.setVisibility(View.GONE); |
||||
binding.etPhoneNumber.setText(""); |
||||
if (isLoginPassword) { |
||||
binding.signUpHint.setText(R.string.if_you_do_not_have_an_account_you_can_use_a_verification_code_to_sign_up_and_log_in); |
||||
} else { |
||||
binding.signUpHint.setText(R.string.unsigned_up_mobile_phone_number_will_be_automatically_signed_up_and_logged_in); |
||||
} |
||||
} else {//邮箱登录
|
||||
binding.llPhoneNumber.setVisibility(View.GONE); |
||||
binding.llEmail.setVisibility(View.VISIBLE); |
||||
binding.etEmail.setText(""); |
||||
if (isLoginPassword) { |
||||
binding.signUpHint.setText(R.string.if_you_do_not_have_an_account_you_can_use_a_verification_code_to_sign_up_and_log_in); |
||||
} else { |
||||
binding.signUpHint.setText(R.string.unsigned_up_email_will_be_automatically_signed_up_and_logged_in); |
||||
} |
||||
} |
||||
checkValid(); |
||||
} |
||||
|
||||
public void onClickBtnPassword() { |
||||
isLoginPassword = !isLoginPassword; |
||||
if (!isLoginPassword) {//现在改为验证码登录
|
||||
binding.llPassword.setVisibility(View.GONE); |
||||
binding.tvNextPage.setText(R.string.next); |
||||
binding.tvLoginPasswordCode.setText(R.string.log_in_with_password); |
||||
if (!isLoginByEmail) {//手机号登录
|
||||
binding.signUpHint.setText(R.string.unsigned_up_mobile_phone_number_will_be_automatically_signed_up_and_logged_in); |
||||
} else { |
||||
binding.signUpHint.setText(R.string.unsigned_up_email_will_be_automatically_signed_up_and_logged_in); |
||||
} |
||||
} else {//现在改为密码登录
|
||||
binding.llPassword.setVisibility(View.VISIBLE); |
||||
binding.tvNextPage.setText(R.string.log_in); |
||||
binding.tvLoginPasswordCode.setText(R.string.log_in_using_verify_code); |
||||
binding.signUpHint.setText(R.string.if_you_do_not_have_an_account_you_can_use_a_verification_code_to_sign_up_and_log_in); |
||||
} |
||||
checkValid(); |
||||
} |
||||
|
||||
public boolean checkValid() { |
||||
if (!isLoginPassword) {//现在改为验证码登录
|
||||
if (isLoginByEmail) { |
||||
if (ValidateUtil.isEmail(binding.etEmail.getText().toString().trim())) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
return false; |
||||
} |
||||
} else { |
||||
if (binding.ccp.isValidFullNumber()) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
return false; |
||||
} |
||||
} |
||||
} else {//现在改为密码登录
|
||||
if (isLoginByEmail) { |
||||
if (ValidateUtil.isEmail(binding.etEmail.getText().toString().trim()) && !StringUtils.isEmpty(binding.etPassword.getText().toString().trim())) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
return false; |
||||
} |
||||
} else { |
||||
if (binding.ccp.isValidFullNumber() && !StringUtils.isEmpty(binding.etPassword.getText().toString().trim())) { |
||||
binding.tvNextPage.setEnabled(true); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_theme_green_full)); |
||||
} else { |
||||
binding.tvNextPage.setEnabled(false); |
||||
binding.tvNextPage.setBackground(getDrawable(R.drawable.rectangle_radius_8_gray_full)); |
||||
return false; |
||||
} |
||||
} |
||||
} |
||||
return true; |
||||
} |
||||
|
||||
public void wxLogin() { |
||||
wxRespCode = null; |
||||
if (Utils.getApp() instanceof BaseApp) { |
||||
if (((BaseApp) Utils.getApp()).getWxApi() != null) { |
||||
if (!((BaseApp) Utils.getApp()).getWxApi().isWXAppInstalled()) { |
||||
ToastUtils.showShort(R.string.you_do_not_have_the_wechat_app_installed); |
||||
} else { |
||||
final SendAuth.Req req = new SendAuth.Req(); |
||||
//应用授权作用域,如获取用户个人信息则填写 snsapi_userinfo
|
||||
req.scope = "snsapi_userinfo"; |
||||
//用于保持请求和回调的状态,授权请求后原样带回给第三方。
|
||||
//该参数可用于防止 csrf 攻击(跨站请求伪造攻击),
|
||||
//建议第三方带上该参数,可设置为简单的随机数加 session 进行校验
|
||||
req.state = getNonceStr(); |
||||
if (((BaseApp) Utils.getApp()).getWxApi() != null) |
||||
((BaseApp) Utils.getApp()).getWxApi().sendReq(req); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
//生成随机号,防重发
|
||||
private String getNonceStr() { |
||||
Random random = new Random(); |
||||
return MD5.getMessageDigest((System.currentTimeMillis() + String.valueOf(random.nextInt(10000))).getBytes()); |
||||
} |
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN) |
||||
public void onMessageEvent(WxRespCodeEvent event) { |
||||
wxRespCode = event.getCode(); |
||||
} |
||||
|
||||
@Override |
||||
protected void onResume() { |
||||
super.onResume(); |
||||
if (wxRespCode != null) { |
||||
loginByWxCode(); |
||||
wxRespCode = null; |
||||
} |
||||
} |
||||
|
||||
private void loginByWxCode() { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
progressDialog = new ProgressDialog(LoginActivity.this); |
||||
progressDialog.setMessage(getString(R.string.logging)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
UserCloudFunction.loginByWxCode(wxRespCode, AppChannel.customChannel, new UserCloudFunction.OnGetSessionTokenListener() { |
||||
@Override |
||||
public void onSessionTokenGetSuccess(String sessionToken, boolean newUser) { |
||||
LCUser.becomeWithSessionTokenInBackground(sessionToken, true).subscribe(new Observer<LCUser>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCUser lcUser) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
if (newUser) { |
||||
EditNicknamePasswordActivity.start(LoginActivity.this); |
||||
} |
||||
((App) Utils.getApp()).isUserStatusChanged = true; |
||||
setResult(RESULT_OK); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(getString(R.string.error_code) + new LCException(e).getCode()); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetFailed(int code, String msg, String resp) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
if (code == 321 || code == 322) {//321此微信未绑定用户,请使用其他方式登录,322缺少手机号或手机号未验证
|
||||
JSONObject jsonObject = JSON.parseObject(resp); |
||||
if (jsonObject.containsKey("data")) { |
||||
JSONObject data = jsonObject.getJSONObject("data"); |
||||
if (data.containsKey("unionid")) { |
||||
String unionid = data.getString("unionid"); |
||||
InputPhoneNumberActivity.start(LoginActivity.this, null, null, unionid, VerifySMSCodeActivity.TO_SIGNUP_OR_LOGIN_BY_WEIXIN_BIND_PHONE, signUpOrLoginLauncher); |
||||
} |
||||
} |
||||
} else { |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetException(String msg) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
|
||||
private void loginSuccess() { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
progressDialog = new ProgressDialog(LoginActivity.this); |
||||
progressDialog.setMessage(getString(R.string.logging)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
VipManager.getInstance().controlSdkRefresh(LoginActivity.this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
if (!StringUtils.isEmpty(finishTo)) { |
||||
try { |
||||
Intent intent = new Intent(LoginActivity.this, Class.forName(finishTo)); |
||||
intent.putExtras(getIntent()); |
||||
startActivity(intent); |
||||
} catch (ClassNotFoundException | NullPointerException ex) { |
||||
ex.printStackTrace(); |
||||
} |
||||
} |
||||
|
||||
((App) Utils.getApp()).isUserStatusChanged = true; |
||||
LeanCloudUserLoginStateUtils.onLogIn(); |
||||
setResult(RESULT_OK); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
ToastUtils.showShort(getString(R.string.error_code) + ":" + errorCode); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
private void loginByEmailPassword(String email, String password) { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
progressDialog = new ProgressDialog(LoginActivity.this); |
||||
progressDialog.setMessage(getString(R.string.logging)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
UserCloudFunction.loginByEmailPassword(email, password, AppChannel.customChannel, new UserCloudFunction.OnGetSessionTokenListener() { |
||||
@Override |
||||
public void onSessionTokenGetSuccess(String sessionToken, boolean newUser) { |
||||
LCUser.becomeWithSessionTokenInBackground(sessionToken, true).subscribe(new Observer<LCUser>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCUser lcUser) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
loginSuccess(); |
||||
if (newUser) { |
||||
EditNicknamePasswordActivity.start(LoginActivity.this); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(getString(R.string.error_code) + new LCException(e).getCode()); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetFailed(int code, String msg, String resp) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
if (code == 303) {//缺少手机号或未验证
|
||||
InputPhoneNumberActivity.start(LoginActivity.this, null, email, null, VerifySMSCodeActivity.TO_SIGNUP_OR_LOGIN_BY_EMAIL_BIND_PHONE, signUpOrLoginLauncher); |
||||
} else if (code == 304) {//邮箱未验证
|
||||
InputEmailActivity.start(LoginActivity.this, email, VerifyEmailCodeActivity.TO_SIGNUP_OR_LOGIN_BY_EMAIL, signUpOrLoginLauncher); |
||||
} else { |
||||
if (msg != null) |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetException(String msg) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
private void loginByPhonePassword(String phoneNumber, String password) { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
progressDialog = new ProgressDialog(LoginActivity.this); |
||||
progressDialog.setMessage(getString(R.string.logging)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
UserCloudFunction.loginByPhonePassword(phoneNumber, password, AppChannel.customChannel, new UserCloudFunction.OnGetSessionTokenListener() { |
||||
@Override |
||||
public void onSessionTokenGetSuccess(String sessionToken, boolean newUser) { |
||||
LCUser.becomeWithSessionTokenInBackground(sessionToken, true).subscribe(new Observer<LCUser>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCUser lcUser) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
loginSuccess(); |
||||
if (newUser) { |
||||
EditNicknamePasswordActivity.start(LoginActivity.this); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(getString(R.string.error_code) + new LCException(e).getCode()); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetFailed(int code, String msg, String resp) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
if (code == 303) {//手机号未验证
|
||||
InputPhoneNumberActivity.start(LoginActivity.this, phoneNumber, null, null, VerifySMSCodeActivity.TO_SIGNUP_OR_LOGIN_BY_PHONE_NUMBER, signUpOrLoginLauncher); |
||||
} else { |
||||
if (msg != null) |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetException(String msg) { |
||||
if (!ActivityUtils.isLiving(LoginActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
}); |
||||
} |
||||
} |
@ -0,0 +1,534 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.content.DialogInterface; |
||||
import android.graphics.Bitmap; |
||||
import android.graphics.Color; |
||||
import android.net.Uri; |
||||
import android.os.Bundle; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.view.View.OnClickListener; |
||||
import android.widget.ImageView; |
||||
import android.widget.RadioGroup; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.appcompat.app.AlertDialog; |
||||
|
||||
import com.afollestad.materialdialogs.DialogAction; |
||||
import com.afollestad.materialdialogs.MaterialDialog; |
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityOpeningRenewalBinding; |
||||
import com.bingce.data.sync.utils.LeanCloudConfigLoader; |
||||
import com.bingce.event.PayOverEvent; |
||||
import com.bingce.pay.OrderType; |
||||
import com.bingce.pay.WxPayV3; |
||||
import com.bingce.surveyor.agentweb.AgentWebActivity; |
||||
import com.bingce.utils.ActivityUtils; |
||||
import com.bingce.utils.DateUtils; |
||||
import com.bingce.utils.StringUtil; |
||||
import com.bingce.utils.Util; |
||||
import com.bingce.utils.VipManager; |
||||
import com.bumptech.glide.Glide; |
||||
import com.huawei.hms.hmsscankit.ScanUtil; |
||||
import com.huawei.hms.hmsscankit.WriterException; |
||||
import com.huawei.hms.ml.scan.HmsBuildBitmapOption; |
||||
import com.huawei.hms.ml.scan.HmsScan; |
||||
|
||||
import org.greenrobot.eventbus.EventBus; |
||||
import org.greenrobot.eventbus.Subscribe; |
||||
import org.greenrobot.eventbus.ThreadMode; |
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.util.Date; |
||||
|
||||
import blankj.utilcode.util.AppUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
import cn.leancloud.LCUser; |
||||
|
||||
public class OpeningRenewalVipActivity extends ColorfulActivity { |
||||
private int total_fee = -1; |
||||
private ImageView qrImageView; |
||||
private int queryCount = 0; |
||||
private int oneMonthPrice = -1, threeMonthsPrice = -1, oneYearPrice = -1; |
||||
private MaterialDialog payingDialog; |
||||
private ActivityOpeningRenewalBinding binding; |
||||
private String orderType = OrderType.ORDER_TYPE_SURVEYOR_365; |
||||
private boolean hasPayResult = false; |
||||
|
||||
@Override |
||||
protected void onCreate(Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityOpeningRenewalBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
setSupportActionBar(binding.getRoot().findViewById(R.id.toolbar)); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
EventBus.getDefault().register(this); |
||||
|
||||
binding.activityOpeningRenewalTvVersion.setText("V" + AppUtils.getAppVersionName()); |
||||
|
||||
if (VipManager.getInstance().expireDate != null) { |
||||
binding.activityOpeningRenewalTvExpirationDate.setText(getString(R.string.current_expiration_date) + ":" + DateUtils.toFull(VipManager.getInstance().expireDate)); |
||||
} else { |
||||
binding.activityOpeningRenewalTvExpirationDate.setText(getString(R.string.current_expiration_date) + ":无"); |
||||
} |
||||
|
||||
binding.activityOpeningRenewalRadiogroup.setOnCheckedChangeListener(new RadioGroup.OnCheckedChangeListener() { |
||||
@Override |
||||
public void onCheckedChanged(RadioGroup group, int checkedId) { |
||||
if (oneMonthPrice <= 0 || threeMonthsPrice <= 0 || oneYearPrice <= 0) { |
||||
ToastUtils.showShort("请先联网获取套餐价格"); |
||||
return; |
||||
} |
||||
if (checkedId == binding.activityOpeningRenewalRadiobuttonOneMonth.getId()) { |
||||
total_fee = oneMonthPrice; |
||||
orderType = OrderType.ORDER_TYPE_SURVEYOR_30; |
||||
} else if (checkedId == binding.activityOpeningRenewalRadiobuttonThreeMonths.getId()) { |
||||
total_fee = threeMonthsPrice; |
||||
orderType = OrderType.ORDER_TYPE_SURVEYOR_90; |
||||
} else if (checkedId == binding.activityOpeningRenewalRadiobuttonOneYear.getId()) { |
||||
total_fee = oneYearPrice; |
||||
orderType = OrderType.ORDER_TYPE_SURVEYOR_365; |
||||
} |
||||
if (total_fee <= 0) { |
||||
binding.activityOpeningRenewalTvTotalFee.setText("联网获取价格"); |
||||
} else { |
||||
binding.activityOpeningRenewalTvTotalFee.setText(Util.formatDouble2StringDotAuto(total_fee / 100.0) + "元"); |
||||
} |
||||
} |
||||
}); |
||||
|
||||
if (VipManager.getInstance().checkReg()) { |
||||
new AlertDialog.Builder(this) |
||||
.setTitle(R.string.hint) |
||||
.setMessage("此手机已经绑定激活,请确定是否需要购买会员,绑定激活和购买会员可以二选其一") |
||||
.setPositiveButton(R.string.i_know, null) |
||||
.show(); |
||||
} |
||||
|
||||
LeanCloudConfigLoader.findInBackground("opening_renewal_fee", instance -> { |
||||
// new LCQuery<>("Configuration")
|
||||
// .whereEqualTo("name", "opening_renewal_fee")
|
||||
// .limit(1)
|
||||
// .findInBackground().subscribe(new Observer<List<LCObject>>() {
|
||||
// @Override
|
||||
// public void onSubscribe(Disposable d) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onNext(List<LCObject> avObjects) {
|
||||
if (!ActivityUtils.isLiving(OpeningRenewalVipActivity.this)) return; |
||||
if (/*avObjects != null && !avObjects.isEmpty() && avObjects.get(0).getString("value") != null*/instance != null && StringUtil.isNotEmpty(instance.value)) { |
||||
String value = /*avObjects.get(0).getString("value")*/instance.value; |
||||
String value2 = /*avObjects.get(0).getString("value2")*/instance.value2; |
||||
String[] valueArr = value.split(","); |
||||
String[] value2Arr = value2.split(","); |
||||
if (valueArr.length == 3 && value2Arr.length == 3) { |
||||
try { |
||||
oneMonthPrice = Integer.parseInt(valueArr[0]); |
||||
threeMonthsPrice = Integer.parseInt(valueArr[1]); |
||||
oneYearPrice = Integer.parseInt(valueArr[2]); |
||||
binding.activityOpeningRenewalRadiobuttonOneMonth.setText(value2Arr[0] + " " + oneMonthPrice / 100.0 + "元"); |
||||
binding.activityOpeningRenewalRadiobuttonThreeMonths.setText(value2Arr[1] + " " + threeMonthsPrice / 100.0 + "元"); |
||||
binding.activityOpeningRenewalRadiobuttonOneYear.setText(value2Arr[2] + " " + oneYearPrice / 100.0 + "元"); |
||||
if (binding.activityOpeningRenewalRadiobuttonOneMonth.isChecked()) { |
||||
total_fee = oneMonthPrice; |
||||
} else if (binding.activityOpeningRenewalRadiobuttonThreeMonths.isChecked()) { |
||||
total_fee = threeMonthsPrice; |
||||
} else if (binding.activityOpeningRenewalRadiobuttonOneYear.isChecked()) { |
||||
total_fee = oneYearPrice; |
||||
} |
||||
if (total_fee <= 0) { |
||||
binding.activityOpeningRenewalTvTotalFee.setText("联网获取价格"); |
||||
} else { |
||||
binding.activityOpeningRenewalTvTotalFee.setText(Util.formatDouble2StringDotAuto(total_fee / 100.0) + "元"); |
||||
} |
||||
} catch (Exception ex) { |
||||
ex.printStackTrace(); |
||||
} |
||||
} |
||||
|
||||
} else { |
||||
binding.activityOpeningRenewalTvTotalFee.setText("联网获取价格"); |
||||
} |
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onError(Throwable e) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onComplete() {
|
||||
//
|
||||
// }
|
||||
}); |
||||
LeanCloudConfigLoader.findInBackground("opening_renewal_activity", instance -> { |
||||
// new LCQuery<>("Configuration")
|
||||
// .whereEqualTo("name", "opening_renewal_activity")
|
||||
// .limit(1)
|
||||
// .findInBackground().subscribe(new Observer<List<LCObject>>() {
|
||||
// @Override
|
||||
// public void onSubscribe(Disposable d) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onNext(List<LCObject> avObjects) {
|
||||
if (!ActivityUtils.isLiving(OpeningRenewalVipActivity.this)) return; |
||||
if (/*avObjects != null && !avObjects.isEmpty() && avObjects.get(0).getString("value") != null*/instance != null && StringUtil.isNotEmpty(instance.value)) { |
||||
String activity = /*avObjects.get(0).getString("value")*/instance.value; |
||||
binding.activityOpeningRenewalTvActivity.setText(activity); |
||||
} |
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onError(Throwable e) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onComplete() {
|
||||
//
|
||||
// }
|
||||
}); |
||||
|
||||
String adsQueryUrl = "android_opening_renewal_vip_img_ads"; |
||||
LeanCloudConfigLoader.findInBackground(adsQueryUrl, instance -> { |
||||
// new LCQuery<>("Configuration")
|
||||
// .whereEqualTo("name", adsQueryUrl)
|
||||
// .limit(1)
|
||||
// .findInBackground()
|
||||
// .subscribe(new Observer<List<LCObject>>() {
|
||||
// @Override
|
||||
// public void onSubscribe(Disposable d) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onNext(List<LCObject> avObjects) {
|
||||
if (!ActivityUtils.isLiving(OpeningRenewalVipActivity.this)) return; |
||||
if (/*avObjects != null && !avObjects.isEmpty()*/instance != null) { |
||||
String adsUrl = /*avObjects.get(0).getString("value")*/instance.value; |
||||
if (adsUrl != null) { |
||||
binding.activityOpeningRenewalImgAds.setVisibility(View.VISIBLE); |
||||
Glide.with(OpeningRenewalVipActivity.this).load(adsUrl).into(binding.activityOpeningRenewalImgAds); |
||||
|
||||
String actionUrl = /*avObjects.get(0).getString("value2")*/instance.value2; |
||||
if (actionUrl != null) { |
||||
binding.activityOpeningRenewalImgAds.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View view) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.setData(Uri.parse(actionUrl));
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2( |
||||
OpeningRenewalVipActivity.this, |
||||
Uri.parse(actionUrl)); |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
} |
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onError(Throwable e) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onComplete() {
|
||||
//
|
||||
// }
|
||||
}); |
||||
|
||||
binding.activityOpeningRenewalBtnTaobaoLink.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", "taobaoUrl");
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2( |
||||
OpeningRenewalVipActivity.this, |
||||
"taobaoUrl"); |
||||
} |
||||
}); |
||||
binding.activityOpeningRenewalBtnContactCustomerService.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", "android_url_contact_author");
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2( |
||||
OpeningRenewalVipActivity.this, |
||||
"android_url_contact_author" |
||||
); |
||||
} |
||||
}); |
||||
|
||||
binding.activityOpeningRenewalBtnWepay.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View view) { |
||||
if (total_fee <= 0) { |
||||
ToastUtils.showShort("请联网获取价格"); |
||||
return; |
||||
} |
||||
binding.activityOpeningRenewalRadiobuttonOneYear.setEnabled(false); |
||||
binding.activityOpeningRenewalRadiobuttonOneMonth.setEnabled(false); |
||||
binding.activityOpeningRenewalRadiobuttonThreeMonths.setEnabled(false); |
||||
showPayListDialog(); |
||||
} |
||||
}); |
||||
|
||||
binding.activityOpeningRenewalBtnOpeningRenewalVipTutorial.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", "android_url_opening_renewal_tutorial");
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2( |
||||
OpeningRenewalVipActivity.this, |
||||
"android_url_opening_renewal_tutorial" |
||||
); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
public void showPayListDialog() { |
||||
if (LCUser.getCurrentUser() == null) { |
||||
ToastUtils.showShort("请重新登录"); |
||||
return; |
||||
} |
||||
if (LCUser.getCurrentUser().getMobilePhoneNumber() == null) { |
||||
ToastUtils.showShort("账号绑定的手机号为空,请绑定后再试"); |
||||
return; |
||||
} |
||||
int fee = total_fee <= 0 ? 50000 : total_fee; |
||||
nativeOrder(fee);//由于云引擎appid是测量员的,所以无法调用app下单,只能二维码下单
|
||||
// new MaterialDialog.Builder(this)
|
||||
// .title(R.string.choose_wechat_pay_type)
|
||||
// .items(new String[]{getString(R.string.wechat_direct_pay), getString(R.string.wechat_qr_pay)})
|
||||
// .itemsCallback(new MaterialDialog.ListCallback() {
|
||||
// @Override
|
||||
// public void onSelection(MaterialDialog dialog, View itemView, int which, CharSequence text) {
|
||||
// switch (which) {
|
||||
// case 0:
|
||||
// appOrder(fee);
|
||||
// break;
|
||||
// case 1:
|
||||
// nativeOrder(fee);
|
||||
// break;
|
||||
// }
|
||||
// binding.activityOpeningRenewalBtnWepay.setEnabled(false);
|
||||
// }
|
||||
// }).show();
|
||||
} |
||||
|
||||
/** |
||||
* 二维码下单 |
||||
* |
||||
* @param fee 金额,单位分 |
||||
*/ |
||||
private void nativeOrder(int fee) { |
||||
WxPayV3.getInstance().generateNativeVipOrder(this, |
||||
LCUser.getCurrentUser().getSessionToken(), |
||||
"导线助手会员", |
||||
fee, |
||||
orderType, |
||||
new WxPayV3.nativeOrderGenerateListener() { |
||||
@Override |
||||
public void onOrderGenerateSuccess(String code_url) { |
||||
showQrCode(code_url); |
||||
} |
||||
|
||||
@Override |
||||
public void onOrderGenerateFailed(String errorMsg) { |
||||
ToastUtils.showLong(errorMsg); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
/** |
||||
* App跳转微信支付,下单 |
||||
* |
||||
* @param fee 金额,单位分 |
||||
*/ |
||||
private void appOrder(int fee) { |
||||
//查询订单是否支付成功
|
||||
payingDialog = new MaterialDialog.Builder(OpeningRenewalVipActivity.this) |
||||
.title(R.string.hint) |
||||
.content("正在支付……稍后请点击\"支付完成\"") |
||||
.positiveText(R.string.pay_over) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
//查询订单是否支付成功
|
||||
queryOrderStatus(); |
||||
} |
||||
}) |
||||
.show(); |
||||
|
||||
WxPayV3.getInstance().generateAppVipOrder(this, |
||||
LCUser.getCurrentUser().getSessionToken(), |
||||
"导线助手会员", |
||||
fee, |
||||
orderType, |
||||
new WxPayV3.appOrderGenerateListener() { |
||||
@Override |
||||
public void onOrderGenerateSuccess() { |
||||
hasPayResult = false; |
||||
WxPayV3.getInstance().pay(); |
||||
} |
||||
|
||||
@Override |
||||
public void onOrderGenerateFailed(String errorMsg) { |
||||
ToastUtils.showLong(errorMsg); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
/** |
||||
* 查询订单支付状态 |
||||
*/ |
||||
private void queryOrderStatus() { |
||||
binding.activityOpeningRenewalBtnWepay.setEnabled(true); |
||||
if (payingDialog != null) |
||||
payingDialog.dismiss(); |
||||
WxPayV3.getInstance().queryVipOrder(this, new WxPayV3.VipOrderQueryListener() { |
||||
@Override |
||||
public void onOrderPaySuccess(String orderType, Date paySuccessDate) { |
||||
VipManager.getInstance().controlSdkRefresh(OpeningRenewalVipActivity.this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
binding.activityOpeningRenewalTvExpirationDate.setText(String.format("%s:%s", getString(R.string.current_expiration_date), DateUtils.toFull(VipManager.getInstance().expireDate))); |
||||
new AlertDialog.Builder(OpeningRenewalVipActivity.this) |
||||
.setTitle(R.string.success) |
||||
.setMessage("续费成功,当前到期时间为" + DateUtils.toFull(VipManager.getInstance().expireDate)) |
||||
.setPositiveButton(R.string.confirm, null) |
||||
.setOnDismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialog) { |
||||
setResult(RESULT_OK); |
||||
finish(); |
||||
} |
||||
}) |
||||
.show(); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
ToastUtils.showShort(getString(R.string.error_code) + ":" + errorCode); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onOrderQueryFailed(String errorMsg) { |
||||
tryQueryPayResultAgain(getString(R.string.pay_failed), errorMsg); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
setResult(RESULT_OK); |
||||
finish(); |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
@Override |
||||
protected void onResume() { |
||||
super.onResume(); |
||||
if (hasPayResult) { |
||||
queryOrderStatus(); |
||||
hasPayResult = false; |
||||
} |
||||
} |
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN) |
||||
public void onMessageEvent(PayOverEvent event) { |
||||
hasPayResult = true; |
||||
} |
||||
|
||||
/** |
||||
* 查询失败后再次显示查询查询 |
||||
*/ |
||||
private void tryQueryPayResultAgain(String title, String message) { |
||||
if (!ActivityUtils.isLiving(this)) { |
||||
return; |
||||
} |
||||
new AlertDialog.Builder(OpeningRenewalVipActivity.this) |
||||
.setTitle(title) |
||||
.setMessage(message) |
||||
.setPositiveButton(R.string.query_again, new DialogInterface.OnClickListener() { |
||||
@Override |
||||
public void onClick(DialogInterface dialog, int which) { |
||||
if (queryCount >= 5) { |
||||
ToastUtils.showLong(R.string.query_times_cannot_bigger_than_five); |
||||
return; |
||||
} |
||||
queryCount++; |
||||
//查询订单是否支付成功
|
||||
queryOrderStatus(); |
||||
} |
||||
}) |
||||
.setNegativeButton(R.string.cancel, null) |
||||
.show(); |
||||
} |
||||
|
||||
/** |
||||
* 生成二维码 |
||||
*/ |
||||
public void showQrCode(String code_url) { |
||||
MaterialDialog dialog = new MaterialDialog.Builder(this) |
||||
.title(R.string.wechat_qr_pay) |
||||
.customView(R.layout.dialog_register_pay_qr_code, false) |
||||
.positiveText(this.getString(R.string.pay_over)) |
||||
.dismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialogInterface) { |
||||
//查询订单是否支付成功
|
||||
queryOrderStatus(); |
||||
} |
||||
}) |
||||
.build(); |
||||
|
||||
qrImageView = dialog.getCustomView().findViewById(R.id.dialog_register_pay_qr_code_imageview); |
||||
try { |
||||
HmsBuildBitmapOption options = new HmsBuildBitmapOption.Creator() |
||||
.setBitmapMargin(1) |
||||
.setBitmapColor(Color.BLACK) |
||||
.setBitmapBackgroundColor(Color.WHITE) |
||||
.create(); |
||||
Bitmap resultImage = ScanUtil.buildBitmap(code_url, HmsScan.QRCODE_SCAN_TYPE, 700, 700, options); |
||||
qrImageView.setImageBitmap(resultImage); |
||||
} catch (WriterException e) { |
||||
ToastUtils.showShort("二维码参数错误!"); |
||||
} |
||||
if (!ActivityUtils.isLiving(this)) { |
||||
return; |
||||
} |
||||
dialog.show(); |
||||
} |
||||
|
||||
@Override |
||||
protected void onDestroy() { |
||||
super.onDestroy(); |
||||
EventBus.getDefault().unregister(this); |
||||
if (payingDialog != null) { |
||||
payingDialog.dismiss(); |
||||
payingDialog = null; |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,171 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.app.ProgressDialog; |
||||
import android.content.DialogInterface; |
||||
import android.graphics.Color; |
||||
import android.os.Bundle; |
||||
import android.text.Editable; |
||||
import android.text.TextWatcher; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.view.View.OnClickListener; |
||||
|
||||
import androidx.appcompat.app.AlertDialog; |
||||
|
||||
import com.bingce.AppChannel; |
||||
import com.bingce.activity.VipCloudFunction; |
||||
import com.bingce.controlapphelper.util.HideKeyUtil; |
||||
import com.bingce.controlapphelper.util.SettingValueUtil; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityRedeemBinding; |
||||
import com.bingce.utils.DateUtils; |
||||
import com.bingce.utils.VipManager; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.util.Date; |
||||
|
||||
import blankj.utilcode.util.AppUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
import cn.leancloud.LCObject; |
||||
import cn.leancloud.LCUser; |
||||
|
||||
public class RedeemVipActivity extends ColorfulActivity { |
||||
private ProgressDialog progressDialog; |
||||
private LCObject cashVoucherLCObject; |
||||
private ActivityRedeemBinding binding; |
||||
|
||||
@Override |
||||
protected void onCreate(Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityRedeemBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
setSupportActionBar(binding.getRoot().findViewById(R.id.toolbar)); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
initMaterialEditTextColor(); |
||||
|
||||
binding.activityRedeemTvVersion.setText("V" + AppUtils.getAppVersionName()); |
||||
|
||||
if (LCUser.getCurrentUser() != null) { |
||||
if (VipManager.getInstance().expireDate != null) { |
||||
binding.activityRedeemTvExpirationDate.setText(getString(R.string.current_expiration_date) + ":" + DateUtils.toFull(VipManager.getInstance().expireDate)); |
||||
} else { |
||||
binding.activityRedeemTvExpirationDate.setText(getString(R.string.current_expiration_date) + ":无"); |
||||
} |
||||
} else { |
||||
ToastUtils.showShort(R.string.not_log_in); |
||||
finish(); |
||||
} |
||||
|
||||
if (VipManager.getInstance().checkReg()) { |
||||
new AlertDialog.Builder(this) |
||||
.setTitle(R.string.hint) |
||||
.setMessage("此手机已经绑定激活,请确定是否需要购买会员,绑定激活和购买会员可以二选其一") |
||||
.setPositiveButton(R.string.i_know, null) |
||||
.show(); |
||||
} |
||||
|
||||
binding.activityRedeemMetRedeemCode.addTextChangedListener(new TextWatcher() { |
||||
@Override |
||||
public void beforeTextChanged(CharSequence s, int start, int count, int after) { |
||||
} |
||||
|
||||
@Override |
||||
public void onTextChanged(CharSequence s, int start, int before, int count) { |
||||
} |
||||
|
||||
@Override |
||||
public void afterTextChanged(Editable s) { |
||||
binding.activityRedeemBtnRedeem.setEnabled(!"".equals(binding.activityRedeemMetRedeemCode.getText().toString().trim())); |
||||
} |
||||
}); |
||||
|
||||
binding.activityRedeemBtnRedeem.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
if (LCUser.getCurrentUser() == null) { |
||||
ToastUtils.showShort(R.string.not_log_in); |
||||
return; |
||||
} |
||||
HideKeyUtil.hideSoftInput(); |
||||
if (binding.activityRedeemMetRedeemCode.getText().toString().trim().length() != 24) { |
||||
ToastUtils.showShort(R.string.cash_voucher_code_length_must_be_24); |
||||
return; |
||||
} |
||||
|
||||
progressDialog = new ProgressDialog(RedeemVipActivity.this); |
||||
progressDialog.setMessage(getString(R.string.please_wait)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
|
||||
String cashVoucherCode = binding.activityRedeemMetRedeemCode.getText().toString().trim().toLowerCase(); |
||||
VipCloudFunction.redeemVip(LCUser.getCurrentUser().getSessionToken(), cashVoucherCode, AppChannel.customChannel, new VipCloudFunction.OnRedeemVipListener() { |
||||
@Override |
||||
public void onRedeemSuccess(Date newExpireDate) { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
savePayLog(cashVoucherCode, newExpireDate); |
||||
|
||||
new AlertDialog.Builder(RedeemVipActivity.this) |
||||
.setTitle(R.string.success) |
||||
.setMessage("续费成功,当前到期时间为" + DateUtils.toFull(newExpireDate)) |
||||
.setPositiveButton(R.string.confirm, null) |
||||
.setOnDismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialog) { |
||||
setResult(RESULT_OK); |
||||
finish(); |
||||
} |
||||
}) |
||||
.show(); |
||||
} |
||||
|
||||
@Override |
||||
public void onRedeemFailed(String errorMsg) { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(errorMsg); |
||||
} |
||||
}); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
private void savePayLog(String cashVoucher, Date newExpireDate) { |
||||
final LCObject payLog = new LCObject("PayLog"); |
||||
payLog.put("payFor", "兑换会员"); |
||||
payLog.put("user", LCUser.getCurrentUser()); |
||||
payLog.put("currentExpireDate", newExpireDate); |
||||
payLog.put("client", "android"); |
||||
payLog.put("channel", "cashVoucher"); |
||||
payLog.put("total_fee", "0"); |
||||
payLog.put("cash_fee", "0"); |
||||
payLog.put("versionCode", AppUtils.getAppVersionCode()); |
||||
payLog.put("cashVoucher", cashVoucher); |
||||
payLog.saveInBackground().subscribe(); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
finish(); |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
private void initMaterialEditTextColor() { |
||||
if (SettingValueUtil.isThemeDark()) { |
||||
binding.activityRedeemMetRedeemCode.setMetTextColor(Color.WHITE); |
||||
|
||||
binding.activityRedeemMetRedeemCode.setPrimaryColor(Color.LTGRAY); |
||||
|
||||
binding.activityRedeemMetRedeemCode.setFocusFraction(1.0f); |
||||
|
||||
binding.activityRedeemMetRedeemCode.setMetHintTextColor(Color.GRAY); |
||||
|
||||
binding.activityRedeemMetRedeemCode.setUnderlineColor(Color.GRAY); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,488 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.Manifest; |
||||
import android.app.Activity; |
||||
import android.app.ProgressDialog; |
||||
import android.content.Context; |
||||
import android.content.DialogInterface; |
||||
import android.content.Intent; |
||||
import android.content.pm.PackageManager; |
||||
import android.graphics.Bitmap; |
||||
import android.graphics.Color; |
||||
import android.os.Build; |
||||
import android.os.Bundle; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.view.View.OnClickListener; |
||||
import android.widget.Button; |
||||
import android.widget.ImageView; |
||||
import android.widget.TextView; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.appcompat.app.AlertDialog; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
import androidx.core.content.ContextCompat; |
||||
|
||||
import com.afollestad.materialdialogs.DialogAction; |
||||
import com.afollestad.materialdialogs.MaterialDialog; |
||||
import com.bingce.controlapphelper.util.SettingValueUtil; |
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.data.sync.utils.LeanCloudConfigLoader; |
||||
import com.bingce.device.enums.SpecialDeviceEnum; |
||||
import com.bingce.device.ui.dialog.DialogUtil; |
||||
import com.bingce.surveyor.agentweb.AgentWebActivity; |
||||
import com.bingce.utils.AppUtil; |
||||
import com.bingce.utils.ClipboardUtils; |
||||
import com.bingce.utils.PropertiesGet; |
||||
import com.bingce.utils.RegisterUtil; |
||||
import com.bingce.utils.SdkUtils; |
||||
import com.bingce.utils.StringUtil; |
||||
import com.bingce.utils.Util; |
||||
import com.bingce.utils.VipManager; |
||||
import com.hjq.permissions.OnPermissionCallback; |
||||
import com.hjq.permissions.Permission; |
||||
import com.hjq.permissions.XXPermissions; |
||||
import com.huawei.hms.hmsscankit.ScanUtil; |
||||
import com.huawei.hms.hmsscankit.WriterException; |
||||
import com.huawei.hms.ml.scan.HmsBuildBitmapOption; |
||||
import com.huawei.hms.ml.scan.HmsScan; |
||||
import com.rengwuxian.materialedittext.MaterialEditText; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.util.List; |
||||
import java.util.Locale; |
||||
|
||||
import blankj.utilcode.util.AppUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
import cn.leancloud.LCException; |
||||
import cn.leancloud.LCObject; |
||||
import cn.leancloud.LCQuery; |
||||
import cn.leancloud.LCUser; |
||||
import io.reactivex.Observer; |
||||
import io.reactivex.disposables.Disposable; |
||||
|
||||
public class RegisterActivity extends ColorfulActivity { |
||||
private MaterialEditText met_machine_code, met_activate_code; |
||||
private Button mBtnCopy, mBtnActivate, mBtnTaobaoLink, mBtnContactAuthor, mBtnMachineQr, mBtnActivateTutorial; |
||||
private TextView mTextViewActivity, mTextViewVersion; |
||||
private String mMachineCode = "", mOriginalMachineCode = ""; |
||||
private Toolbar mToolbar; |
||||
boolean hasAndroidPermission = false; |
||||
private ProgressDialog progressDialog; |
||||
private ImageView qrImageView; |
||||
|
||||
@Override |
||||
protected void onCreate(Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
setContentView(R.layout.activity_activate); |
||||
mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
initWidget(); |
||||
initMaterialEditTextColor(); |
||||
|
||||
mTextViewVersion.setText("V" + AppUtils.getAppVersionName()); |
||||
|
||||
if (!AppUtil.isZh() && SdkUtils.isRegCodeValidate() && !SdkUtils.isIntlCodeValidate()) {//非中文环境需要国际许可码
|
||||
DialogUtil.mDismissAlertDialog(this, R.string.hint, R.string.you_need_apply_for_an_international_license_code, R.string.i_know, null, null); |
||||
} |
||||
|
||||
boolean isSpecial = false; |
||||
for (SpecialDeviceEnum device : SpecialDeviceEnum.values()) { |
||||
if (device.getModel().equals(PropertiesGet.getModel()) |
||||
&& device.getDevice().equals(PropertiesGet.getDevice()) |
||||
&& device.getBoard().equals(PropertiesGet.getBoard()) |
||||
&& device.getBrand().equals(PropertiesGet.getBrand()) |
||||
&& device.getCpuAbi().equals(PropertiesGet.getCpuAbi()) |
||||
&& device.getHardware().equals(PropertiesGet.getHardware()) |
||||
&& device.getManufacturer().equals(PropertiesGet.getManufacturer())) { |
||||
isSpecial = true; |
||||
break; |
||||
} |
||||
} |
||||
if (!isSpecial && Build.VERSION.SDK_INT >= 29) { |
||||
mBtnTaobaoLink.setVisibility(View.GONE); |
||||
new AlertDialog.Builder(this) |
||||
.setMessage("由于安卓10及以上系统限制App读取硬件信息,原来绑定手机激活的方式已经不可用,如果您之前绑定手机激活过,很遗憾,现在只能刷机降级到安卓9或安卓8重新输入激活才可以。如果您不想刷机,可以购买会员继续使用") |
||||
.setPositiveButton(R.string.user_vip_activate, new DialogInterface.OnClickListener() { |
||||
@Override |
||||
public void onClick(DialogInterface dialog, int which) { |
||||
if (LCUser.getCurrentUser() == null) { |
||||
Intent intent = new Intent(Utils.getApp(), LoginActivity.class); |
||||
intent.putExtra("finishTo", UserInfoActivity.class.getName()); |
||||
startActivity(intent); |
||||
} else { |
||||
startActivity(new Intent(RegisterActivity.this, UserInfoActivity.class)); |
||||
} |
||||
} |
||||
}) |
||||
.setNeutralButton(R.string.opening_vip_tutorial, new DialogInterface.OnClickListener() { |
||||
@Override |
||||
public void onClick(DialogInterface dialog, int which) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", "android_url_opening_renewal_tutorial");
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2(RegisterActivity.this, |
||||
"android_url_opening_renewal_tutorial"); |
||||
} |
||||
}) |
||||
.setNegativeButton(R.string.cancel, null) |
||||
.setOnDismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialog) { |
||||
if (!hasAndroidPermission) |
||||
finish(); |
||||
} |
||||
}).show(); |
||||
} else { |
||||
int checkStoragePermission = ContextCompat.checkSelfPermission(Utils.getApp(), Manifest.permission.READ_PHONE_STATE); |
||||
if (checkStoragePermission != PackageManager.PERMISSION_GRANTED) { |
||||
requestPhoneStatePermission(this); |
||||
} else { |
||||
if ("".equals(RegisterUtil.getOriginalMachineCode()) || "SERIALNUMBERunknown".equals(RegisterUtil.getOriginalMachineCode()) || "SERIALNUMBERnull".equals(RegisterUtil.getOriginalMachineCode())) { |
||||
new MaterialDialog.Builder(this) |
||||
.title(R.string.hint) |
||||
.content("此手机机器码未知,请关闭相关限制软件请重启软件") |
||||
.positiveText(R.string.i_know) |
||||
.dismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialog) { |
||||
finish(); |
||||
} |
||||
}).show(); |
||||
} |
||||
} |
||||
} |
||||
if (VipManager.getInstance().checkReg()) { |
||||
getSupportActionBar().setTitle(R.string.activated); |
||||
met_activate_code.setText(((App) Utils.getApp()).registerCodeV2); |
||||
mBtnActivate.setEnabled(false); |
||||
met_activate_code.setEnabled(false); |
||||
mBtnActivate.setText(R.string.activated); |
||||
} |
||||
|
||||
mMachineCode = RegisterUtil.getEncryptMachineCodeInfo(); |
||||
mOriginalMachineCode = RegisterUtil.getOriginalMachineCode(); |
||||
if (mMachineCode != null) { |
||||
met_machine_code.setText(mMachineCode); |
||||
} else { |
||||
met_machine_code.setText(getString(R.string.get_machine_code_fail)); |
||||
} |
||||
String queryUrl = "activate_activity_for_control_network"; |
||||
LeanCloudConfigLoader.findInBackground(queryUrl, instance -> { |
||||
// new LCQuery<>("Configuration")
|
||||
// .whereEqualTo("name", queryUrl)
|
||||
// .limit(1)
|
||||
// .findInBackground()
|
||||
// .subscribe(new Observer<List<LCObject>>() {
|
||||
// @Override
|
||||
// public void onSubscribe(Disposable d) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onNext(List<LCObject> avObjects) {
|
||||
if (isFinishing()) return; |
||||
if (/*avObjects != null && !avObjects.isEmpty() && avObjects.get(0).getString("value") != null*/instance != null && StringUtil.isNotEmpty(instance.value)) { |
||||
String activity = /*avObjects.get(0).getString("value")*/instance.value; |
||||
mTextViewActivity.setText(activity); |
||||
} |
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onError(Throwable e) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// @Override
|
||||
// public void onComplete() {
|
||||
//
|
||||
// }
|
||||
}); |
||||
mBtnCopy.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View arg0) { |
||||
if (mMachineCode != null) { |
||||
ClipboardUtils.copyText(mMachineCode); |
||||
ToastUtils.showShort(R.string.has_copy_to_clipboard); |
||||
} else { |
||||
ToastUtils.showShort(R.string.get_machine_code_fail); |
||||
} |
||||
} |
||||
}); |
||||
mBtnActivate.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View arg0) { |
||||
final String registerCode = met_activate_code.getText().toString().trim().toUpperCase(Locale.CHINA).replaceAll(" |\n|\r", ""); |
||||
if (mMachineCode == null) { |
||||
ToastUtils.showShort(R.string.machine_code_illegal); |
||||
return; |
||||
} |
||||
if ("".equals(met_activate_code.getText().toString().trim())) { |
||||
ToastUtils.showShort(R.string.please_input_register_code); |
||||
return; |
||||
} |
||||
if (registerCode.length() != 16) { |
||||
ToastUtils.showShort(R.string.register_code_is_16_characters); |
||||
return; |
||||
} |
||||
progressDialog = new ProgressDialog(RegisterActivity.this); |
||||
progressDialog.setMessage(getString(R.string.please_wait)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
|
||||
new LCQuery<>("DeviceBlacklist") |
||||
.whereEqualTo("machineCode", mOriginalMachineCode) |
||||
.limit(1) |
||||
.findInBackground().subscribe(new Observer<List<LCObject>>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(List<LCObject> avObjects) { |
||||
if (isFinishing()) return; |
||||
if (avObjects == null || avObjects.isEmpty()) { |
||||
new LCQuery<>("Device") |
||||
.whereEqualTo("machineCode", mOriginalMachineCode) |
||||
.whereEqualTo("controlRegCode", registerCode) |
||||
.limit(1) |
||||
.findInBackground().subscribe(new Observer<List<LCObject>>() { |
||||
@Override |
||||
public void onSubscribe(Disposable disposable) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(List<LCObject> lcObjects) { |
||||
if (isFinishing()) return; |
||||
if (!lcObjects.isEmpty()) { |
||||
if (lcObjects.get(0).getBoolean("activated") && !lcObjects.get(0).getBoolean("converted")) { |
||||
((App) Utils.getApp()).registerCodeV2 = registerCode; |
||||
Util.putPreference("registerCodeV2", registerCode); |
||||
|
||||
VipManager.getInstance().controlSdkRefresh(RegisterActivity.this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
progressDialog.dismiss(); |
||||
getSupportActionBar().setTitle(R.string.activated); |
||||
mBtnActivate.setEnabled(false); |
||||
met_activate_code.setEnabled(false); |
||||
ToastUtils.showShort(R.string.activate_success); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(getString(R.string.error_code) + ":" + errorCode); |
||||
} |
||||
}); |
||||
//激活次数+1
|
||||
lcObjects.get(0).increment("activationTimes"); |
||||
lcObjects.get(0).saveInBackground().subscribe(); |
||||
} else if (lcObjects.get(0).getBoolean("converted")) { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort("此设备已经兑换过年会员,无法再绑定手机"); |
||||
} else if (!lcObjects.get(0).getBoolean("activated")) { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort("无法激活,请联系开发人员"); |
||||
} else { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(R.string.cloud_has_not_register_code); |
||||
} |
||||
} else { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort("激活码无效"); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable throwable) { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(getString(R.string.error_code) + ":" + new LCException(throwable).getCode()); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} else { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(R.string.you_are_in_blacklist); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(getString(R.string.activate_need_to_connect_to_the_internet) + "," + getString(R.string.error_code) + ":" + new LCException(e).getCode()); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
}); |
||||
mBtnTaobaoLink.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", "taobaoUrl");
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2(RegisterActivity.this, "taobaoUrl"); |
||||
} |
||||
}); |
||||
mBtnContactAuthor.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", "android_url_contact_author");
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2(RegisterActivity.this, |
||||
"android_url_contact_author"); |
||||
} |
||||
}); |
||||
|
||||
mBtnMachineQr.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View view) { |
||||
if (!mMachineCode.isEmpty()) |
||||
showMachineCodeQr(mMachineCode); |
||||
} |
||||
}); |
||||
|
||||
mBtnActivateTutorial.setOnClickListener(new OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
// Intent intent = new Intent();
|
||||
// intent.setClass(Utils.getApp(), AgentWebActivity.class);
|
||||
// intent.putExtra("short_url", "android_url_activate_tutorial");
|
||||
// startActivity(intent);
|
||||
AgentWebActivity.navigation2( |
||||
RegisterActivity.this, |
||||
"android_url_activate_tutorial"); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
private void initWidget() { |
||||
met_machine_code = findViewById(R.id.activity_activate_met_machine_code); |
||||
met_activate_code = findViewById(R.id.activity_activate_met_activate_code); |
||||
mBtnCopy = findViewById(R.id.activity_activate_btn_copy); |
||||
mBtnActivate = findViewById(R.id.activity_activate_btn_activate); |
||||
mBtnTaobaoLink = findViewById(R.id.activity_activate_btn_taobao_link); |
||||
mBtnContactAuthor = findViewById(R.id.activity_activate_btn_contact_customer_service); |
||||
mBtnMachineQr = findViewById(R.id.activity_activate_btn_machine_code_qr_code); |
||||
mBtnActivateTutorial = findViewById(R.id.activity_activate_btn_activate_tutorial); |
||||
mTextViewActivity = findViewById(R.id.activity_activate_tv_activity); |
||||
mTextViewVersion = findViewById(R.id.activity_activate_tv_version); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
if (item.getItemId() == android.R.id.home) { |
||||
finish(); |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
public void onActivityResult(int requestCode, int resultCode, Intent data) { |
||||
super.onActivityResult(requestCode, resultCode, data); |
||||
if (requestCode == 12) { |
||||
if (resultCode == Activity.RESULT_OK) { |
||||
met_activate_code.setText(((App) Utils.getApp()).registerCodeV2); |
||||
getSupportActionBar().setTitle(R.string.activated); |
||||
mBtnActivate.setEnabled(false); |
||||
met_activate_code.setEnabled(false); |
||||
} |
||||
} |
||||
} |
||||
|
||||
private void initMaterialEditTextColor() { |
||||
if (SettingValueUtil.isThemeDark()) { |
||||
met_machine_code.setMetTextColor(Color.WHITE); |
||||
met_activate_code.setMetTextColor(Color.WHITE); |
||||
|
||||
met_machine_code.setPrimaryColor(Color.LTGRAY); |
||||
met_activate_code.setPrimaryColor(Color.LTGRAY); |
||||
|
||||
met_machine_code.setFocusFraction(1.0f); |
||||
met_activate_code.setFocusFraction(1.0f); |
||||
|
||||
met_machine_code.setMetHintTextColor(Color.GRAY); |
||||
met_activate_code.setMetHintTextColor(Color.GRAY); |
||||
|
||||
met_machine_code.setUnderlineColor(Color.GRAY); |
||||
met_activate_code.setUnderlineColor(Color.GRAY); |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 生成机器码的二维码 |
||||
*/ |
||||
public void showMachineCodeQr(String mMachineCode) { |
||||
MaterialDialog dialog = new MaterialDialog.Builder(this) |
||||
.title(R.string.machine_code) |
||||
.customView(R.layout.dialog_machine_code_qr_code, false) |
||||
.positiveText(this.getString(R.string.close)) |
||||
.build(); |
||||
|
||||
qrImageView = dialog.getCustomView().findViewById(R.id.dialog_machine_code_qr_code_imageview); |
||||
try { |
||||
HmsBuildBitmapOption options = new HmsBuildBitmapOption.Creator() |
||||
.setBitmapMargin(1) |
||||
.setBitmapColor(Color.BLACK) |
||||
.setBitmapBackgroundColor(Color.WHITE) |
||||
.create(); |
||||
Bitmap resultImage = ScanUtil.buildBitmap(mMachineCode, HmsScan.QRCODE_SCAN_TYPE, 700, 700, options); |
||||
qrImageView.setImageBitmap(resultImage); |
||||
} catch (WriterException e) { |
||||
ToastUtils.showShort("二维码参数错误!"); |
||||
} |
||||
dialog.show(); |
||||
} |
||||
|
||||
public static void requestPhoneStatePermission(Context context) { |
||||
new MaterialDialog.Builder(context) |
||||
.title(R.string.mobile_phone_permissions) |
||||
.content(R.string.verify_imei_imsi_code_to_prevent_account_theft) |
||||
.canceledOnTouchOutside(false) |
||||
.positiveText(R.string.to_allow) |
||||
.negativeText(R.string.refuse) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
XXPermissions.with(context) |
||||
.permission(Permission.READ_PHONE_STATE) |
||||
.request(new OnPermissionCallback() { |
||||
@Override |
||||
public void onGranted(List<String> permissions, boolean all) { |
||||
} |
||||
|
||||
@Override |
||||
public void onDenied(List<String> permissions, boolean never) { |
||||
if (never) { |
||||
ToastUtils.showShort(R.string.manually_enable_the_phone_state_permission_to_bind_hardware_devices); |
||||
} else { |
||||
ToastUtils.showShort(R.string.please_open_permission_to_activation); |
||||
requestPhoneStatePermission(context); |
||||
} |
||||
} |
||||
}); |
||||
} |
||||
}) |
||||
.show(); |
||||
} |
||||
} |
@ -0,0 +1,781 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.Manifest; |
||||
import android.annotation.SuppressLint; |
||||
import android.app.ProgressDialog; |
||||
import android.content.DialogInterface; |
||||
import android.content.Intent; |
||||
import android.content.pm.PackageManager; |
||||
import android.graphics.Bitmap; |
||||
import android.graphics.Color; |
||||
import android.net.Uri; |
||||
import android.os.Bundle; |
||||
import android.text.Editable; |
||||
import android.text.TextWatcher; |
||||
import android.util.Log; |
||||
import android.view.LayoutInflater; |
||||
import android.view.Menu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.widget.Button; |
||||
import android.widget.ImageView; |
||||
import android.widget.TextView; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.app.AlertDialog; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
import androidx.core.app.ActivityCompat; |
||||
import androidx.core.content.ContextCompat; |
||||
|
||||
import com.afollestad.materialdialogs.DialogAction; |
||||
import com.afollestad.materialdialogs.MaterialDialog; |
||||
import com.afollestad.materialdialogs.internal.MDButton; |
||||
import com.bingce.AppChannel; |
||||
import com.bingce.controlapphelper.util.SettingValueUtil; |
||||
import com.bingce.controlnetwork.App; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.DialogEditNicknameBinding; |
||||
import com.bingce.controlnetwork.ui.WechatImagePicker; |
||||
import com.bingce.utils.DateUtils; |
||||
import com.bingce.utils.FileUtil; |
||||
import com.bingce.utils.LCDeviceUtil; |
||||
import com.bingce.utils.ServiceDateUtils; |
||||
import com.bingce.utils.ValidateUtil; |
||||
import com.bingce.utils.VipManager; |
||||
import com.bumptech.glide.Glide; |
||||
import com.leon.lib.settingview.LSettingItem; |
||||
import com.qingmei2.rximagepicker.core.RxImagePicker; |
||||
import com.qingmei2.rximagepicker.entity.Result; |
||||
import com.qingmei2.rximagepicker_extension.MimeType; |
||||
import com.qingmei2.rximagepicker_extension_wechat.WechatConfigrationBuilder; |
||||
import com.qingmei2.rximagepicker_extension_wechat.ui.WechatImagePickerFragment; |
||||
import com.yalantis.ucrop.UCrop; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.io.File; |
||||
import java.io.FileNotFoundException; |
||||
import java.io.IOException; |
||||
import java.util.Date; |
||||
import java.util.List; |
||||
|
||||
import blankj.utilcode.util.StringUtils; |
||||
import blankj.utilcode.util.ToastUtils; |
||||
import blankj.utilcode.util.Utils; |
||||
import cn.leancloud.LCFile; |
||||
import cn.leancloud.LCObject; |
||||
import cn.leancloud.LCQuery; |
||||
import cn.leancloud.LCUser; |
||||
import de.hdodenhof.circleimageview.CircleImageView; |
||||
import id.zelory.compressor.Compressor; |
||||
import io.reactivex.Observer; |
||||
import io.reactivex.disposables.Disposable; |
||||
import io.reactivex.functions.Consumer; |
||||
|
||||
public class UserInfoActivity extends ColorfulActivity { |
||||
private static final String TAG = "UserInfoActivity"; |
||||
private static final int REQUEST_CODE_ASK_CAMERA = 166; |
||||
private static final int REQUEST_CODE_UPDATE_USER_INFO = 11; |
||||
private Toolbar mToolbar; |
||||
private CircleImageView avatarImageView; |
||||
private TextView tv_nick_name; |
||||
private ImageView tv_nick_name_edit; |
||||
private MDButton mPositiveAction; |
||||
private LSettingItem item_phone, item_email, item_user_level, item_expiration, item_bound_device, item_control_level, item_control_expiration; |
||||
private WechatImagePicker rxImagePicker; |
||||
private Button btn_log_out, btn_opening_renewal; |
||||
private ProgressDialog progressDialog; |
||||
private boolean buy = false; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
setContentView(R.layout.activity_user_info); |
||||
mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) |
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
buy = getIntent().getBooleanExtra("buy", false); |
||||
|
||||
rxImagePicker = RxImagePicker.create(WechatImagePicker.class); |
||||
|
||||
avatarImageView = findViewById(R.id.activity_user_info_avatar_image); |
||||
tv_nick_name = findViewById(R.id.activity_user_info_nick_name); |
||||
tv_nick_name_edit = findViewById(R.id.activity_user_info_nick_name_edit); |
||||
item_phone = findViewById(R.id.activity_user_info_item_phone); |
||||
item_email = findViewById(R.id.activity_user_info_item_email); |
||||
item_user_level = findViewById(R.id.activity_user_info_item_user_level); |
||||
item_expiration = findViewById(R.id.activity_user_info_item_expiration_date); |
||||
item_bound_device = findViewById(R.id.activity_user_info_item_bound_device); |
||||
item_control_level = findViewById(R.id.activity_user_info_item_control_level); |
||||
item_control_expiration = findViewById(R.id.activity_user_info_item_control_expiration_date); |
||||
btn_opening_renewal = findViewById(R.id.activity_user_info_btn_opening_renewal); |
||||
btn_log_out = findViewById(R.id.activity_user_info_btn_log_out); |
||||
|
||||
updateUserInfo(); |
||||
|
||||
avatarImageView.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
showProfileAvatarChangeDialog(); |
||||
} |
||||
}); |
||||
tv_nick_name.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
showEditNicknameDialog(); |
||||
} |
||||
}); |
||||
tv_nick_name_edit.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
showEditNicknameDialog(); |
||||
} |
||||
}); |
||||
item_phone.setOnSettingItemClick(new LSettingItem.onSettingItemClick() { |
||||
@Override |
||||
public void click(boolean isChecked) { |
||||
if (!LCUser.getCurrentUser().isMobilePhoneVerified()) { |
||||
// Intent intent = new Intent(Utils.getApp(), MobilePhoneVerifyActivity.class);
|
||||
// startActivity(intent);
|
||||
} |
||||
} |
||||
}); |
||||
btn_log_out.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
LCUser.logOut(); |
||||
ToastUtils.showShort(R.string.log_out); |
||||
VipManager.getInstance().controlSdkRefresh(UserInfoActivity.this, ((App) Utils.getApp()).registerCodeV2, null); |
||||
((App) Utils.getApp()).isUserStatusChanged = true;//返回MainActivity时updateHeaderResult
|
||||
finish(); |
||||
} |
||||
}); |
||||
btn_opening_renewal.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View v) { |
||||
if (AppChannel.customChannel != AppChannel.CUSTOM_CONTROL_PUBLIC) { |
||||
new AlertDialog.Builder(UserInfoActivity.this) |
||||
.setTitle(R.string.hint) |
||||
.setMessage("定制版本无法续费,只能以绑定手机形式使用") |
||||
.setPositiveButton(R.string.i_know, null) |
||||
.show(); |
||||
} else if (LCUser.getCurrentUser().getInt("level") == 0 || LCUser.getCurrentUser().getInt("level") == 1) { |
||||
startActivityForResult(new Intent(UserInfoActivity.this, OpeningRenewalVipActivity.class), REQUEST_CODE_UPDATE_USER_INFO); |
||||
} else { |
||||
ToastUtils.showShort("当前会员模式不支持续费,请联系开发者"); |
||||
} |
||||
} |
||||
}); |
||||
|
||||
item_bound_device.setOnSettingItemClick(new LSettingItem.onSettingItemClick() { |
||||
@Override |
||||
public void click(boolean isChecked) { |
||||
unbind(); |
||||
} |
||||
}); |
||||
|
||||
if (buy) { |
||||
btn_opening_renewal.performClick(); |
||||
} |
||||
} |
||||
|
||||
private void unbind() { |
||||
if (LCUser.getCurrentUser() != null) { |
||||
progressDialog = new ProgressDialog(UserInfoActivity.this); |
||||
progressDialog.setMessage(getString(R.string.please_wait)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
|
||||
ServiceDateUtils.getServerDate(new DateUtils.OnServerDateCallBack() { |
||||
@Override |
||||
public void get(Date serverDate) { |
||||
if (isFinishing()) return; |
||||
//查询条件为:查询今年开始时间,查询开年来的解绑次数
|
||||
Date startOfAYear = DateUtils.addDayOfMonth(serverDate, -365, false, false); |
||||
|
||||
LCQuery<LCObject> unbindDeviceQuery = new LCQuery<>("UnbindDevice"); |
||||
unbindDeviceQuery.whereEqualTo("user", LCUser.getCurrentUser()); |
||||
unbindDeviceQuery.limit(15) |
||||
.whereGreaterThan("updatedAt", startOfAYear) |
||||
.findInBackground().subscribe(new Observer<List<LCObject>>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(List<LCObject> avObjects) { |
||||
progressDialog.dismiss(); |
||||
if (avObjects != null) { |
||||
int totalTimes = 0; |
||||
if (LCUser.getCurrentUser().getInt("level") == 1) { |
||||
totalTimes = 5; |
||||
} else if (LCUser.getCurrentUser().getInt("level") == 10) { |
||||
totalTimes = 10; |
||||
} |
||||
final int leftTimes = Math.max(totalTimes - avObjects.size(), 0); |
||||
new MaterialDialog.Builder(UserInfoActivity.this) |
||||
.title(R.string.unbind_device) |
||||
.content(getString(R.string.number_of_untying_opportunities_at_your_membership_level) + ":" + totalTimes + "\n" |
||||
+ getString(R.string.your_remaining_untying_times_remain) + ":" + leftTimes) |
||||
.positiveText(R.string.unbind_device) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) { |
||||
if (leftTimes > 0) { |
||||
progressDialog = new ProgressDialog(UserInfoActivity.this); |
||||
progressDialog.setMessage(getString(R.string.please_wait)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
|
||||
LCObject unbindDevice = new LCObject("UnbindDevice"); |
||||
unbindDevice.put("user", LCUser.getCurrentUser()); |
||||
if (LCUser.getCurrentUser().get("controlBoundDevice") != null) |
||||
unbindDevice.put("oldDevice", LCUser.getCurrentUser().get("controlBoundDevice")); |
||||
unbindDevice.put("success", true); |
||||
unbindDevice.saveInBackground().subscribe(new Observer<LCObject>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCObject avObject) { |
||||
LCUser.getCurrentUser().remove("controlBoundDevice"); |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(new Observer<LCObject>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCObject avObject) { |
||||
if (VipManager.getInstance().isControlBoundDevice) { |
||||
LCUser.logOut(); |
||||
VipManager.getInstance().controlSdkRefresh(UserInfoActivity.this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
progressDialog.dismiss(); |
||||
new MaterialDialog.Builder(UserInfoActivity.this) |
||||
.title(R.string.unbind_device_success) |
||||
.content(R.string.unbind_device_success_next_to_do) |
||||
.positiveText(R.string.i_know) |
||||
.dismissListener(new DialogInterface.OnDismissListener() { |
||||
@Override |
||||
public void onDismiss(DialogInterface dialog) { |
||||
((App) Utils.getApp()).isUserStatusChanged = true;//返回MainActivity时updateHeaderResult
|
||||
finish(); |
||||
} |
||||
}) |
||||
.show(); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
progressDialog.dismiss(); |
||||
} |
||||
}); |
||||
} else { |
||||
LCDeviceUtil.updateDeviceInfo("controlnetwork", ((App) Utils.getApp()).registerCodeV2, new LCDeviceUtil.OnDeviceUpdateListener() { |
||||
@Override |
||||
public void onUpdateSuccess() { |
||||
VipManager.getInstance().controlSdkRefresh(UserInfoActivity.this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
progressDialog.dismiss(); |
||||
item_bound_device.setRightText(VipManager.getInstance().boundName); |
||||
ToastUtils.showShort(R.string.unbind_device_success); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(getString(R.string.error_code) + ":" + errorCode); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onUpdateFailed() { |
||||
progressDialog.dismiss(); |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
progressDialog.dismiss(); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
progressDialog.dismiss(); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} else { |
||||
ToastUtils.showLong(R.string.your_remaining_untying_times_remain_is_zero); |
||||
} |
||||
} |
||||
}) |
||||
.negativeText(R.string.cancel) |
||||
.show(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
progressDialog.dismiss(); |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void error(Throwable throwable) { |
||||
progressDialog.dismiss(); |
||||
Log.d("error", "unbind_device"); |
||||
ToastUtils.showShort(R.string.get_server_date_failed); |
||||
} |
||||
}); |
||||
} else { |
||||
ToastUtils.showShort(R.string.you_are_not_vip_no_need_unbind); |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 刷新用户信息 |
||||
*/ |
||||
private void updateUserInfo() { |
||||
if (LCUser.getCurrentUser() != null) { |
||||
if (LCUser.getCurrentUser().getMobilePhoneNumber() != null) |
||||
item_phone.setRightText(LCUser.getCurrentUser().getMobilePhoneNumber()); |
||||
if (LCUser.getCurrentUser().getEmail() != null) |
||||
item_email.setRightText(LCUser.getCurrentUser().getEmail()); |
||||
if (VipManager.getInstance().controlBoundName != null) |
||||
item_bound_device.setRightText(VipManager.getInstance().controlBoundName); |
||||
|
||||
fetchNickNameAndAvatar(); |
||||
|
||||
if (VipManager.getInstance().checkReg()) { |
||||
item_user_level.setRightText(getString(R.string.bound_device)); |
||||
item_expiration.setVisibility(View.GONE); |
||||
} else if (VipManager.getInstance().level > 0) { |
||||
item_expiration.setVisibility(View.VISIBLE); |
||||
if (VipManager.getInstance().expireDate != null) |
||||
item_expiration.setRightText(DateUtils.toFull(VipManager.getInstance().expireDate)); |
||||
if (VipManager.getInstance().isInExpireDate) { |
||||
switch (VipManager.getInstance().level) { |
||||
case 1: |
||||
item_user_level.setRightText(getString(R.string.user_level_1)); |
||||
break; |
||||
case 10: |
||||
item_user_level.setRightText(getString(R.string.surveyor_life_vip)); |
||||
break; |
||||
default: |
||||
item_user_level.setRightText(getString(R.string.user_level_unknown)); |
||||
} |
||||
} else { |
||||
item_user_level.setRightText(getString(R.string.vip_expired)); |
||||
} |
||||
} else { |
||||
item_user_level.setRightText(getString(R.string.user_level_0)); |
||||
item_expiration.setVisibility(View.GONE); |
||||
} |
||||
if (VipManager.getInstance().controlLevel > 0) { |
||||
item_control_level.setVisibility(View.VISIBLE); |
||||
item_control_expiration.setVisibility(View.VISIBLE); |
||||
item_control_expiration.setRightText(DateUtils.toFull(VipManager.getInstance().controlExpireDate)); |
||||
if (VipManager.getInstance().isControlInExpireDate) { |
||||
switch (VipManager.getInstance().controlLevel) { |
||||
case 1: |
||||
case 2: |
||||
item_control_level.setRightText(getString(R.string.user_level_try)); |
||||
break; |
||||
case 3: |
||||
item_control_level.setRightText(getString(R.string.user_level_control_pro)); |
||||
break; |
||||
} |
||||
} else { |
||||
item_control_level.setRightText(getString(R.string.vip_expired)); |
||||
} |
||||
} |
||||
} else { |
||||
ToastUtils.showShort(R.string.not_log_in); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public boolean onCreateOptionsMenu(Menu menu) { |
||||
getMenuInflater().inflate(R.menu.menu_activity_user_info, menu); |
||||
return super.onCreateOptionsMenu(menu); |
||||
} |
||||
|
||||
@Override |
||||
public boolean onOptionsItemSelected(MenuItem item) { |
||||
switch (item.getItemId()) { |
||||
case android.R.id.home: |
||||
finish(); |
||||
break; |
||||
case R.id.menu_activity_user_info_redeem_code: |
||||
if (AppChannel.customChannel != AppChannel.CUSTOM_CONTROL_PUBLIC) { |
||||
new AlertDialog.Builder(UserInfoActivity.this) |
||||
.setTitle(R.string.hint) |
||||
.setMessage("定制版本无法续费,只能以绑定手机形式使用") |
||||
.setPositiveButton(R.string.i_know, null) |
||||
.show(); |
||||
} else if (LCUser.getCurrentUser().getInt("level") == 0 || LCUser.getCurrentUser().getInt("level") == 1) { |
||||
startActivityForResult(new Intent(UserInfoActivity.this, RedeemVipActivity.class), REQUEST_CODE_UPDATE_USER_INFO); |
||||
} else { |
||||
ToastUtils.showShort("当前会员模式不支持续费,请联系开发者"); |
||||
} |
||||
break; |
||||
} |
||||
return super.onOptionsItemSelected(item); |
||||
} |
||||
|
||||
@Override |
||||
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) { |
||||
if (grantResults.length > 0) { |
||||
if (requestCode == REQUEST_CODE_ASK_CAMERA) { |
||||
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) { |
||||
pickByTake(); |
||||
} else { |
||||
ToastUtils.showShort(getString(R.string.please_granted_camera_permission)); |
||||
} |
||||
} else { |
||||
super.onRequestPermissionsResult(requestCode, permissions, grantResults); |
||||
} |
||||
} |
||||
} |
||||
|
||||
public void onActivityResult(int requestCode, int resultCode, Intent data) { |
||||
super.onActivityResult(requestCode, resultCode, data); |
||||
if (resultCode == RESULT_OK) { |
||||
switch (requestCode) { |
||||
case REQUEST_CODE_UPDATE_USER_INFO: |
||||
VipManager.getInstance().controlSdkRefresh(UserInfoActivity.this, ((App) Utils.getApp()).registerCodeV2, new VipManager.OnSdkRefreshListener() { |
||||
@Override |
||||
public void onRefreshSuccess() { |
||||
updateUserInfo(); |
||||
} |
||||
|
||||
@Override |
||||
public void onRefreshFailed(int errorCode) { |
||||
ToastUtils.showShort(getString(R.string.error_code) + ":" + errorCode); |
||||
} |
||||
}); |
||||
break; |
||||
case UCrop.REQUEST_CROP: |
||||
final Uri resultUri = UCrop.getOutput(data); |
||||
try { |
||||
File compressedImage = new Compressor(UserInfoActivity.this) |
||||
.setMaxWidth(256) |
||||
.setMaxHeight(256) |
||||
.setQuality(50) |
||||
.setCompressFormat(Bitmap.CompressFormat.JPEG) |
||||
.compressToFile(new File(FileUtil.getRealPathFromUri(resultUri))); |
||||
|
||||
updateProfileAvatar(compressedImage.getAbsolutePath()); |
||||
} catch (IOException e) { |
||||
e.printStackTrace(); |
||||
} |
||||
break; |
||||
case UCrop.RESULT_ERROR: |
||||
final Throwable cropError = UCrop.getError(data); |
||||
if (cropError != null) |
||||
Log.d("cropError", cropError.getMessage()); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* 编辑昵称 |
||||
*/ |
||||
public void showEditNicknameDialog() { |
||||
if (LCUser.getCurrentUser() == null) { |
||||
ToastUtils.showShort(R.string.not_log_in); |
||||
return; |
||||
} |
||||
DialogEditNicknameBinding dialogEditNicknameBinding = DialogEditNicknameBinding.inflate(LayoutInflater.from(this)); |
||||
MaterialDialog dialog = new MaterialDialog.Builder(this) |
||||
.title(R.string.edit_nickname) |
||||
.customView(dialogEditNicknameBinding.getRoot(), false) |
||||
.onPositive((dialog1, which) -> { |
||||
final String nickname = dialogEditNicknameBinding.metDialogEditNickname.getText().toString(); |
||||
LCUser.getCurrentUser().put("nickname", nickname); |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(); |
||||
ToastUtils.showShort(R.string.edit_nickname_success); |
||||
tv_nick_name.setText(nickname); |
||||
((App) Utils.getApp()).isUserStatusChanged = true;//返回MainActivity时updateHeaderResult
|
||||
}) |
||||
.positiveText(getString(R.string.save)) |
||||
.negativeText(getString(R.string.cancel)) |
||||
.dismissListener(dialog12 -> |
||||
dialogEditNicknameBinding.metDialogEditNickname.clearFocus()) |
||||
.build(); |
||||
mPositiveAction = dialog.getActionButton(DialogAction.POSITIVE); |
||||
|
||||
if (SettingValueUtil.isThemeDark()) { |
||||
dialogEditNicknameBinding.metDialogEditNickname.setMetTextColor(Color.WHITE); |
||||
dialogEditNicknameBinding.metDialogEditNickname.setPrimaryColor(Color.LTGRAY); |
||||
dialogEditNicknameBinding.metDialogEditNickname.setFocusFraction(1.0f); |
||||
dialogEditNicknameBinding.metDialogEditNickname.setMetHintTextColor(Color.GRAY); |
||||
dialogEditNicknameBinding.metDialogEditNickname.setUnderlineColor(Color.GRAY); |
||||
} |
||||
|
||||
TextWatcher watcher = new TextWatcher() { |
||||
@Override |
||||
public void beforeTextChanged(CharSequence s, int start, int count, int after) { |
||||
} |
||||
|
||||
@Override |
||||
public void onTextChanged(CharSequence s, int start, int before, int count) { |
||||
} |
||||
|
||||
@Override |
||||
public void afterTextChanged(Editable s) { |
||||
String nickname_text = s == null ? "" : s.toString(); |
||||
mPositiveAction.setEnabled(ValidateUtil.isNickName(nickname_text)); |
||||
} |
||||
}; |
||||
|
||||
dialogEditNicknameBinding.metDialogEditNickname.addTextChangedListener(watcher); |
||||
|
||||
dialog.show(); |
||||
mPositiveAction.setEnabled(false); |
||||
} |
||||
|
||||
/** |
||||
* 编辑头像 |
||||
*/ |
||||
private void showProfileAvatarChangeDialog() { |
||||
new MaterialDialog.Builder(this) |
||||
.title(R.string.change_profile_avatar) |
||||
.positiveText(R.string.pick_by_select) |
||||
.negativeText(R.string.pick_by_take) |
||||
.neutralText(R.string.cancel) |
||||
.onPositive(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull @NotNull MaterialDialog dialog, @NonNull @NotNull DialogAction which) { |
||||
pickBySelect(); |
||||
} |
||||
}) |
||||
.onNegative(new MaterialDialog.SingleButtonCallback() { |
||||
@Override |
||||
public void onClick(@NonNull @NotNull MaterialDialog dialog, @NonNull @NotNull DialogAction which) { |
||||
pickByTake(); |
||||
} |
||||
}) |
||||
.show(); |
||||
} |
||||
|
||||
/** |
||||
* 相册选择照片 |
||||
*/ |
||||
@SuppressLint("CheckResult") |
||||
public void pickBySelect() { |
||||
rxImagePicker.openGallery(this, new WechatConfigrationBuilder(MimeType.INSTANCE.ofImage(), false) |
||||
.capture(true) |
||||
.maxSelectable(1) |
||||
.countable(true) |
||||
.spanCount(4) |
||||
.countable(false) |
||||
.build()) |
||||
.subscribe(rxImagePickerConsumerOnNext, rxImagePickerConsumerOnError); |
||||
} |
||||
|
||||
/** |
||||
* 拍照片 |
||||
*/ |
||||
@SuppressLint("CheckResult") |
||||
public void pickByTake() { |
||||
if ((PackageManager.PERMISSION_GRANTED != ContextCompat.checkSelfPermission(Utils.getApp(), Manifest.permission.CAMERA))) { |
||||
ActivityCompat.requestPermissions(UserInfoActivity.this, new String[]{Manifest.permission.CAMERA}, REQUEST_CODE_ASK_CAMERA); |
||||
} else { |
||||
rxImagePicker.openCamera(this).subscribe(rxImagePickerConsumerOnNext, rxImagePickerConsumerOnError); |
||||
} |
||||
} |
||||
|
||||
Consumer<Result> rxImagePickerConsumerOnNext = new Consumer<Result>() { |
||||
@Override |
||||
public void accept(Result result) throws Exception { |
||||
boolean originalMode = result.getBooleanExtra(WechatImagePickerFragment.EXTRA_ORIGINAL_IMAGE, false); |
||||
// String mimeType = result.getStringExtra(WechatImagePickerFragment.EXTRA_OPTIONAL_MIME_TYPE, "");
|
||||
Log.d(TAG, "select image original:" + originalMode + " , uri path: " + FileUtil.getRealPathFromUri(result.getUri())); |
||||
UCrop.of(result.getUri(), result.getUri()) |
||||
.withAspectRatio(1, 1) |
||||
.withMaxResultSize(256, 256) |
||||
.start(UserInfoActivity.this); |
||||
} |
||||
}; |
||||
|
||||
Consumer<Throwable> rxImagePickerConsumerOnError = new Consumer<Throwable>() { |
||||
@Override |
||||
public void accept(Throwable throwable) { |
||||
ToastUtils.showShort("打开图片失败"); |
||||
} |
||||
}; |
||||
|
||||
/** |
||||
* 更新云端头像 |
||||
* |
||||
* @param path |
||||
*/ |
||||
private void updateProfileAvatar(String path) { |
||||
try { |
||||
final LCFile file = LCFile.withAbsoluteLocalPath("avatar.jpg", path); |
||||
if (LCUser.getCurrentUser() != null) { |
||||
LCUser.getCurrentUser().put("avatar", file); |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(new Observer<LCObject>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCObject lcObject) { |
||||
Glide.with(UserInfoActivity.this).load(file.getUrl()).into(avatarImageView); |
||||
ToastUtils.showShort(R.string.update_avatar_success); |
||||
((App) Utils.getApp()).isUserStatusChanged = true;//返回MainActivity时updateHeaderResult
|
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} else { |
||||
ToastUtils.showShort(R.string.not_log_in); |
||||
} |
||||
} catch (FileNotFoundException e) { |
||||
e.printStackTrace(); |
||||
} |
||||
} |
||||
|
||||
private void fetchNickNameAndAvatar() { |
||||
if (LCUser.getCurrentUser() != null) { |
||||
String nickname = LCUser.getCurrentUser().getString("nickname"); |
||||
LCFile avatarFile = LCUser.getCurrentUser().getLCFile("avatar"); |
||||
if (!StringUtils.isEmpty(nickname)) { |
||||
tv_nick_name.setText(nickname); |
||||
if (avatarFile == null) { |
||||
avatarImageView.setImageResource(R.mipmap.profile_image); |
||||
} else { |
||||
Glide.with(UserInfoActivity.this).load(avatarFile.getUrl()).into(avatarImageView); |
||||
} |
||||
} else { |
||||
LCObject userProfile = LCUser.getCurrentUser().getLCObject("profile"); |
||||
if (userProfile != null) { |
||||
userProfile.fetchInBackground().subscribe(new Observer<LCObject>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(LCObject avObject) { |
||||
if (isFinishing()) return; |
||||
String nickname = avObject.getString("nickname"); |
||||
LCFile avatarFile = avObject.getLCFile("avatar"); |
||||
if (!StringUtils.isEmpty(nickname)) { |
||||
tv_nick_name.setText(nickname); |
||||
if (avatarFile == null) { |
||||
avatarImageView.setImageResource(R.mipmap.profile_image); |
||||
} else { |
||||
Glide.with(UserInfoActivity.this).load(avatarFile.getUrl()).into(avatarImageView); |
||||
} |
||||
//保存到_User,下次不再查Profile
|
||||
LCUser.getCurrentUser().put("nickname", nickname); |
||||
if (avatarFile != null) |
||||
LCUser.getCurrentUser().put("avatar", avatarFile); |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} else { |
||||
new LCQuery<>("Profile") |
||||
.whereEqualTo("creatorId", LCUser.getCurrentUser().getObjectId()) |
||||
.findInBackground() |
||||
.subscribe(new Observer<List<LCObject>>() { |
||||
@Override |
||||
public void onSubscribe(Disposable d) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onNext(List<LCObject> list) { |
||||
if (isFinishing()) return; |
||||
if (list != null && !list.isEmpty()) { |
||||
String nickname = list.get(0).getString("nickname"); |
||||
LCFile avatarFile = list.get(0).getLCFile("avatar"); |
||||
if (!StringUtils.isEmpty(nickname)) { |
||||
tv_nick_name.setText(nickname); |
||||
if (avatarFile == null) { |
||||
avatarImageView.setImageResource(R.mipmap.profile_image); |
||||
} else { |
||||
Glide.with(UserInfoActivity.this).load(avatarFile.getUrl()).into(avatarImageView); |
||||
} |
||||
|
||||
//保存到_User,下次不再查Profile
|
||||
LCUser.getCurrentUser().put("nickname", nickname); |
||||
if (avatarFile != null) |
||||
LCUser.getCurrentUser().put("avatar", avatarFile); |
||||
LCUser.getCurrentUser().saveInBackground().subscribe(); |
||||
} |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onError(Throwable e) { |
||||
|
||||
} |
||||
|
||||
@Override |
||||
public void onComplete() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
} |
||||
} else { |
||||
tv_nick_name.setText(getString(R.string.please_log_in_again)); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,234 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.app.ProgressDialog; |
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.text.SpannableString; |
||||
import android.text.Spanned; |
||||
import android.text.style.TextAppearanceSpan; |
||||
import android.view.View; |
||||
|
||||
import androidx.activity.result.ActivityResultLauncher; |
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import com.bingce.AppChannel; |
||||
import com.bingce.activity.UserCloudFunction; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityVerifyCodeBinding; |
||||
import com.bingce.utils.ActivityUtils; |
||||
import com.bingce.utils.IntentUtil; |
||||
import com.bingce.utils.SendCodeCountDownManager; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.util.regex.Matcher; |
||||
import java.util.regex.Pattern; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
public class VerifyEmailCodeActivity extends ColorfulActivity { |
||||
|
||||
public static final String KEY_EMAIL = "email"; |
||||
public static final String KEY_TODO = "todo"; |
||||
private static ActivityResultLauncher<Intent> mLauncher; |
||||
|
||||
public static final int TO_VERIFY_EMAIL = 0; |
||||
public static final int TO_SIGNUP_OR_LOGIN_BY_EMAIL = 1; |
||||
|
||||
private ActivityVerifyCodeBinding binding; |
||||
private ProgressDialog progressDialog; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityVerifyCodeBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
getSupportActionBar().setTitle(R.string.verify); |
||||
|
||||
binding.tvInputHintTitle.setText(R.string.enter_email_verification_code); |
||||
|
||||
String trip = String.format(getString(R.string.format_enter_verification_code), getEmail()); |
||||
binding.tvInputTrip.setText(matcherChangeText(trip, getEmail()));//+前需要转义
|
||||
|
||||
SendCodeCountDownManager.getInstance().start(this, 60000, 1000, binding.tvSendAuthCode, new SendCodeCountDownManager.OnCountDownListener() { |
||||
@Override |
||||
public void onSendValid() { |
||||
sendCode(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSendInvalid() { |
||||
|
||||
} |
||||
}); |
||||
binding.tvSendAuthCode.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View view) { |
||||
SendCodeCountDownManager.getInstance().start(VerifyEmailCodeActivity.this, 60000, 1000, binding.tvSendAuthCode, new SendCodeCountDownManager.OnCountDownListener() { |
||||
@Override |
||||
public void onSendValid() { |
||||
sendCode(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSendInvalid() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
}); |
||||
|
||||
binding.etInputAuthCode.setOnInputListener(code -> { |
||||
verifyCode(code); |
||||
}); |
||||
} |
||||
|
||||
private void sendCode() { |
||||
if (getEmail() == null) { |
||||
ToastUtils.showShort(R.string.email_address_illegal); |
||||
return; |
||||
} |
||||
UserCloudFunction.sendEmailCode(getEmail(), new UserCloudFunction.OnSendCodeListener() { |
||||
@Override |
||||
public void onCodeSendSuccess() { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showShort(R.string.send_success); |
||||
} |
||||
|
||||
@Override |
||||
public void onCodeSendFailed(String errorMsg) { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(errorMsg); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
private void verifyCode(String code) { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
progressDialog = new ProgressDialog(VerifyEmailCodeActivity.this); |
||||
progressDialog.setMessage(getString(R.string.logging)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
switch (getToDo()) { |
||||
case TO_VERIFY_EMAIL: |
||||
if (getEmail() == null) { |
||||
ToastUtils.showShort(R.string.email_address_illegal); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
UserCloudFunction.verifyEmailCode(getEmail(), code, new UserCloudFunction.OnVerifyCodeListener() { |
||||
@Override |
||||
public void onCodeVerifySuccess() { |
||||
if (!ActivityUtils.isLiving(VerifyEmailCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
SendCodeCountDownManager.getInstance().resetRemainingTime();//验证成功,重置倒计时,否则跳转到下一个验证页面不会自动发送验证码
|
||||
|
||||
Intent intent = new Intent(); |
||||
intent.putExtra("isMail", true); |
||||
intent.putExtra("phoneNumberOrEmail", getEmail()); |
||||
setResult(RESULT_OK, intent); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onCodeVerifyFailed(String errorMsg) { |
||||
if (!ActivityUtils.isLiving(VerifyEmailCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(errorMsg); |
||||
} |
||||
}); |
||||
break; |
||||
case TO_SIGNUP_OR_LOGIN_BY_EMAIL: |
||||
if (getEmail() == null) { |
||||
ToastUtils.showShort(R.string.email_address_illegal); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
UserCloudFunction.signUpOrLoginByEmail(getEmail(), code, AppChannel.customChannel, |
||||
new UserCloudFunction.OnGetSessionTokenListener() { |
||||
@Override |
||||
public void onSessionTokenGetSuccess(String sessionToken, boolean newUser) { |
||||
if (!ActivityUtils.isLiving(VerifyEmailCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
SendCodeCountDownManager.getInstance().resetRemainingTime();//验证成功,重置倒计时,否则跳转到下一个验证页面不会自动发送验证码
|
||||
|
||||
Intent intent = new Intent(); |
||||
intent.putExtra("sessionToken", sessionToken); |
||||
intent.putExtra("newUser", newUser); |
||||
setResult(RESULT_OK, intent); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetFailed(int code, String msg, String resp) { |
||||
if (!ActivityUtils.isLiving(VerifyEmailCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
if (code == 303) {//缺少手机号或未验证
|
||||
SendCodeCountDownManager.getInstance().resetRemainingTime(); |
||||
InputPhoneNumberActivity.start(VerifyEmailCodeActivity.this, null, getEmail(), null, VerifySMSCodeActivity.TO_SIGNUP_OR_LOGIN_BY_EMAIL_BIND_PHONE, mLauncher); |
||||
finish(); |
||||
} else { |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetException(String msg) { |
||||
if (!ActivityUtils.isLiving(VerifyEmailCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
}); |
||||
break; |
||||
} |
||||
} |
||||
|
||||
|
||||
private String getEmail() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_EMAIL); |
||||
} |
||||
|
||||
private int getToDo() { |
||||
return IntentUtil.intExtra(getIntent(), KEY_TODO); |
||||
} |
||||
|
||||
public static void start(Context context, String email, int todo, ActivityResultLauncher<Intent> launcher) { |
||||
Intent intent = new Intent(context, VerifyEmailCodeActivity.class); |
||||
intent.putExtra(KEY_EMAIL, email); |
||||
intent.putExtra(KEY_TODO, todo); |
||||
mLauncher = launcher; |
||||
launcher.launch(intent); |
||||
} |
||||
|
||||
private SpannableString matcherChangeText(String str, String keyword) { |
||||
SpannableString ss = new SpannableString(str); |
||||
Pattern pattern = Pattern.compile(keyword); |
||||
Matcher matcher = pattern.matcher(ss); |
||||
while (matcher.find()) { |
||||
int start = matcher.start(); |
||||
int end = matcher.end(); |
||||
ss.setSpan(new TextAppearanceSpan(this, R.style.style_color_black), start, end, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);//new ForegroundColorSpan(color)
|
||||
} |
||||
return ss; |
||||
} |
||||
} |
@ -0,0 +1,329 @@ |
||||
package com.bingce.controlnetwork.activity.user; |
||||
|
||||
import android.app.ProgressDialog; |
||||
import android.content.Context; |
||||
import android.content.Intent; |
||||
import android.os.Bundle; |
||||
import android.text.SpannableString; |
||||
import android.text.Spanned; |
||||
import android.text.style.TextAppearanceSpan; |
||||
import android.view.View; |
||||
|
||||
import androidx.activity.result.ActivityResultLauncher; |
||||
import androidx.annotation.Nullable; |
||||
import androidx.appcompat.widget.Toolbar; |
||||
|
||||
import com.bingce.AppChannel; |
||||
import com.bingce.activity.UserCloudFunction; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.databinding.ActivityVerifyCodeBinding; |
||||
import com.bingce.utils.ActivityUtils; |
||||
import com.bingce.utils.IntentUtil; |
||||
import com.bingce.utils.SendCodeCountDownManager; |
||||
|
||||
import org.polaric.colorful.ColorfulActivity; |
||||
|
||||
import java.util.regex.Matcher; |
||||
import java.util.regex.Pattern; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
public class VerifySMSCodeActivity extends ColorfulActivity { |
||||
public static final String KEY_PHONE = "phone_number"; |
||||
public static final String KEY_EMAIL = "email"; |
||||
public static final String KEY_UNION_ID = "unionid"; |
||||
public static final String KEY_TODO = "todo"; |
||||
|
||||
public static final int TO_VERIFY_PHONE_NUMBER = 0; |
||||
public static final int TO_SIGNUP_OR_LOGIN_BY_PHONE_NUMBER = 1; |
||||
public static final int TO_SIGNUP_OR_LOGIN_BY_EMAIL_BIND_PHONE = 2; |
||||
public static final int TO_SIGNUP_OR_LOGIN_BY_WEIXIN_BIND_PHONE = 3; |
||||
private ActivityVerifyCodeBinding binding; |
||||
private ProgressDialog progressDialog; |
||||
|
||||
@Override |
||||
protected void onCreate(@Nullable Bundle savedInstanceState) { |
||||
super.onCreate(savedInstanceState); |
||||
binding = ActivityVerifyCodeBinding.inflate(getLayoutInflater()); |
||||
setContentView(binding.getRoot()); |
||||
|
||||
Toolbar mToolbar = findViewById(R.id.toolbar); |
||||
setSupportActionBar(mToolbar); |
||||
if (getSupportActionBar() != null) getSupportActionBar().setDisplayHomeAsUpEnabled(true); |
||||
|
||||
getSupportActionBar().setTitle(R.string.verify); |
||||
|
||||
binding.tvInputHintTitle.setText(R.string.enter_sms_verification_code); |
||||
|
||||
String phoneOrEmail = getPhoneNumber(); |
||||
String trip = String.format(getString(R.string.format_enter_verification_code), phoneOrEmail); |
||||
binding.tvInputTrip.setText(matcherChangeText(trip, phoneOrEmail.startsWith("+") ? ("\\" + phoneOrEmail) : phoneOrEmail));//+前需要转义
|
||||
|
||||
SendCodeCountDownManager.getInstance().start(this, 60000, 1000, binding.tvSendAuthCode, new SendCodeCountDownManager.OnCountDownListener() { |
||||
@Override |
||||
public void onSendValid() { |
||||
sendCode(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSendInvalid() { |
||||
|
||||
} |
||||
}); |
||||
binding.tvSendAuthCode.setOnClickListener(new View.OnClickListener() { |
||||
@Override |
||||
public void onClick(View view) { |
||||
SendCodeCountDownManager.getInstance().start(VerifySMSCodeActivity.this, 60000, 1000, binding.tvSendAuthCode, new SendCodeCountDownManager.OnCountDownListener() { |
||||
@Override |
||||
public void onSendValid() { |
||||
sendCode(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSendInvalid() { |
||||
|
||||
} |
||||
}); |
||||
} |
||||
}); |
||||
|
||||
binding.etInputAuthCode.setOnInputListener(code -> { |
||||
verifyCode(code); |
||||
}); |
||||
} |
||||
|
||||
private void sendCode() { |
||||
if (getPhoneNumber() == null) { |
||||
ToastUtils.showShort(R.string.phone_number_invalid); |
||||
return; |
||||
} |
||||
UserCloudFunction.sendSMSCode(getPhoneNumber(), new UserCloudFunction.OnSendCodeListener() { |
||||
@Override |
||||
public void onCodeSendSuccess() { |
||||
ToastUtils.showShort(R.string.send_success); |
||||
} |
||||
|
||||
@Override |
||||
public void onCodeSendFailed(String errorMsg) { |
||||
ToastUtils.showLong(errorMsg); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
private void verifyCode(String code) { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
progressDialog = new ProgressDialog(VerifySMSCodeActivity.this); |
||||
progressDialog.setMessage(getString(R.string.logging)); |
||||
progressDialog.setCanceledOnTouchOutside(false); |
||||
progressDialog.show(); |
||||
|
||||
switch (getTodo()) { |
||||
case TO_VERIFY_PHONE_NUMBER: |
||||
if (getPhoneNumber() == null) { |
||||
ToastUtils.showShort(R.string.phone_number_invalid); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
UserCloudFunction.verifySMSCode(getPhoneNumber(), code, new UserCloudFunction.OnVerifyCodeListener() { |
||||
@Override |
||||
public void onCodeVerifySuccess() { |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
SendCodeCountDownManager.getInstance().resetRemainingTime();//验证成功,重置倒计时,否则跳转到下一个验证页面不会自动发送验证码
|
||||
|
||||
Intent intent = new Intent(); |
||||
intent.putExtra("isMail", false); |
||||
intent.putExtra("phoneNumberOrEmail", getPhoneNumber()); |
||||
setResult(RESULT_OK, intent); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onCodeVerifyFailed(String errorMsg) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(errorMsg); |
||||
} |
||||
}); |
||||
break; |
||||
case TO_SIGNUP_OR_LOGIN_BY_PHONE_NUMBER: |
||||
if (getPhoneNumber() == null) { |
||||
ToastUtils.showShort(R.string.phone_number_invalid); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
UserCloudFunction.signUpOrLoginByMobilePhone(getPhoneNumber(), code, AppChannel.customChannel, |
||||
new UserCloudFunction.OnGetSessionTokenListener() { |
||||
@Override |
||||
public void onSessionTokenGetSuccess(String sessionToken, boolean newUser) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
SendCodeCountDownManager.getInstance().resetRemainingTime();//验证成功,重置倒计时,否则跳转到下一个验证页面不会自动发送验证码
|
||||
|
||||
Intent intent = new Intent(); |
||||
intent.putExtra("sessionToken", sessionToken); |
||||
intent.putExtra("newUser", newUser); |
||||
setResult(RESULT_OK, intent); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetFailed(int code, String msg, String resp) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetException(String msg) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
}); |
||||
break; |
||||
case TO_SIGNUP_OR_LOGIN_BY_EMAIL_BIND_PHONE: |
||||
if (getEmail() == null) { |
||||
ToastUtils.showShort(R.string.email_address_illegal); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
if (getPhoneNumber() == null) { |
||||
ToastUtils.showShort(R.string.phone_number_invalid); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
UserCloudFunction.loginByEmailBindPhone(getEmail(), getPhoneNumber(), code, AppChannel.customChannel, |
||||
new UserCloudFunction.OnGetSessionTokenListener() { |
||||
@Override |
||||
public void onSessionTokenGetSuccess(String sessionToken, boolean newUser) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
SendCodeCountDownManager.getInstance().resetRemainingTime();//验证成功,重置倒计时,否则跳转到下一个验证页面不会自动发送验证码
|
||||
|
||||
Intent intent = new Intent(); |
||||
intent.putExtra("sessionToken", sessionToken); |
||||
intent.putExtra("newUser", newUser); |
||||
setResult(RESULT_OK, intent); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetFailed(int code, String msg, String resp) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetException(String msg) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
}); |
||||
break; |
||||
case TO_SIGNUP_OR_LOGIN_BY_WEIXIN_BIND_PHONE: |
||||
if (getUnionId() == null) { |
||||
ToastUtils.showShort(R.string.wechat_unionid_invalid); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
if (getPhoneNumber() == null) { |
||||
ToastUtils.showShort(R.string.phone_number_invalid); |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
return; |
||||
} |
||||
UserCloudFunction.loginByWxUnionIdBindPhone(getUnionId(), getPhoneNumber(), AppChannel.customChannel, |
||||
new UserCloudFunction.OnGetSessionTokenListener() { |
||||
@Override |
||||
public void onSessionTokenGetSuccess(String sessionToken, boolean newUser) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
|
||||
SendCodeCountDownManager.getInstance().resetRemainingTime();//验证成功,重置倒计时,否则跳转到下一个验证页面不会自动发送验证码
|
||||
|
||||
Intent intent = new Intent(); |
||||
intent.putExtra("sessionToken", sessionToken); |
||||
intent.putExtra("newUser", newUser); |
||||
setResult(RESULT_OK, intent); |
||||
finish(); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetFailed(int code, String msg, String resp) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
|
||||
@Override |
||||
public void onSessionTokenGetException(String msg) { |
||||
if (!ActivityUtils.isLiving(VerifySMSCodeActivity.this)) return; |
||||
if (progressDialog != null) |
||||
progressDialog.dismiss(); |
||||
ToastUtils.showLong(msg); |
||||
} |
||||
}); |
||||
break; |
||||
} |
||||
|
||||
} |
||||
|
||||
private String getPhoneNumber() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_PHONE); |
||||
} |
||||
|
||||
private String getEmail() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_EMAIL); |
||||
} |
||||
|
||||
private String getUnionId() { |
||||
return IntentUtil.stringExtra(getIntent(), KEY_UNION_ID); |
||||
} |
||||
|
||||
|
||||
private int getTodo() { |
||||
return IntentUtil.intExtra(getIntent(), KEY_TODO); |
||||
} |
||||
|
||||
public static void start(Context context, String phoneNumber, String email, String unionid, int todo, ActivityResultLauncher<Intent> launcher) { |
||||
Intent intent = new Intent(context, VerifySMSCodeActivity.class); |
||||
intent.putExtra(KEY_PHONE, phoneNumber); |
||||
intent.putExtra(KEY_EMAIL, email); |
||||
intent.putExtra(KEY_UNION_ID, unionid); |
||||
intent.putExtra(KEY_TODO, todo); |
||||
launcher.launch(intent); |
||||
} |
||||
|
||||
private SpannableString matcherChangeText(String str, String keyword) { |
||||
SpannableString ss = new SpannableString(str); |
||||
Pattern pattern = Pattern.compile(keyword); |
||||
Matcher matcher = pattern.matcher(ss); |
||||
while (matcher.find()) { |
||||
int start = matcher.start(); |
||||
int end = matcher.end(); |
||||
ss.setSpan(new TextAppearanceSpan(this, R.style.style_color_black), start, end, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);//new ForegroundColorSpan(color)
|
||||
} |
||||
return ss; |
||||
} |
||||
} |
@ -0,0 +1,176 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.content.Context; |
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
import android.widget.BaseExpandableListAdapter; |
||||
|
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.point.PointRecord; |
||||
import com.bingce.controlapphelper.model.PickPointResult; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlapphelper.util.Tools; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.ui.vh.GroupParentViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.TextSelectableViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
/* |
||||
* 限差详情adapter |
||||
* */ |
||||
public abstract class AbstractPointSelectAdapter extends BaseExpandableListAdapter { |
||||
private final ArrayList<String> selectedId = new ArrayList<>(); |
||||
private final ArrayList<String> selectedName = new ArrayList<>(); |
||||
private final int maxCount; |
||||
private final Context context; |
||||
|
||||
public AbstractPointSelectAdapter(PickPointResult defaultValue, |
||||
int maxCount, |
||||
Context context) { |
||||
this.maxCount = maxCount; |
||||
if (defaultValue != null) { |
||||
List<String> ids = defaultValue.getSelectedIds(); |
||||
if (ids != null) { |
||||
selectedId.addAll(ids); |
||||
} |
||||
|
||||
List<String> names = defaultValue.getSelectedNames(); |
||||
if (names != null) { |
||||
selectedName.addAll(names); |
||||
} |
||||
} |
||||
this.context = context; |
||||
} |
||||
|
||||
protected Context context() { |
||||
return context; |
||||
} |
||||
|
||||
public ArrayList<String> getSelectedId() { |
||||
return selectedId; |
||||
} |
||||
|
||||
public ArrayList<String> getSelectedName() { |
||||
return selectedName; |
||||
} |
||||
|
||||
public abstract int getGroupCount(); |
||||
|
||||
public abstract int getChildrenCount(int groupPosition); |
||||
|
||||
public abstract String getGroup(int groupPosition); |
||||
|
||||
public abstract PointRecord getChild(int groupPosition, int childPosition); |
||||
|
||||
@Override |
||||
final public long getGroupId(int groupPosition) { |
||||
return groupPosition; |
||||
} |
||||
|
||||
@Override |
||||
final public long getChildId(int groupPosition, int childPosition) { |
||||
return groupPosition * 10000L + childPosition; |
||||
} |
||||
|
||||
@Override |
||||
public boolean hasStableIds() { |
||||
return true; |
||||
} |
||||
|
||||
protected boolean showGroupArrow() { |
||||
return true; |
||||
} |
||||
|
||||
@Override |
||||
public View getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) { |
||||
GroupParentViewHolder viewHolder = null; |
||||
if (convertView == null) { |
||||
convertView = ViewFactory.generatorView(parent.getContext(), parent, ViewItemType.groupParent); |
||||
viewHolder = new GroupParentViewHolder(convertView); |
||||
convertView.setTag(viewHolder); |
||||
} else { |
||||
viewHolder = (GroupParentViewHolder) convertView.getTag(); |
||||
} |
||||
if (viewHolder != null) { |
||||
String groupName = getGroup(groupPosition); |
||||
if (viewHolder.name != null) { |
||||
viewHolder.name.setText(groupName); |
||||
} |
||||
if (viewHolder.expandIcon != null) { |
||||
if (showGroupArrow()) { |
||||
viewHolder.expandIcon.setImageResource(isExpanded ? R.drawable.ic_arrow_up : R.drawable.ic_arrow_down); |
||||
viewHolder.expandIcon.setVisibility(View.VISIBLE); |
||||
} else { |
||||
viewHolder.expandIcon.setVisibility(View.GONE); |
||||
} |
||||
} |
||||
} |
||||
return convertView; |
||||
} |
||||
|
||||
@Override |
||||
public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) { |
||||
PointRecord record = getChild(groupPosition, childPosition); |
||||
RecyclerView.ViewHolder viewHolder = null; |
||||
if (convertView == null) { |
||||
viewHolder = ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewItemType.textSelectable); |
||||
if (viewHolder == null) { |
||||
return null; |
||||
} |
||||
convertView = viewHolder.itemView; |
||||
convertView.setTag(viewHolder); |
||||
} else { |
||||
viewHolder = (RecyclerView.ViewHolder) convertView.getTag(); |
||||
} |
||||
//更新item内容
|
||||
if (viewHolder instanceof TextSelectableViewHolder) { |
||||
TextSelectableViewHolder titleWithSubtitleViewHolder = (TextSelectableViewHolder) viewHolder; |
||||
titleWithSubtitleViewHolder.name.setText(record.getName()); |
||||
if (selectedId.contains(record.getId())) { |
||||
titleWithSubtitleViewHolder.status.setVisibility(View.VISIBLE); |
||||
} else { |
||||
titleWithSubtitleViewHolder.status.setVisibility(View.GONE); |
||||
} |
||||
} |
||||
convertView.setOnClickListener(v -> { |
||||
if (!selectedId.contains(record.getId())) { |
||||
// if (singlePick) {
|
||||
// selectedId.clear();
|
||||
// selectedName.clear();
|
||||
// }
|
||||
// selectedId.add(record.getId());
|
||||
// selectedName.add(record.getName());
|
||||
if (maxCount == 1) { |
||||
selectedId.clear(); |
||||
selectedName.clear(); |
||||
selectedId.add(record.getId()); |
||||
selectedName.add(record.getName()); |
||||
} else if (maxCount < 0) { |
||||
selectedId.add(record.getId()); |
||||
selectedName.add(record.getName()); |
||||
} else if (selectedId.size() >= maxCount) { |
||||
ToastUtils.showShort(Tools.getString(R.string.max_select_hint, maxCount)); |
||||
} else { |
||||
selectedId.add(record.getId()); |
||||
selectedName.add(record.getName()); |
||||
} |
||||
} else { |
||||
selectedId.remove(record.getId()); |
||||
selectedName.remove(record.getName()); |
||||
} |
||||
notifyDataSetChanged(); |
||||
}); |
||||
return convertView; |
||||
} |
||||
|
||||
@Override |
||||
public boolean isChildSelectable(int groupPosition, int childPosition) { |
||||
return true; |
||||
} |
||||
} |
@ -0,0 +1,57 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.List; |
||||
|
||||
public abstract class BaseAdapter<T, VH extends RecyclerView.ViewHolder> extends RecyclerView.Adapter<VH> { |
||||
private final List<T> mValues; |
||||
|
||||
public BaseAdapter(List<T> items) { |
||||
mValues = items; |
||||
} |
||||
|
||||
public void updateData(List<T> list) { |
||||
mValues.clear(); |
||||
if (list != null && !list.isEmpty()) { |
||||
mValues.addAll(list); |
||||
} |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
protected abstract VH createVH(@NotNull ViewGroup parent, int viewType); |
||||
|
||||
@Override |
||||
public @NotNull |
||||
VH onCreateViewHolder(@NotNull ViewGroup parent, int viewType) { |
||||
VH viewHolder = createVH(parent, viewType); |
||||
assert viewHolder != null; |
||||
return viewHolder; |
||||
} |
||||
|
||||
protected T getItem(int position) { |
||||
return mValues.get(position); |
||||
} |
||||
|
||||
protected boolean clickEnable(int position) { |
||||
return true; |
||||
} |
||||
|
||||
@Override |
||||
public int getItemCount() { |
||||
if (mValues == null) { |
||||
return 0; |
||||
} |
||||
return mValues.size(); |
||||
} |
||||
|
||||
public interface IOnItemClick<T extends IUniversalListItem<?>> { |
||||
void onItemClick(T item); |
||||
} |
||||
} |
@ -0,0 +1,61 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ContextMenu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.widget.TextView; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.adapter.contextmenu.IAdapterContextMenu; |
||||
import com.bingce.controlnetwork.ui.vh.IndexTextViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.IndexTextWithPrefixViewHolder; |
||||
|
||||
public abstract class BaseIndexPrefixTextWithContextMenuAdapter<T extends IUniversalListItem<?>> |
||||
extends IndexWithTextAndPrefixAdapter<T> |
||||
implements View.OnCreateContextMenuListener { |
||||
private int currentLongPressIndex = -1; |
||||
private final IAdapterContextMenu<T> adapterContextMenu; |
||||
|
||||
public BaseIndexPrefixTextWithContextMenuAdapter(List<T> items, |
||||
IOnItemClick<T> callback, |
||||
IAdapterContextMenu<T> adapterContextMenu) { |
||||
super(items, callback); |
||||
this.adapterContextMenu = adapterContextMenu; |
||||
} |
||||
|
||||
@Override |
||||
final public void onBindViewHolder(@NotNull IndexTextViewHolder holder, int position) { |
||||
super.onBindViewHolder(holder, position); |
||||
holder.itemView.setOnLongClickListener(v -> { |
||||
currentLongPressIndex = position; |
||||
return false; |
||||
}); |
||||
holder.itemView.setOnCreateContextMenuListener(this); |
||||
if (holder instanceof IndexTextWithPrefixViewHolder) { |
||||
onSetPrefix(((IndexTextWithPrefixViewHolder) holder).prefix, getItem(position)); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
final public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) { |
||||
if (adapterContextMenu == null) { |
||||
return; |
||||
} |
||||
menu.clear(); |
||||
for (int index = 0; index < adapterContextMenu.menuItemSize(); index++) { |
||||
menu.add(0, index, 0, adapterContextMenu.menuItemName(index)); |
||||
MenuItem menuItem = menu.getItem(index); |
||||
if (menuItem != null) { |
||||
menuItem.setOnMenuItemClickListener(item -> |
||||
adapterContextMenu.onMenuItemClick(getItem(currentLongPressIndex), item)); |
||||
} |
||||
} |
||||
} |
||||
|
||||
protected abstract void onSetPrefix(TextView prefixTextView, T item); |
||||
} |
@ -0,0 +1,54 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ContextMenu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.adapter.contextmenu.IAdapterContextMenu; |
||||
import com.bingce.controlnetwork.ui.vh.IndexTextViewHolder; |
||||
|
||||
public class BaseIndexTextWithContextMenuAdapter<T extends IUniversalListItem<?>> |
||||
extends IndexWithTextAdapter<T> |
||||
implements View.OnCreateContextMenuListener { |
||||
private int currentLongPressIndex = -1; |
||||
private final IAdapterContextMenu<T> adapterContextMenu; |
||||
|
||||
public BaseIndexTextWithContextMenuAdapter(List<T> items, |
||||
IOnItemClick<T> callback, |
||||
IAdapterContextMenu<T> adapterContextMenu) { |
||||
super(items, callback); |
||||
this.adapterContextMenu = adapterContextMenu; |
||||
} |
||||
|
||||
@Override |
||||
final public void onBindViewHolder(@NotNull IndexTextViewHolder holder, int position) { |
||||
super.onBindViewHolder(holder, position); |
||||
holder.itemView.setOnLongClickListener(v -> { |
||||
currentLongPressIndex = position; |
||||
return false; |
||||
}); |
||||
holder.itemView.setOnCreateContextMenuListener(this); |
||||
} |
||||
|
||||
@Override |
||||
final public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) { |
||||
if (adapterContextMenu == null) { |
||||
return; |
||||
} |
||||
menu.clear(); |
||||
for (int index = 0; index < adapterContextMenu.menuItemSize(); index++) { |
||||
menu.add(0, index, 0, adapterContextMenu.menuItemName(index)); |
||||
MenuItem menuItem = menu.getItem(index); |
||||
if (menuItem != null) { |
||||
menuItem.setOnMenuItemClickListener(item -> |
||||
adapterContextMenu.onMenuItemClick(getItem(currentLongPressIndex), item)); |
||||
} |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,55 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ContextMenu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.adapter.contextmenu.IAdapterContextMenu; |
||||
import com.bingce.controlnetwork.ui.vh.IndexTextViewHolder; |
||||
|
||||
public class BaseSelectableIndexTextWithContextMenuAdapter<T extends IUniversalListItem<?>> |
||||
extends SelectableIndexWithTextAdapter<T> |
||||
implements View.OnCreateContextMenuListener { |
||||
private int currentLongPressIndex = -1; |
||||
private final IAdapterContextMenu<T> adapterContextMenu; |
||||
|
||||
public BaseSelectableIndexTextWithContextMenuAdapter(String selectedId, |
||||
List<T> items, |
||||
IOnItemClick<T> callback, |
||||
IAdapterContextMenu<T> adapterContextMenu) { |
||||
super(selectedId, items, callback); |
||||
this.adapterContextMenu = adapterContextMenu; |
||||
} |
||||
|
||||
@Override |
||||
final public void onBindViewHolder(@NotNull IndexTextViewHolder holder, int position) { |
||||
super.onBindViewHolder(holder, position); |
||||
holder.itemView.setOnLongClickListener(v -> { |
||||
currentLongPressIndex = position; |
||||
return false; |
||||
}); |
||||
holder.itemView.setOnCreateContextMenuListener(this); |
||||
} |
||||
|
||||
@Override |
||||
final public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) { |
||||
if (adapterContextMenu == null) { |
||||
return; |
||||
} |
||||
menu.clear(); |
||||
for (int index = 0; index < adapterContextMenu.menuItemSize(); index++) { |
||||
menu.add(0, index, 0, adapterContextMenu.menuItemName(index)); |
||||
MenuItem menuItem = menu.getItem(index); |
||||
if (menuItem != null) { |
||||
menuItem.setOnMenuItemClickListener(item -> |
||||
adapterContextMenu.onMenuItemClick(getItem(currentLongPressIndex), item)); |
||||
} |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,51 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ContextMenu; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItemWithTitleAndSubtitle; |
||||
import com.bingce.controlnetwork.adapter.contextmenu.IAdapterContextMenu; |
||||
import com.bingce.controlnetwork.ui.vh.TitleWithSubtitleViewHolder; |
||||
|
||||
import java.util.List; |
||||
|
||||
public class BaseTitleAndSubtitleWithContextMenuAdapter<T extends IUniversalListItemWithTitleAndSubtitle<?>> |
||||
extends TitleWithSubtitleAdapter<T> |
||||
implements View.OnCreateContextMenuListener { |
||||
private int currentLongPressIndex = -1; |
||||
private final IAdapterContextMenu<T> adapterContextMenu; |
||||
|
||||
public BaseTitleAndSubtitleWithContextMenuAdapter(List<T> items, |
||||
IOnItemClick<T> callback, |
||||
IAdapterContextMenu<T> adapterContextMenu) { |
||||
super(items, callback); |
||||
this.adapterContextMenu = adapterContextMenu; |
||||
} |
||||
|
||||
@Override |
||||
final public void onBindViewHolder(TitleWithSubtitleViewHolder holder, int position) { |
||||
super.onBindViewHolder(holder, position); |
||||
holder.itemView.setOnLongClickListener(v -> { |
||||
currentLongPressIndex = position; |
||||
return false; |
||||
}); |
||||
holder.itemView.setOnCreateContextMenuListener(this); |
||||
} |
||||
|
||||
@Override |
||||
final public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) { |
||||
if (adapterContextMenu == null) { |
||||
return; |
||||
} |
||||
menu.clear(); |
||||
for (int index = 0; index < adapterContextMenu.menuItemSize(); index++) { |
||||
menu.add(0, index, 0, adapterContextMenu.menuItemName(index)); |
||||
MenuItem menuItem = menu.getItem(index); |
||||
if (menuItem != null) { |
||||
menuItem.setOnMenuItemClickListener(item -> |
||||
adapterContextMenu.onMenuItemClick(getItem(currentLongPressIndex), item)); |
||||
} |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,49 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.content.Context; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.point.PointRecord; |
||||
import com.bingce.controlapphelper.model.PickPointResult; |
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
import java.util.List; |
||||
|
||||
/* |
||||
* 限差详情adapter |
||||
* */ |
||||
public class GlobalControlPointSelectAdapter extends AbstractPointSelectAdapter { |
||||
private final List<PointRecord> pointRecordList; |
||||
|
||||
public GlobalControlPointSelectAdapter(List<PointRecord> pointRecords, |
||||
PickPointResult defaultValue, |
||||
int maxCount,//boolean singlePick,
|
||||
Context context) { |
||||
super(defaultValue, maxCount, context); |
||||
this.pointRecordList = pointRecords; |
||||
} |
||||
|
||||
@Override |
||||
public int getGroupCount() { |
||||
return 1; |
||||
} |
||||
|
||||
@Override |
||||
public int getChildrenCount(int groupPosition) { |
||||
return pointRecordList.size(); |
||||
} |
||||
|
||||
@Override |
||||
public String getGroup(int groupPosition) { |
||||
return context().getString(R.string.global_control_point); |
||||
} |
||||
|
||||
@Override |
||||
public PointRecord getChild(int groupPosition, int childPosition) { |
||||
return pointRecordList.get(childPosition); |
||||
} |
||||
|
||||
@Override |
||||
protected boolean showGroupArrow() { |
||||
return false; |
||||
} |
||||
} |
@ -0,0 +1,9 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.MenuItem; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
|
||||
public interface IOnContextItemSelectedCallback { |
||||
void onContextItemSelected(@NonNull MenuItem item); |
||||
} |
@ -0,0 +1,9 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
|
||||
import java.util.List; |
||||
|
||||
public interface IUpdateListAdapter<T extends IUniversalListItem<?>> { |
||||
void updateData(List<T> list); |
||||
} |
@ -0,0 +1,88 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
import android.widget.TextView; |
||||
|
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.ui.vh.IndexTextViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
public class IndexWithTextAdapter<T extends IUniversalListItem<?>> extends BaseAdapter<T, IndexTextViewHolder> { |
||||
private IOnItemClick<T> callback; |
||||
private boolean showIndex = true; |
||||
|
||||
public IndexWithTextAdapter(List<T> items, IOnItemClick<T> callback) { |
||||
super(items); |
||||
this.callback = callback; |
||||
} |
||||
|
||||
public IndexWithTextAdapter(List<T> items) { |
||||
super(items); |
||||
this.callback = null; |
||||
} |
||||
|
||||
public void setCallback(IOnItemClick<T> callback) { |
||||
this.callback = callback; |
||||
} |
||||
|
||||
protected ViewItemType itemType() { |
||||
return ViewItemType.indexWithName; |
||||
} |
||||
|
||||
@Override |
||||
final protected IndexTextViewHolder createVH(@NotNull ViewGroup parent, int viewType) { |
||||
RecyclerView.ViewHolder viewHolder = ViewFactory.generatorViewHolder(parent.getContext(), parent, itemType()); |
||||
if (viewHolder instanceof IndexTextViewHolder) { |
||||
return (IndexTextViewHolder) viewHolder; |
||||
} |
||||
return null; |
||||
} |
||||
|
||||
protected void hideIndex() { |
||||
showIndex = false; |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
protected void showIndex() { |
||||
showIndex = true; |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
protected boolean clickEnable(int position) { |
||||
return true; |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(final @NotNull IndexTextViewHolder holder, int position) { |
||||
T item = getItem(position); |
||||
if (showIndex) { |
||||
holder.index.setVisibility(View.VISIBLE); |
||||
holder.index.setText(String.valueOf(position + 1)); |
||||
} else { |
||||
holder.index.setVisibility(View.GONE); |
||||
} |
||||
onSetName(holder.name, item); |
||||
holder.itemView.setOnClickListener(v -> { |
||||
if (callback != null && clickEnable(position)) { |
||||
callback.onItemClick(item); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
protected void onSetName(TextView nameTextView, T item) { |
||||
nameTextView.setText(item.getName()); |
||||
} |
||||
|
||||
public interface IOnItemClick<T extends IUniversalListItem<?>> { |
||||
void onItemClick(T item); |
||||
} |
||||
} |
@ -0,0 +1,20 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
|
||||
import java.util.List; |
||||
|
||||
public class IndexWithTextAndPrefixAdapter<T extends IUniversalListItem<?>> extends IndexWithTextAdapter<T> { |
||||
public IndexWithTextAndPrefixAdapter(List<T> items, IOnItemClick<T> callback) { |
||||
super(items, callback); |
||||
} |
||||
|
||||
public IndexWithTextAndPrefixAdapter(List<T> items) { |
||||
super(items); |
||||
} |
||||
|
||||
protected ViewItemType itemType() { |
||||
return ViewItemType.indexWithNameAndPrefix; |
||||
} |
||||
} |
@ -0,0 +1,122 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.IAdapter; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlapphelper.surveyor.data.CachedDataAloneDistance; |
||||
import com.bingce.controlapphelper.surveyor.data.ICachedData; |
||||
import com.bingce.controlapphelper.surveyor.data.ICycleRecorder; |
||||
import com.bingce.controlapphelper.surveyor.data.IDistanceTypeChangeListener; |
||||
import com.bingce.controlapphelper.surveyor.data.IMeasureCache; |
||||
import com.bingce.controlapphelper.surveyor.data.ISurveyorData; |
||||
|
||||
import com.bingce.controlnetwork.ui.vh.SurveyorDataAloneDistanceViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.SurveyorDataViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
/** |
||||
* 测量记录adapter |
||||
* 井定向-距离 |
||||
*/ |
||||
public class MeasureAngleDistanceAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> |
||||
implements IAdapter, IDistanceTypeChangeListener { |
||||
|
||||
public static final String TYPE_ANGLE = "TYPE_ANGLE"; |
||||
public static final String TYPE_DISTANCE = "TYPE_DISTANCE"; |
||||
|
||||
private final IMeasureCache cachedData; |
||||
private final ISurveyorData surveyorData; |
||||
private final ICycleRecorder cycleRecorder; |
||||
private boolean showSlopDistance = true; |
||||
private final String stationId; |
||||
private final String type;//区分水平还是距离
|
||||
|
||||
|
||||
public MeasureAngleDistanceAdapter( |
||||
String stationId, |
||||
IMeasureCache cachedData, |
||||
ICycleRecorder cycleRecorder, |
||||
ISurveyorData surveyorData, |
||||
String type) { |
||||
this.stationId = stationId; |
||||
this.cachedData = cachedData; |
||||
this.surveyorData = surveyorData; |
||||
this.cycleRecorder = cycleRecorder; |
||||
this.type = type; |
||||
//注册数据监听
|
||||
cachedData.register(this); |
||||
} |
||||
|
||||
@NonNull |
||||
@Override |
||||
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { |
||||
RecyclerView.ViewHolder vh = null; |
||||
switch (type) { |
||||
case TYPE_ANGLE: |
||||
vh = ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewItemType.surveyorStationPointItem); |
||||
break; |
||||
case TYPE_DISTANCE: |
||||
vh = ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewItemType.aloneDistanceMeasure); |
||||
break; |
||||
} |
||||
assert vh != null; |
||||
return vh; |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) { |
||||
if (holder instanceof SurveyorDataAloneDistanceViewHolder) { |
||||
SurveyorDataAloneDistanceViewHolder holderDistance = (SurveyorDataAloneDistanceViewHolder) holder; |
||||
holderDistance.setup(position, |
||||
stationId, |
||||
showSlopDistance, |
||||
(CachedDataAloneDistance) cachedData, |
||||
cycleRecorder, |
||||
surveyorData); |
||||
} else if (holder instanceof SurveyorDataViewHolder) { |
||||
SurveyorDataViewHolder holderHorizontalAngle = (SurveyorDataViewHolder) holder; |
||||
holderHorizontalAngle.setup(position, |
||||
stationId, |
||||
showSlopDistance, |
||||
(ICachedData) cachedData, |
||||
cycleRecorder, |
||||
surveyorData); |
||||
} |
||||
|
||||
holder.itemView.setOnClickListener(v -> { |
||||
if (iItemClickListener != null) { |
||||
iItemClickListener.click(position); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public int getItemCount() { |
||||
return cachedData.pointCount(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDataChange() { |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
@Override |
||||
public void onShowSlopDistance(boolean value) { |
||||
this.showSlopDistance = value; |
||||
} |
||||
|
||||
|
||||
private IItemClickListener iItemClickListener; |
||||
|
||||
public void setOnItemClickListener(IItemClickListener iItemClickListener) { |
||||
this.iItemClickListener = iItemClickListener; |
||||
} |
||||
|
||||
public interface IItemClickListener { |
||||
void click(int position); |
||||
} |
||||
} |
@ -0,0 +1,98 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.IAdapter; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlapphelper.surveyor.data.ICachedData; |
||||
import com.bingce.controlapphelper.surveyor.data.ICycleRecorder; |
||||
import com.bingce.controlapphelper.surveyor.data.IDistanceTypeChangeListener; |
||||
import com.bingce.controlapphelper.surveyor.data.IMeasureCache; |
||||
import com.bingce.controlapphelper.surveyor.data.ISurveyorData; |
||||
|
||||
import java.util.Objects; |
||||
|
||||
import com.bingce.controlnetwork.ui.vh.SurveyorDataViewHolderHeightTraverse; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
/** |
||||
* 高程导线数据适配器 |
||||
*/ |
||||
public class MeasureHeightTraverseAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> |
||||
implements IAdapter, IDistanceTypeChangeListener { |
||||
|
||||
private final IMeasureCache cachedData; |
||||
private final ISurveyorData surveyorData; |
||||
private final ICycleRecorder cycleRecorder; |
||||
private boolean showSlopDistance = true; |
||||
private final String stationId; |
||||
private final int typeBackOrFront;//区分后视还是前视
|
||||
|
||||
|
||||
public MeasureHeightTraverseAdapter( |
||||
String stationId, |
||||
IMeasureCache cachedData, |
||||
ICycleRecorder cycleRecorder, |
||||
ISurveyorData surveyorData, |
||||
int typeBackOrFront) { |
||||
this.stationId = stationId; |
||||
this.cachedData = cachedData; |
||||
this.surveyorData = surveyorData; |
||||
this.cycleRecorder = cycleRecorder; |
||||
this.typeBackOrFront = typeBackOrFront; |
||||
//注册数据监听
|
||||
cachedData.register(this); |
||||
} |
||||
|
||||
@NonNull |
||||
@Override |
||||
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { |
||||
return Objects.requireNonNull(ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewItemType.heightTraverseSurveyor)); |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) { |
||||
SurveyorDataViewHolderHeightTraverse viewHolder = (SurveyorDataViewHolderHeightTraverse) holder; |
||||
viewHolder.setup(position, |
||||
stationId, |
||||
showSlopDistance, |
||||
(ICachedData) cachedData, |
||||
cycleRecorder, |
||||
surveyorData); |
||||
|
||||
holder.itemView.setOnClickListener(v -> { |
||||
if (iItemClickListener != null) { |
||||
iItemClickListener.click(position); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public int getItemCount() { |
||||
return cachedData.pointCount(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDataChange() { |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
@Override |
||||
public void onShowSlopDistance(boolean value) { |
||||
this.showSlopDistance = value; |
||||
} |
||||
|
||||
|
||||
private IItemClickListener iItemClickListener; |
||||
|
||||
public void setOnItemClickListener(IItemClickListener iItemClickListener) { |
||||
this.iItemClickListener = iItemClickListener; |
||||
} |
||||
|
||||
public interface IItemClickListener { |
||||
void click(int position); |
||||
} |
||||
} |
@ -0,0 +1,71 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.View; |
||||
import android.widget.ImageView; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.ui.vh.IndexTextSelectableViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.IndexTextViewHolder; |
||||
|
||||
public class MultipleSelectableIndexWithTextAdapter<T extends IUniversalListItem<?>> extends IndexWithTextAdapter<T> { |
||||
private final List<String> selectedIds = new ArrayList<>(); |
||||
|
||||
public MultipleSelectableIndexWithTextAdapter(List<String> selectedIds, |
||||
List<T> items, |
||||
IOnItemClick<T> callback) { |
||||
super(items); |
||||
setCallback(item -> { |
||||
onItemClicked(item.getId()); |
||||
if (callback == null) { |
||||
return; |
||||
} |
||||
callback.onItemClick(item); |
||||
}); |
||||
this.selectedIds.addAll(selectedIds); |
||||
} |
||||
|
||||
protected void onItemClicked(String id) { |
||||
if (selectedIds.contains(id)) { |
||||
selectedIds.remove(id); |
||||
} else { |
||||
selectedIds.add(id); |
||||
} |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
@Override |
||||
protected ViewItemType itemType() { |
||||
return ViewItemType.indexWithNameSelectable; |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(@NotNull IndexTextViewHolder holder, int position) { |
||||
super.onBindViewHolder(holder, position); |
||||
//设置状态
|
||||
T t = getItem(position); |
||||
if (t == null) { |
||||
return; |
||||
} |
||||
if (holder instanceof IndexTextSelectableViewHolder) { |
||||
ImageView iv = ((IndexTextSelectableViewHolder) holder).status; |
||||
if (iv != null) { |
||||
if (selectedIds.contains(t.getId())) { |
||||
iv.setVisibility(View.VISIBLE); |
||||
} else { |
||||
iv.setVisibility(View.GONE); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
public List<String> selectedIds() { |
||||
return selectedIds; |
||||
} |
||||
} |
@ -0,0 +1,75 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.content.Context; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.fragment.app.FragmentActivity; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.SurveyorDatabaseFactory; |
||||
import com.bingce.controlapphelper.datasource.database.point.PointRecord; |
||||
import com.bingce.controlapphelper.util.PointUtil; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
|
||||
import java.util.List; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
import com.bingce.controlnetwork.adapter.contextmenu.ContextMenuDeleteEdit; |
||||
import com.bingce.controlnetwork.fragment.PointFragment; |
||||
import com.bingce.controlnetwork.ui.widget.dialog.LoadingUtil; |
||||
|
||||
public class PointRecordAdapter extends BaseIndexTextWithContextMenuAdapter<PointRecord> { |
||||
public PointRecordAdapter(List<PointRecord> items, |
||||
@NonNull FragmentActivity activity) { |
||||
super(items, |
||||
item -> editRecord(activity, item), |
||||
new ContextMenuDeleteEdit<PointRecord>() { |
||||
@Override |
||||
protected void delete(PointRecord item) { |
||||
deletePoint(activity, item); |
||||
} |
||||
|
||||
@Override |
||||
protected void edit(PointRecord item) { |
||||
editRecord(activity, item); |
||||
} |
||||
|
||||
/** |
||||
* 删除点 |
||||
* 项目里这个点只要有数据就不能删除 |
||||
* |
||||
* @param item |
||||
*/ |
||||
private void deletePoint(Context context, PointRecord item) { |
||||
LoadingUtil.show(context, null); |
||||
|
||||
ThreadPoolUtil.execute(() -> { |
||||
String msg = PointUtil.getUsedMsg(item.getId()); |
||||
if (msg != null) { |
||||
ToastUtils.showShort(msg); |
||||
dismissLoading(); |
||||
return; |
||||
} |
||||
SurveyorDatabaseFactory |
||||
.instance |
||||
.getPointDataSource() |
||||
.delete(item); |
||||
|
||||
dismissLoading(); |
||||
}); |
||||
} |
||||
|
||||
private void dismissLoading() { |
||||
ThreadPoolUtil.executeInMain(LoadingUtil::dismiss); |
||||
} |
||||
|
||||
}); |
||||
} |
||||
|
||||
|
||||
private static void editRecord(FragmentActivity activity, PointRecord record) { |
||||
PointFragment.edit(activity.getSupportFragmentManager(), |
||||
record.projectId, |
||||
record.getName(), record.getId(), record.getPointType(), record.getX(), record.getY(), record.getZ()); |
||||
} |
||||
} |
@ -0,0 +1,61 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.content.Context; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.point.PointRecord; |
||||
import com.bingce.controlapphelper.model.KnownAndUnknownPoints; |
||||
import com.bingce.controlapphelper.model.PickPointResult; |
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
import java.util.List; |
||||
|
||||
public class PointSelectAdapter extends AbstractPointSelectAdapter { |
||||
private final KnownAndUnknownPoints data; |
||||
private final List<PointRecord> globalPoints; |
||||
|
||||
public PointSelectAdapter(KnownAndUnknownPoints points, |
||||
List<PointRecord> globalPoints, |
||||
PickPointResult defaultValue, |
||||
int maxCount, |
||||
Context context) { |
||||
super(defaultValue, maxCount, context); |
||||
this.data = points; |
||||
this.globalPoints = globalPoints; |
||||
} |
||||
|
||||
@Override |
||||
public int getGroupCount() { |
||||
// return data.groupCount() + 1;
|
||||
return data.groupCount() ; |
||||
} |
||||
|
||||
@Override |
||||
public int getChildrenCount(int groupPosition) { |
||||
if (groupPosition >= data.groupCount()) { |
||||
if (globalPoints == null) { |
||||
return 0; |
||||
} |
||||
return globalPoints.size(); |
||||
} |
||||
return data.childrenCount(groupPosition); |
||||
} |
||||
|
||||
@Override |
||||
public String getGroup(int groupPosition) { |
||||
if (groupPosition >= data.groupCount()) { |
||||
return context().getString(R.string.global_control_point); |
||||
} |
||||
return data.groupName(groupPosition, context()); |
||||
} |
||||
|
||||
@Override |
||||
public PointRecord getChild(int groupPosition, int childPosition) { |
||||
if (groupPosition >= data.groupCount()) { |
||||
if (globalPoints == null) { |
||||
return null; |
||||
} |
||||
return globalPoints.get(childPosition); |
||||
} |
||||
return data.child(groupPosition, childPosition); |
||||
} |
||||
} |
@ -0,0 +1,94 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ContextMenu; |
||||
import android.view.LayoutInflater; |
||||
import android.view.MenuItem; |
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.prism.PrismRecord; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.adapter.contextmenu.IAdapterContextMenu; |
||||
import com.bingce.controlnetwork.ui.vh.PrismManageViewHolder; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.List; |
||||
|
||||
public class PrismMagegeAdapter extends BaseAdapter<PrismRecord, PrismManageViewHolder> |
||||
implements View.OnCreateContextMenuListener { |
||||
private IOnItemClick<PrismRecord> callback; |
||||
|
||||
private int currentLongPressIndex = -1; |
||||
|
||||
private final IAdapterContextMenu<PrismRecord> adapterContextMenu; |
||||
|
||||
public PrismMagegeAdapter(List<PrismRecord> items, IOnItemClick<PrismRecord> callback, IAdapterContextMenu<PrismRecord> adapterContextMenu) { |
||||
super(items); |
||||
this.callback = callback; |
||||
this.adapterContextMenu = adapterContextMenu; |
||||
} |
||||
|
||||
public void setCallback(IOnItemClick<PrismRecord> callback) { |
||||
this.callback = callback; |
||||
} |
||||
|
||||
@Override |
||||
final protected PrismManageViewHolder createVH(@NotNull ViewGroup parent, int viewType) { |
||||
View itemView = LayoutInflater.from(parent.getContext()).inflate(R.layout.item_prism_manager, parent, false); |
||||
PrismManageViewHolder prismManageViewHolder = new PrismManageViewHolder(itemView); |
||||
return prismManageViewHolder; |
||||
} |
||||
|
||||
protected boolean clickEnable(int position) { |
||||
return true; |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(final @NotNull PrismManageViewHolder holder, int position) { |
||||
//长按出菜单
|
||||
holder.itemView.setOnLongClickListener(v -> { |
||||
currentLongPressIndex = position; |
||||
return false; |
||||
}); |
||||
holder.itemView.setOnCreateContextMenuListener(this); |
||||
|
||||
PrismRecord item = getItem(position); |
||||
|
||||
holder.tvName.setText(item.getShowPrismTypeName()); |
||||
holder.tvType.setText(item.prismTypeLarge); |
||||
|
||||
//绝对常数
|
||||
holder.tvConstant.setText(item.prismTypeConstant); |
||||
|
||||
holder.itemView.setOnClickListener(v -> { |
||||
if (callback != null && clickEnable(position)) { |
||||
callback.onItemClick(item); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
public interface IOnItemClick<T> { |
||||
void onItemClick(T item); |
||||
} |
||||
|
||||
@Override |
||||
final public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) { |
||||
if (adapterContextMenu == null) { |
||||
return; |
||||
} |
||||
PrismRecord currentItem = getItem(currentLongPressIndex); |
||||
if (currentItem.modify == PrismRecord.MODIFY_DEFAULT) { |
||||
return; |
||||
} |
||||
menu.clear(); |
||||
for (int index = 0; index < adapterContextMenu.menuItemSize(); index++) { |
||||
menu.add(0, index, 0, adapterContextMenu.menuItemName(index)); |
||||
MenuItem menuItem = menu.getItem(index); |
||||
if (menuItem != null) { |
||||
menuItem.setOnMenuItemClickListener(menuItemBack -> |
||||
adapterContextMenu.onMenuItemClick(currentItem, menuItemBack)); |
||||
} |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,28 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.content.Context; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.fragment.app.FragmentManager; |
||||
import androidx.lifecycle.LifecycleOwner; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.project.ProjectRecord; |
||||
import com.bingce.controlapphelper.util.IUIRunner; |
||||
|
||||
import java.util.ArrayList; |
||||
|
||||
import com.bingce.controlnetwork.adapter.contextmenu.ProjectAdapterContextMenu; |
||||
|
||||
public class ProjectListAdapter extends BaseIndexTextWithContextMenuAdapter<ProjectRecord> |
||||
implements IUpdateListAdapter<ProjectRecord> { |
||||
|
||||
public ProjectListAdapter(IOnItemClick<ProjectRecord> callback, |
||||
@NonNull Context context, |
||||
@NonNull IUIRunner iuiRunner, |
||||
@NonNull LifecycleOwner lifecycleOwner, |
||||
@NonNull FragmentManager fragmentManager) { |
||||
super(new ArrayList<>(), |
||||
callback, |
||||
new ProjectAdapterContextMenu(context, iuiRunner, lifecycleOwner, fragmentManager)); |
||||
} |
||||
} |
@ -0,0 +1,56 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
|
||||
import com.bingce.controlapphelper.model.UniversalListItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
|
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.ui.vh.IndexTextSelectableViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
public class ReSurveyorCycleAdapter extends BaseAdapter<UniversalListItem<String>, IndexTextSelectableViewHolder> { |
||||
|
||||
private final List<UniversalListItem<String>> dataList; |
||||
private final ICallBack callBack; |
||||
|
||||
private int selectPosition = -1; |
||||
|
||||
public ReSurveyorCycleAdapter(List<UniversalListItem<String>> dataList, ICallBack callBack) { |
||||
super(dataList); |
||||
this.dataList = dataList; |
||||
this.callBack = callBack; |
||||
} |
||||
|
||||
@Override |
||||
protected IndexTextSelectableViewHolder createVH(@NonNull ViewGroup parent, int viewType) { |
||||
return (IndexTextSelectableViewHolder) ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewItemType.indexWithNameSelectable); |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(@NonNull IndexTextSelectableViewHolder holder, int position) { |
||||
holder.index.setVisibility(View.GONE); |
||||
holder.name.setText(dataList.get(position).getName()); |
||||
|
||||
if (position == selectPosition) { |
||||
holder.status.setVisibility(View.VISIBLE); |
||||
} else { |
||||
holder.status.setVisibility(View.GONE); |
||||
} |
||||
|
||||
holder.itemView.setOnClickListener(v -> { |
||||
selectPosition = holder.getAbsoluteAdapterPosition(); |
||||
notifyItemRangeChanged(0, dataList.size()); |
||||
callBack.back(selectPosition); |
||||
}); |
||||
} |
||||
|
||||
public interface ICallBack { |
||||
void back(int cycleIndex); |
||||
} |
||||
|
||||
} |
@ -0,0 +1,61 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.content.Context; |
||||
|
||||
import androidx.fragment.app.FragmentManager; |
||||
import androidx.lifecycle.LifecycleOwner; |
||||
|
||||
import com.bingce.controlapphelper.model.UniversalListItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
|
||||
import java.util.List; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.fragment.TipsFragment; |
||||
|
||||
public class ResurveyorPointsAdapter extends MultipleSelectableIndexWithTextAdapter<ResurveyorPointsAdapter.Item> { |
||||
private final FragmentManager fragmentManager; |
||||
private final LifecycleOwner lifecycleOwner; |
||||
private final Context context; |
||||
|
||||
public ResurveyorPointsAdapter(List<String> selectedIds, |
||||
List<Item> items, |
||||
Context context, |
||||
FragmentManager fragmentManager, |
||||
LifecycleOwner lifecycleOwner) { |
||||
super(selectedIds, items, null); |
||||
this.fragmentManager = fragmentManager; |
||||
this.lifecycleOwner = lifecycleOwner; |
||||
this.context = context; |
||||
} |
||||
|
||||
@Override |
||||
protected void onItemClicked(String id) { |
||||
//判断上限数据
|
||||
if (!selectedIds().contains(id)) { |
||||
if (selectedIds().size() + 1 > getItemCount() / 3) { |
||||
TipsFragment.tipsOnly(fragmentManager, lifecycleOwner, context, |
||||
context.getString(R.string.tips_resurveyor_count_exceed_1_3)); |
||||
return; |
||||
} |
||||
} |
||||
if (getItem(0) != null && getItem(0).getId().equals(id)) { |
||||
ToastUtils.showShort(R.string.tips_resurveyor_must_select_0_point); |
||||
return; |
||||
} |
||||
super.onItemClicked(id); |
||||
} |
||||
|
||||
public static class Item extends UniversalListItem<String> { |
||||
public Item(String name, String id) { |
||||
super(name, id, null); |
||||
} |
||||
|
||||
@Override |
||||
public ViewItemType getType() { |
||||
return null; |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,99 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.View; |
||||
import android.widget.ImageView; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.ui.vh.IndexTextSelectableViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.IndexTextViewHolder; |
||||
|
||||
public class SelectableIndexWithTextAdapter<T extends IUniversalListItem<?>> extends IndexWithTextAdapter<T> { |
||||
private String selectedId; |
||||
private final List<String> enableList = new ArrayList<>(); |
||||
|
||||
public SelectableIndexWithTextAdapter(String selectedId, List<T> items, List<String> enableIndex, IOnItemClick<T> callback) { |
||||
super(items); |
||||
setCallback(item -> { |
||||
updateCurrentSelectedId(item.getId()); |
||||
if (callback == null) { |
||||
return; |
||||
} |
||||
callback.onItemClick(item); |
||||
}); |
||||
if (enableIndex != null) { |
||||
enableList.addAll(enableIndex); |
||||
} |
||||
this.selectedId = selectedId; |
||||
} |
||||
|
||||
public SelectableIndexWithTextAdapter(String selectedId, List<T> items, IOnItemClick<T> callback) { |
||||
this(selectedId, items, null, callback); |
||||
} |
||||
|
||||
protected void updateCurrentSelectedId(String id) { |
||||
selectedId = id; |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
// @Override
|
||||
// protected RecyclerView.ViewHolder createVH(@NotNull ViewGroup parent, int viewType) {
|
||||
// return ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewFactory.ItemType.indexWithNameSelectable);
|
||||
// }
|
||||
@Override |
||||
protected ViewItemType itemType() { |
||||
return ViewItemType.indexWithNameSelectable; |
||||
} |
||||
|
||||
@Override |
||||
protected boolean clickEnable(int position) { |
||||
if (enableList.isEmpty() || enableList.contains(String.valueOf(position))) { |
||||
return super.clickEnable(position); |
||||
} |
||||
return false; |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(@NotNull IndexTextViewHolder holder, int position) { |
||||
super.onBindViewHolder(holder, position); |
||||
//设置状态
|
||||
T t = getItem(position); |
||||
if (t == null) { |
||||
return; |
||||
} |
||||
if (holder instanceof IndexTextSelectableViewHolder) { |
||||
ImageView iv = ((IndexTextSelectableViewHolder) holder).status; |
||||
if (iv != null) { |
||||
if (t.getId().equals(selectedId)) { |
||||
iv.setVisibility(View.VISIBLE); |
||||
} else { |
||||
iv.setVisibility(View.GONE); |
||||
} |
||||
} |
||||
|
||||
if (!enableList.isEmpty()) { |
||||
if (enableList.contains(String.valueOf(position))) { |
||||
((IndexTextSelectableViewHolder) holder).mask.setVisibility(View.GONE); |
||||
((IndexTextSelectableViewHolder) holder).item.setAlpha(1f); |
||||
} else { |
||||
((IndexTextSelectableViewHolder) holder).mask.setVisibility(View.VISIBLE); |
||||
((IndexTextSelectableViewHolder) holder).item.setAlpha(.5f); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
protected String currentSelectedItemId() { |
||||
return selectedId; |
||||
} |
||||
|
||||
protected boolean isItemSelected(int index) { |
||||
return currentSelectedItemId().equals(getItem(index).getId()); |
||||
} |
||||
} |
@ -0,0 +1,83 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.content.Context; |
||||
import android.view.LayoutInflater; |
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
import android.widget.BaseAdapter; |
||||
import android.widget.ImageView; |
||||
import android.widget.TextView; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
public class SpinnerAdapter extends BaseAdapter { |
||||
|
||||
private final Context context; |
||||
|
||||
private final List<String> lists; |
||||
|
||||
|
||||
public SpinnerAdapter(Context context, List<String> list) { |
||||
this.context = context; |
||||
this.lists = new ArrayList<>(); |
||||
lists.addAll(list); |
||||
} |
||||
|
||||
@Override |
||||
public int getCount() { |
||||
return lists.size(); |
||||
} |
||||
|
||||
@Override |
||||
public String getItem(int position) { |
||||
return lists.get(position); |
||||
} |
||||
|
||||
@Override |
||||
public long getItemId(int position) { |
||||
return position; |
||||
} |
||||
|
||||
@Override |
||||
public View getView(int position, View convertView, ViewGroup parent) { |
||||
convertView = getConvertView(convertView, parent); |
||||
ViewHodler viewHodler = (ViewHodler) convertView.getTag(); |
||||
viewHodler.textView.setText(getItem(position)); |
||||
return convertView; |
||||
} |
||||
|
||||
@Override |
||||
public View getDropDownView(int position, View convertView, ViewGroup parent) { |
||||
convertView = getConvertView(convertView, parent); |
||||
ViewHodler viewHodler = (ViewHodler) convertView.getTag(); |
||||
viewHodler.imageView.setVisibility(position == 0 ? View.VISIBLE : View.GONE); |
||||
viewHodler.textView.setText(getItem(position)); |
||||
return convertView; |
||||
} |
||||
|
||||
|
||||
private View getConvertView(View convertView, ViewGroup parent) { |
||||
if (convertView == null) { |
||||
ViewHodler viewHodler = new ViewHodler(); |
||||
convertView = LayoutInflater.from(context).inflate(R.layout.item_spinner_content, parent, false); |
||||
viewHodler.textView = convertView.findViewById(R.id.tv); |
||||
viewHodler.imageView = convertView.findViewById(R.id.ivArrow); |
||||
convertView.setTag(viewHodler); |
||||
} |
||||
return convertView; |
||||
} |
||||
|
||||
private class ViewHodler { |
||||
public TextView textView; |
||||
public ImageView imageView; |
||||
} |
||||
|
||||
public void setLists(List<String> lists) { |
||||
this.lists.clear(); |
||||
this.lists.addAll(lists); |
||||
notifyDataSetChanged(); |
||||
} |
||||
} |
@ -0,0 +1,32 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.os.Bundle; |
||||
|
||||
import androidx.fragment.app.DialogFragment; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.surveyorcycle.SurveyorPeriodRecord; |
||||
|
||||
import java.util.ArrayList; |
||||
|
||||
import com.bingce.controlnetwork.adapter.contextmenu.SurveyorPeriodAdapterContextMenu; |
||||
import com.bingce.controlnetwork.fragment.BottomSheetSurveyorPeriodFragment; |
||||
|
||||
public class SurveyorPeriodAdapter extends BaseSelectableIndexTextWithContextMenuAdapter<SurveyorPeriodRecord> { |
||||
public SurveyorPeriodAdapter(String selectedId, DialogFragment fragment) { |
||||
super(selectedId, |
||||
new ArrayList<>(), |
||||
item -> { |
||||
Bundle args = new Bundle(); |
||||
args.putString(BottomSheetSurveyorPeriodFragment.KEY_RESULT_ID, item.getValue()); |
||||
args.putString(BottomSheetSurveyorPeriodFragment.KEY_RESULT_NAME, item.getName()); |
||||
fragment.getParentFragmentManager().setFragmentResult(BottomSheetSurveyorPeriodFragment.KEY_REQUEST_TIME, args); |
||||
fragment.dismiss(); |
||||
}, |
||||
new SurveyorPeriodAdapterContextMenu(fragment.getContext(), selectedId, |
||||
fragment.getViewLifecycleOwner(), fragment.getChildFragmentManager())); |
||||
} |
||||
|
||||
public void changeCurrentSelect(String id) { |
||||
updateCurrentSelectedId(id); |
||||
} |
||||
} |
@ -0,0 +1,287 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
|
||||
import static com.bingce.controlapphelper.datasource.database.surveyorstation.SurveyorStationRecord.isLineStation; |
||||
|
||||
import android.content.Context; |
||||
import android.widget.TextView; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.annotation.WorkerThread; |
||||
import androidx.fragment.app.FragmentManager; |
||||
import androidx.lifecycle.LifecycleOwner; |
||||
import androidx.lifecycle.LiveData; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.SurveyorDatabaseFactory; |
||||
import com.bingce.controlapphelper.datasource.database.line.LineRecord; |
||||
import com.bingce.controlapphelper.datasource.database.point.PointRecord; |
||||
import com.bingce.controlapphelper.datasource.database.surveyorrecord.ISurveyorRecordDataSource; |
||||
import com.bingce.controlapphelper.datasource.database.surveyorstation.SurveyorStationRecord; |
||||
import com.bingce.controlapphelper.util.IUIRunner; |
||||
import com.bingce.controlapphelper.util.StationUtil; |
||||
import com.bingce.controlapphelper.util.Tools; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.adapter.contextmenu.ContextMenuEdit; |
||||
import com.bingce.controlnetwork.fragment.TipsFragment; |
||||
import com.bingce.controlnetwork.fragment.TipsWith2OptionFragment; |
||||
import com.bingce.controlnetwork.fragment.stationdetail.SingleStationDetailAndEditFragment; |
||||
import com.bingce.controlnetwork.util.SurveyorStationUtil; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
|
||||
import java.util.HashMap; |
||||
import java.util.List; |
||||
import java.util.Map; |
||||
|
||||
public class SurveyorStationListAdapter extends BaseIndexPrefixTextWithContextMenuAdapter<SurveyorStationRecord> { |
||||
private final LifecycleOwner lifecycleOwner; |
||||
|
||||
public SurveyorStationListAdapter(List<SurveyorStationRecord> items, |
||||
@NonNull FragmentManager fragmentManager, |
||||
@NonNull LifecycleOwner lifecycleOwner, |
||||
@NonNull IUIRunner iuiRunner, |
||||
Context context, |
||||
IOnItemClick<SurveyorStationRecord> itemClick, |
||||
boolean editAble) { |
||||
super(items, itemClick, |
||||
contextMenu(fragmentManager, lifecycleOwner, iuiRunner, context, editAble)); |
||||
this.lifecycleOwner = lifecycleOwner; |
||||
} |
||||
|
||||
@Override |
||||
protected void onSetName(TextView nameTextView, SurveyorStationRecord item) { |
||||
String pointId = item.getItems().get(0).getPointId(); |
||||
nameTextView.setText(cachedId2Name.get(pointId)); |
||||
|
||||
if (item.getItems() == null || item.getItems().isEmpty()) { |
||||
return; |
||||
} |
||||
//停止原livedata订阅
|
||||
Object tag = nameTextView.getTag(); |
||||
LiveData<PointRecord> pointRecordLiveData; |
||||
if (tag instanceof LiveData) { |
||||
pointRecordLiveData = (LiveData<PointRecord>) tag; |
||||
pointRecordLiveData.removeObservers(lifecycleOwner); |
||||
} |
||||
//创建新订阅
|
||||
pointRecordLiveData = SurveyorDatabaseFactory |
||||
.instance |
||||
.getPointDataSource() |
||||
.findById(pointId); |
||||
nameTextView.setTag(pointRecordLiveData); |
||||
|
||||
//监听
|
||||
pointRecordLiveData.observe(lifecycleOwner, pointRecord -> { |
||||
if (pointRecord == null) { |
||||
return; |
||||
} |
||||
nameTextView.setText(pointRecord.getName()); |
||||
cachedId2Name.put(pointRecord.id, pointRecord.getName()); |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
protected void onSetPrefix(TextView prefixTextView, SurveyorStationRecord item) { |
||||
String lineId = item.getLineId(); |
||||
if (cachedId2LineName.containsKey(lineId)) { |
||||
prefixTextView.setText(cachedId2LineName.get(lineId)); |
||||
} else { |
||||
prefixTextView.setText(StationUtil.mulCycleAngleStationPrefix()); |
||||
} |
||||
|
||||
if (lineId == null || lineId.isEmpty()) { |
||||
return; |
||||
} |
||||
//停止原livedata订阅
|
||||
Object tag = prefixTextView.getTag(); |
||||
LiveData<LineRecord> lineRecordLiveData; |
||||
if (tag instanceof LiveData) { |
||||
lineRecordLiveData = (LiveData<LineRecord>) tag; |
||||
lineRecordLiveData.removeObservers(lifecycleOwner); |
||||
} |
||||
//创建新订阅
|
||||
lineRecordLiveData = SurveyorDatabaseFactory |
||||
.instance |
||||
.getLineRecordDatabase() |
||||
.liveData(lineId); |
||||
prefixTextView.setTag(lineRecordLiveData); |
||||
|
||||
//监听
|
||||
lineRecordLiveData.observe(lifecycleOwner, lineRecord -> { |
||||
if (lineRecord == null) { |
||||
return; |
||||
} |
||||
prefixTextView.setText(lineRecord.name + "-"); |
||||
cachedId2LineName.put(lineRecord.id, lineRecord.name); |
||||
cachedId2LineType.put(lineRecord.id, lineRecord.type); |
||||
}); |
||||
} |
||||
|
||||
private static final Map<String, String> cachedId2Name = new HashMap<>(); |
||||
private static final Map<String, String> cachedId2LineName = new HashMap<>(); |
||||
private static final Map<String, String> cachedId2LineType = new HashMap<>(); |
||||
|
||||
private static ContextMenuEdit<SurveyorStationRecord> contextMenu( |
||||
@NonNull FragmentManager fragmentManager, |
||||
@NonNull LifecycleOwner lifecycleOwner, |
||||
@NonNull IUIRunner iuiRunner, |
||||
Context context, |
||||
boolean editAble) { |
||||
if (!editAble) { |
||||
return null; |
||||
} |
||||
return new ContextMenuEdit<SurveyorStationRecord>() { |
||||
@Override |
||||
protected void edit(SurveyorStationRecord item) { |
||||
if (SurveyorStationRecord.isLineWell(cachedId2LineType.get(item.getLineId()))) { |
||||
TipsWith2OptionFragment.tips(fragmentManager, lifecycleOwner, |
||||
context.getString(R.string.button_edit_station), |
||||
context.getString(R.string.button_delete_station), |
||||
context.getString(R.string.tips_select_default_station_operator_well), |
||||
new TipsWith2OptionFragment.SimpleCallback() { |
||||
@Override |
||||
public void onConfirm() { |
||||
SurveyorStationUtil.editLine(context, item.getLineId()); |
||||
} |
||||
|
||||
@Override |
||||
public void onCancel() { |
||||
try2DeleteLine(item.getLineId(), context, fragmentManager, lifecycleOwner, iuiRunner); |
||||
} |
||||
}); |
||||
return; |
||||
} |
||||
|
||||
|
||||
//检测是否属于导线测量
|
||||
if (isLineStation(item.getLineId())) { |
||||
String lineId = item.getLineId(); |
||||
TipsWith2OptionFragment.tips(fragmentManager, lifecycleOwner, |
||||
context.getString(R.string.button_edit_line), |
||||
context.getString(R.string.button_delete_line), |
||||
context.getString(R.string.tips_forbid_delete_station_because_batch), |
||||
new TipsWith2OptionFragment.SimpleCallback() { |
||||
@Override |
||||
public void onConfirm() { |
||||
try2EditLine(lineId, context, fragmentManager, lifecycleOwner, iuiRunner); |
||||
} |
||||
|
||||
@Override |
||||
public void onCancel() { |
||||
try2DeleteLine(lineId, context, fragmentManager, lifecycleOwner, iuiRunner); |
||||
} |
||||
}); |
||||
} else { |
||||
TipsWith2OptionFragment.tips(fragmentManager, lifecycleOwner, |
||||
context.getString(R.string.button_edit_station), |
||||
context.getString(R.string.button_delete_station), |
||||
context.getString(R.string.tips_select_default_station_operator), |
||||
new TipsWith2OptionFragment.SimpleCallback() { |
||||
@Override |
||||
public void onConfirm() { |
||||
ThreadPoolUtil.execute(() -> { |
||||
String stationName = StationUtil.getStationName(item); |
||||
String lineType = StationUtil.getLineTypeFromStation(item); |
||||
SingleStationDetailAndEditFragment.start(context, item.getId(), stationName, item.getProjectId(), lineType); |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public void onCancel() { |
||||
String stationId = item.getId(); |
||||
try2DeleteStation(stationId, context, fragmentManager, lifecycleOwner, iuiRunner); |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
}; |
||||
} |
||||
|
||||
@WorkerThread |
||||
private static boolean isStationHasData(String stationId) { |
||||
ISurveyorRecordDataSource surveyorRecordDataSource = |
||||
SurveyorDatabaseFactory.instance.getSurveyorRecordDataSource(); |
||||
return surveyorRecordDataSource.recordCount(stationId) > 0; |
||||
} |
||||
|
||||
@WorkerThread |
||||
private static boolean isLineHasData(String lineId) { |
||||
boolean lineHasData = Tools.isLineHasData(lineId); |
||||
// ISurveyorStationDataSource stationDataSource =
|
||||
// SurveyorDatabaseFactory.instance.getSurveyorStation();
|
||||
// List<SurveyorStationRecord> stationRecordList = stationDataSource.getDataListByLine(lineId);
|
||||
// if (stationRecordList == null || stationRecordList.isEmpty()) {
|
||||
// return false;
|
||||
// }
|
||||
// ISurveyorRecordDataSource surveyorRecordDataSource =
|
||||
// SurveyorDatabaseFactory.instance.getSurveyorRecordDataSource();
|
||||
// boolean hasData = false;
|
||||
// for (SurveyorStationRecord stationRecord : stationRecordList) {
|
||||
// if (stationRecord == null) {
|
||||
// continue;
|
||||
// }
|
||||
// if (surveyorRecordDataSource.recordCount(stationRecord.getId()) <= 0) {
|
||||
// continue;
|
||||
// }
|
||||
// hasData = true;
|
||||
// break;
|
||||
// }
|
||||
return lineHasData; |
||||
} |
||||
|
||||
public static void try2DeleteLine(String lineId, Context context, |
||||
FragmentManager fragmentManager, LifecycleOwner lifecycleOwner, |
||||
@NonNull IUIRunner iuiRunner) { |
||||
ThreadPoolUtil.execute(() -> { |
||||
if (isLineHasData(lineId)) { |
||||
iuiRunner.runOnUI(() -> TipsFragment.cancelAbleTips(fragmentManager, lifecycleOwner, context, |
||||
context.getString(R.string.tips_is_sure_to_delete_line_with_record), |
||||
4, |
||||
() -> SurveyorDatabaseFactory |
||||
.instance |
||||
.getSurveyorStation() |
||||
.deleteByLineId(lineId))); |
||||
} else { |
||||
SurveyorDatabaseFactory |
||||
.instance |
||||
.getSurveyorStation() |
||||
.deleteByLineId(lineId); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
public static void try2EditLine(String lineId, Context context, |
||||
FragmentManager fragmentManager, LifecycleOwner lifecycleOwner, |
||||
@NonNull IUIRunner iuiRunner) { |
||||
ThreadPoolUtil.execute(() -> { |
||||
if (isLineHasData(lineId)) { |
||||
iuiRunner.runOnUI(() -> TipsFragment.cancelAbleTips(fragmentManager, lifecycleOwner, context, |
||||
context.getString(R.string.tips_is_sure_to_edit_line_with_record), |
||||
4, |
||||
() -> SurveyorStationUtil.editLine(context, lineId))); |
||||
} else { |
||||
SurveyorStationUtil.editLine(context, lineId); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
public static void try2DeleteStation(String stationId, Context context, |
||||
FragmentManager fragmentManager, LifecycleOwner lifecycleOwner, |
||||
@NonNull IUIRunner iuiRunner) { |
||||
ThreadPoolUtil.execute(() -> { |
||||
if (isStationHasData(stationId)) { |
||||
iuiRunner.runOnUI(() -> TipsFragment.cancelAbleTips(fragmentManager, lifecycleOwner, context, |
||||
context.getString(R.string.tips_is_sure_to_delete_station_with_record), |
||||
4, |
||||
() -> SurveyorDatabaseFactory |
||||
.instance |
||||
.getSurveyorStation() |
||||
.deleteById(stationId))); |
||||
} else { |
||||
SurveyorDatabaseFactory |
||||
.instance |
||||
.getSurveyorStation() |
||||
.deleteById(stationId); |
||||
} |
||||
}); |
||||
} |
||||
} |
@ -0,0 +1,77 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.IAdapter; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlapphelper.surveyor.data.ICachedData; |
||||
import com.bingce.controlapphelper.surveyor.data.ICycleRecorder; |
||||
import com.bingce.controlapphelper.surveyor.data.IDistanceTypeChangeListener; |
||||
import com.bingce.controlapphelper.surveyor.data.ISurveyorData; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import com.bingce.controlnetwork.ui.vh.SurveyorDataViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
/* |
||||
* 测量记录adapter |
||||
* */ |
||||
public class SurveyorStationRecordsAdapter extends RecyclerView.Adapter<SurveyorDataViewHolder> |
||||
implements IAdapter, IDistanceTypeChangeListener { |
||||
private final ICachedData cachedData; |
||||
private final ISurveyorData surveyorData; |
||||
private final ICycleRecorder cycleRecorder; |
||||
private boolean showSlopDistance = true; |
||||
private final String stationId; |
||||
|
||||
public SurveyorStationRecordsAdapter( |
||||
String stationId, |
||||
ICachedData cachedData, |
||||
ICycleRecorder cycleRecorder, |
||||
ISurveyorData surveyorData) { |
||||
this.stationId = stationId; |
||||
this.cachedData = cachedData; |
||||
this.surveyorData = surveyorData; |
||||
this.cycleRecorder = cycleRecorder; |
||||
//注册数据监听
|
||||
cachedData.register(this); |
||||
} |
||||
|
||||
@NonNull |
||||
@NotNull |
||||
@Override |
||||
public SurveyorDataViewHolder onCreateViewHolder(@NonNull @NotNull ViewGroup parent, int viewType) { |
||||
RecyclerView.ViewHolder vh = ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewItemType.surveyorStationPointItem); |
||||
assert vh != null; |
||||
return (SurveyorDataViewHolder) vh; |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(@NonNull @NotNull SurveyorDataViewHolder holder, int position) { |
||||
holder.setup(position, |
||||
stationId, |
||||
showSlopDistance, |
||||
cachedData, |
||||
cycleRecorder, |
||||
surveyorData); |
||||
} |
||||
|
||||
@Override |
||||
public int getItemCount() { |
||||
return cachedData.pointCount(); |
||||
} |
||||
|
||||
@Override |
||||
public void onDataChange() { |
||||
notifyItemRangeChanged(0, getItemCount()); |
||||
} |
||||
|
||||
@Override |
||||
public void onShowSlopDistance(boolean value) { |
||||
this.showSlopDistance = value; |
||||
} |
||||
} |
@ -0,0 +1,76 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.IUniversalListItemWithTitleAndSubtitle; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlnetwork.ui.vh.TitleWithSubtitleViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.List; |
||||
|
||||
public class TitleWithSubtitleAdapter<T extends IUniversalListItemWithTitleAndSubtitle<?>> |
||||
extends RecyclerView.Adapter<TitleWithSubtitleViewHolder> { |
||||
|
||||
private final List<T> mValues; |
||||
private final TitleWithSubtitleAdapter.IOnItemClick<T> callback; |
||||
|
||||
public TitleWithSubtitleAdapter(List<T> items, TitleWithSubtitleAdapter.IOnItemClick<T> callback) { |
||||
mValues = items; |
||||
this.callback = callback; |
||||
} |
||||
|
||||
public void updateData(List<T> list) { |
||||
if (mValues != null) { |
||||
mValues.clear(); |
||||
} |
||||
if (list != null) { |
||||
mValues.addAll(list); |
||||
} |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
protected RecyclerView.ViewHolder createVH(@NotNull ViewGroup parent, int viewType) { |
||||
return ViewFactory.generatorViewHolder(parent.getContext(), parent, ViewItemType.titleWithSubtitle); |
||||
} |
||||
|
||||
@Override |
||||
public @NotNull |
||||
TitleWithSubtitleViewHolder onCreateViewHolder(@NotNull ViewGroup parent, int viewType) { |
||||
RecyclerView.ViewHolder viewHolder = createVH(parent, viewType); |
||||
assert viewHolder != null; |
||||
return (TitleWithSubtitleViewHolder) viewHolder; |
||||
} |
||||
|
||||
protected T getItem(int position) { |
||||
return mValues.get(position); |
||||
} |
||||
|
||||
@Override |
||||
public void onBindViewHolder(final TitleWithSubtitleViewHolder holder, int position) { |
||||
T item = getItem(position); |
||||
holder.title.setText(item.getTitle()); |
||||
holder.subTitle.setText(item.getSubtitle()); |
||||
holder.itemView.setOnClickListener(v -> { |
||||
if (callback != null) { |
||||
callback.onItemClick(item); |
||||
} |
||||
}); |
||||
} |
||||
|
||||
@Override |
||||
public int getItemCount() { |
||||
if (mValues == null) { |
||||
return 0; |
||||
} |
||||
return mValues.size(); |
||||
} |
||||
|
||||
public interface IOnItemClick<T extends IUniversalListItemWithTitleAndSubtitle<?>> { |
||||
void onItemClick(T item); |
||||
} |
||||
} |
@ -0,0 +1,136 @@ |
||||
package com.bingce.controlnetwork.adapter; |
||||
|
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
import android.widget.BaseExpandableListAdapter; |
||||
|
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.interfacee.IProjectTolerance; |
||||
import com.bingce.controlapphelper.model.ProjectTolerance; |
||||
import com.bingce.controlapphelper.model.UniversalListItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.ui.vh.GroupParentViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.KeyBoolViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.KeyValueViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.ViewFactory; |
||||
|
||||
import java.util.Arrays; |
||||
import java.util.List; |
||||
|
||||
/* |
||||
* 限差详情adapter |
||||
* */ |
||||
public class ToleranceDetailAdapter extends BaseExpandableListAdapter { |
||||
private IProjectTolerance data; |
||||
private static final List<ViewItemType> childTypes = |
||||
Arrays.asList( |
||||
ViewItemType.nameWithBool, |
||||
ViewItemType.nameWithText); |
||||
|
||||
public ToleranceDetailAdapter(IProjectTolerance limit) { |
||||
data = limit; |
||||
} |
||||
|
||||
public void updateData(IProjectTolerance limit) { |
||||
this.data = limit; |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
@Override |
||||
public int getGroupCount() { |
||||
return data.groupCount(); |
||||
} |
||||
|
||||
@Override |
||||
public int getChildrenCount(int groupPosition) { |
||||
return data.childrenCount(groupPosition); |
||||
} |
||||
|
||||
@Override |
||||
public String getGroup(int groupPosition) { |
||||
return data.groupName(groupPosition); |
||||
} |
||||
|
||||
@Override |
||||
public UniversalListItem<?> getChild(int groupPosition, int childPosition) { |
||||
return data.child(groupPosition, childPosition); |
||||
} |
||||
|
||||
@Override |
||||
public long getGroupId(int groupPosition) { |
||||
return groupPosition; |
||||
} |
||||
|
||||
@Override |
||||
public long getChildId(int groupPosition, int childPosition) { |
||||
return groupPosition * 10L + childPosition; |
||||
} |
||||
|
||||
@Override |
||||
public boolean hasStableIds() { |
||||
return true; |
||||
} |
||||
|
||||
@Override |
||||
public View getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) { |
||||
GroupParentViewHolder viewHolder = null; |
||||
if (convertView == null) { |
||||
convertView = ViewFactory.generatorView(parent.getContext(), parent, ViewItemType.groupParent); |
||||
viewHolder = new GroupParentViewHolder(convertView); |
||||
convertView.setTag(viewHolder); |
||||
} else { |
||||
viewHolder = (GroupParentViewHolder) convertView.getTag(); |
||||
} |
||||
if (viewHolder != null) { |
||||
String groupName = getGroup(groupPosition); |
||||
if (viewHolder.name != null) { |
||||
viewHolder.name.setText(groupName); |
||||
} |
||||
if (viewHolder.expandIcon != null) { |
||||
viewHolder.expandIcon.setImageResource(isExpanded ? R.drawable.ic_arrow_up : R.drawable.ic_arrow_down); |
||||
} |
||||
} |
||||
return convertView; |
||||
} |
||||
|
||||
@Override |
||||
public int getChildTypeCount() { |
||||
return childTypes.size(); |
||||
} |
||||
|
||||
@Override |
||||
public int getChildType(int groupPosition, int childPosition) { |
||||
return childTypes.indexOf(getChild(groupPosition, childPosition).getType()); |
||||
} |
||||
|
||||
@Override |
||||
public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) { |
||||
UniversalListItem<?> item = getChild(groupPosition, childPosition); |
||||
RecyclerView.ViewHolder viewHolder = null; |
||||
if (convertView == null) { |
||||
viewHolder = ViewFactory.generatorViewHolder(parent.getContext(), parent, item.getType()); |
||||
convertView = viewHolder.itemView; |
||||
convertView.setTag(viewHolder); |
||||
} else { |
||||
viewHolder = (RecyclerView.ViewHolder) convertView.getTag(); |
||||
} |
||||
if (viewHolder instanceof KeyValueViewHolder) { |
||||
KeyValueViewHolder kvHolder = (KeyValueViewHolder) viewHolder; |
||||
kvHolder.key.setText(item.getName()); |
||||
kvHolder.value.setText(item.getValue().toString()); |
||||
} else if (viewHolder instanceof KeyBoolViewHolder) { |
||||
KeyBoolViewHolder kvHolder = (KeyBoolViewHolder) viewHolder; |
||||
kvHolder.key.setText(item.getName()); |
||||
kvHolder.checkBox.setChecked((Boolean) item.getValue()); |
||||
} |
||||
return convertView; |
||||
} |
||||
|
||||
@Override |
||||
public boolean isChildSelectable(int groupPosition, int childPosition) { |
||||
return true; |
||||
} |
||||
|
||||
} |
@ -0,0 +1,28 @@ |
||||
package com.bingce.controlnetwork.adapter.contextmenu; |
||||
|
||||
import android.view.MenuItem; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
public abstract class ContextMenuDelete<T> implements IAdapterContextMenu<T> { |
||||
@Override |
||||
public int menuItemSize() { |
||||
return 1; |
||||
} |
||||
|
||||
@Override |
||||
public int menuItemName(int index) { |
||||
return R.string.menu_delete; |
||||
} |
||||
|
||||
@Override |
||||
final public boolean onMenuItemClick(T item, MenuItem menuItem) { |
||||
if (menuItem.getItemId() == 0) { |
||||
delete(item); |
||||
return true; |
||||
} |
||||
return false; |
||||
} |
||||
|
||||
protected abstract void delete(T item); |
||||
} |
@ -0,0 +1,37 @@ |
||||
package com.bingce.controlnetwork.adapter.contextmenu; |
||||
|
||||
import android.view.MenuItem; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
public abstract class ContextMenuDeleteEdit<T> implements IAdapterContextMenu<T> { |
||||
@Override |
||||
final public int menuItemSize() { |
||||
return 2; |
||||
} |
||||
|
||||
@Override |
||||
final public int menuItemName(int index) { |
||||
if (index == 0) { |
||||
return R.string.menu_delete; |
||||
} |
||||
return R.string.menu_edit; |
||||
} |
||||
|
||||
@Override |
||||
final public boolean onMenuItemClick(T item, MenuItem menuItem) { |
||||
if (menuItem.getItemId() == 0) { |
||||
delete(item); |
||||
return true; |
||||
} |
||||
if (menuItem.getItemId() == 1) { |
||||
edit(item); |
||||
return true; |
||||
} |
||||
return false; |
||||
} |
||||
|
||||
protected abstract void delete(T item); |
||||
|
||||
protected abstract void edit(T item); |
||||
} |
@ -0,0 +1,28 @@ |
||||
package com.bingce.controlnetwork.adapter.contextmenu; |
||||
|
||||
import android.view.MenuItem; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
|
||||
public abstract class ContextMenuEdit<T> implements IAdapterContextMenu<T> { |
||||
@Override |
||||
public int menuItemSize() { |
||||
return 1; |
||||
} |
||||
|
||||
@Override |
||||
public int menuItemName(int index) { |
||||
return R.string.menu_edit; |
||||
} |
||||
|
||||
@Override |
||||
final public boolean onMenuItemClick(T item, MenuItem menuItem) { |
||||
if (menuItem.getItemId() == 0) { |
||||
edit(item); |
||||
return true; |
||||
} |
||||
return false; |
||||
} |
||||
|
||||
protected abstract void edit(T item); |
||||
} |
@ -0,0 +1,14 @@ |
||||
package com.bingce.controlnetwork.adapter.contextmenu; |
||||
|
||||
import android.view.MenuItem; |
||||
|
||||
import androidx.annotation.StringRes; |
||||
|
||||
public interface IAdapterContextMenu<T> { |
||||
int menuItemSize(); |
||||
|
||||
@StringRes |
||||
int menuItemName(int index); |
||||
|
||||
boolean onMenuItemClick(T item, MenuItem menuItem); |
||||
} |
@ -0,0 +1,49 @@ |
||||
package com.bingce.controlnetwork.adapter.contextmenu; |
||||
|
||||
import android.content.Context; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.fragment.app.FragmentManager; |
||||
import androidx.lifecycle.LifecycleOwner; |
||||
|
||||
import com.bingce.controlapphelper.ProjectHelper; |
||||
import com.bingce.controlapphelper.datasource.database.project.ProjectRecord; |
||||
import com.bingce.controlapphelper.util.IUIRunner; |
||||
|
||||
import com.bingce.controlnetwork.fragment.projectedit.AbstractProjectEditFragment; |
||||
|
||||
public class ProjectAdapterContextMenu extends ContextMenuDeleteEdit<ProjectRecord> { |
||||
private @NonNull |
||||
final FragmentManager fragmentManager; |
||||
private @NonNull |
||||
final Context context; |
||||
private final @NonNull |
||||
IUIRunner iuiRunner; |
||||
private final @NonNull |
||||
LifecycleOwner lifecycleOwner; |
||||
|
||||
private final ProjectHelper projectHelper; |
||||
|
||||
public ProjectAdapterContextMenu( |
||||
@NonNull Context context, |
||||
@NonNull IUIRunner iuiRunner, |
||||
@NonNull LifecycleOwner lifecycleOwner, |
||||
@NonNull FragmentManager fragmentManager) { |
||||
this.fragmentManager = fragmentManager; |
||||
this.context = context; |
||||
this.iuiRunner = iuiRunner; |
||||
this.lifecycleOwner = lifecycleOwner; |
||||
projectHelper = new ProjectHelper(lifecycleOwner.getLifecycle()); |
||||
} |
||||
|
||||
@Override |
||||
protected void delete(ProjectRecord item) { |
||||
projectHelper.deleteProject(fragmentManager, lifecycleOwner, context, item); |
||||
} |
||||
|
||||
@Override |
||||
protected void edit(ProjectRecord item) { |
||||
AbstractProjectEditFragment.editProject(fragmentManager, context, item.getId(), item.getProjectTypeFault(), |
||||
item.getToleranceId(), item.getProjectName()); |
||||
} |
||||
} |
@ -0,0 +1,84 @@ |
||||
package com.bingce.controlnetwork.adapter.contextmenu; |
||||
|
||||
import android.content.Context; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.fragment.app.FragmentManager; |
||||
import androidx.lifecycle.LifecycleOwner; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.SurveyorDatabaseFactory; |
||||
import com.bingce.controlapphelper.datasource.database.config.ConfigConstants; |
||||
import com.bingce.controlapphelper.datasource.database.config.ConfigRecord; |
||||
import com.bingce.controlapphelper.datasource.database.config.IConfigDataSource; |
||||
import com.bingce.controlapphelper.datasource.database.surveyorcycle.SurveyorPeriodRecord; |
||||
import com.bingce.controlapphelper.util.Tools; |
||||
import com.bingce.controlnetwork.fragment.StringInputFragment; |
||||
import com.bingce.utils.ThreadPoolUtil; |
||||
|
||||
import blankj.utilcode.util.ToastUtils; |
||||
|
||||
import com.bingce.controlnetwork.R; |
||||
import com.bingce.controlnetwork.fragment.StringInputFragment; |
||||
|
||||
public class SurveyorPeriodAdapterContextMenu extends ContextMenuDeleteEdit<SurveyorPeriodRecord> { |
||||
private @NonNull |
||||
final LifecycleOwner lifecycleOwner; |
||||
private @NonNull |
||||
final FragmentManager fragmentManager; |
||||
private final String selectedId; |
||||
private final Context context; |
||||
|
||||
public SurveyorPeriodAdapterContextMenu(Context context, String selectedId, |
||||
@NonNull LifecycleOwner lifecycleOwner, |
||||
@NonNull FragmentManager fragmentManager) { |
||||
this.context = context; |
||||
this.selectedId = selectedId; |
||||
this.lifecycleOwner = lifecycleOwner; |
||||
this.fragmentManager = fragmentManager; |
||||
} |
||||
|
||||
@Override |
||||
protected void delete(SurveyorPeriodRecord item) { |
||||
String id = item.getId(); |
||||
if (selectedId.equals(id)) { |
||||
ToastUtils.showShort(Tools.getString(R.string.current_period_selected_not_delete)); |
||||
} else { |
||||
SurveyorDatabaseFactory |
||||
.instance |
||||
.getSurveyorPeriod() |
||||
.deleteById(id); |
||||
//检测是否需要修改默认测期
|
||||
ThreadPoolUtil.execute(new Runnable() { |
||||
@Override |
||||
public void run() { |
||||
IConfigDataSource configDataSource = |
||||
SurveyorDatabaseFactory |
||||
.instance.getConfigDataSource(); |
||||
ConfigRecord configRecord = configDataSource.getByKeySync(ConfigConstants.KEY_DEFAULT_PERIOD_ID); |
||||
if (configRecord != null && id.equals(configRecord.getConfigValue())) { |
||||
configDataSource.set(ConfigConstants.KEY_DEFAULT_PERIOD_ID, selectedId); |
||||
} |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
protected void edit(SurveyorPeriodRecord item) { |
||||
StringInputFragment |
||||
.input( |
||||
fragmentManager, |
||||
Tools.getString(R.string.modify_period_name), |
||||
item.getName(), |
||||
lifecycleOwner, |
||||
string -> { |
||||
if (string != null && !string.isEmpty()) { |
||||
item.setName(string); |
||||
SurveyorDatabaseFactory |
||||
.instance |
||||
.getSurveyorPeriod() |
||||
.saveRecord(item); |
||||
} |
||||
}); |
||||
} |
||||
} |
@ -0,0 +1,227 @@ |
||||
package com.bingce.controlnetwork.adapter.stationdetail; |
||||
|
||||
import android.text.TextUtils; |
||||
import android.view.View; |
||||
|
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.datasource.database.surveyorstation.model.SurveyorPoint; |
||||
import com.bingce.controlapphelper.model.PickPointResult; |
||||
import com.bingce.controlapphelper.model.StationDetailItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlnetwork.ui.vh.DraggableTextViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.StationGroupItemViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.recyclerview.AbstractDraggableRecycleViewAdapter; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
public abstract class BaseStationDetailAdapter extends AbstractDraggableRecycleViewAdapter<StationDetailItem> { |
||||
private final boolean adjustable; |
||||
private final IOnSelectPointDelegate selectPointCallback; |
||||
|
||||
protected BaseStationDetailAdapter(IOnSelectPointDelegate selectPointCallback, |
||||
List<StationDetailItem> items, |
||||
boolean adjustable) { |
||||
super(items); |
||||
this.adjustable = adjustable; |
||||
this.selectPointCallback = selectPointCallback; |
||||
} |
||||
|
||||
public void setStationPoint(String id, String name) { |
||||
StationDetailItem item = getItem(1); |
||||
if (item != null) { |
||||
if (StationDetailItem.ITEM_TYPE_STATION_ITEM.equals(item.getType())) { |
||||
setItem(1, new StationDetailItem( |
||||
name, StationDetailItem.ITEM_TYPE_STATION_ITEM, id)); |
||||
notifyItemChanged(1); |
||||
} else { |
||||
StationDetailItem newInstance = new StationDetailItem( |
||||
name, StationDetailItem.ITEM_TYPE_STATION_ITEM, id); |
||||
insert(1, newInstance); |
||||
notifyItemInserted(1); |
||||
} |
||||
} |
||||
} |
||||
|
||||
public void setSurveyorPoint(List<String> ids, List<String> names) { |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
for (int index = 0; index < ids.size(); index++) { |
||||
StationDetailItem item = new StationDetailItem( |
||||
names.get(index), StationDetailItem.ITEM_TYPE_POINT_ITEM, ids.get(index)); |
||||
items.add(item); |
||||
} |
||||
if (items == null || items.isEmpty()) { |
||||
return; |
||||
} |
||||
for (int i = getItemCount() - 1; i >= 0; i--) { |
||||
StationDetailItem item = getItem(i); |
||||
if (TextUtils.equals(item.getType(), StationDetailItem.ITEM_TYPE_POINT_ITEM)) { |
||||
remove(item); |
||||
} |
||||
} |
||||
insertAll(items); |
||||
notifyDataSetChanged(); |
||||
} |
||||
|
||||
private StationDetailItem getStationItem() { |
||||
StationDetailItem o = getItem(1); |
||||
if (o != null && StationDetailItem.ITEM_TYPE_STATION_ITEM.equals(o.getType())) { |
||||
return o; |
||||
} |
||||
return null; |
||||
} |
||||
|
||||
@Override |
||||
protected void bindItem(StationDetailItem item, RecyclerView.ViewHolder viewHolder) { |
||||
if (viewHolder instanceof DraggableTextViewHolder) { |
||||
DraggableTextViewHolder draggableTextViewHolder = (DraggableTextViewHolder) viewHolder; |
||||
DraggableTextViewHolder.update(draggableTextViewHolder, item, adjustable); |
||||
} else if (viewHolder instanceof StationGroupItemViewHolder) { |
||||
StationGroupItemViewHolder surveyorStationSetupGroupParentViewHolder = ((StationGroupItemViewHolder) viewHolder); |
||||
StationGroupItemViewHolder.update( |
||||
surveyorStationSetupGroupParentViewHolder, |
||||
item, |
||||
adjustable, |
||||
(itemType, surveyorStationSetupGroupParentViewHolder1) -> { |
||||
if (StationDetailItem.ITEM_TYPE_STATION_GROUP.equals(item.getType())) { |
||||
View.OnClickListener listener = v -> { |
||||
if (selectPointCallback != null) { |
||||
//收集信息
|
||||
PickPointResult pickPointResult = new PickPointResult(); |
||||
StationDetailItem stationItem = getStationItem(); |
||||
if (stationItem != null) { |
||||
pickPointResult.getSelectedIds().add(stationItem.getOriginalPointId()); |
||||
pickPointResult.getSelectedNames().add(stationItem.getName()); |
||||
} |
||||
ArrayList<String> filters = new ArrayList<>(); |
||||
for (int index = 2; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_POINT_ITEM.equals(obj.getType())) { |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
} |
||||
selectPointCallback.onSelectStationPoint(pickPointResult, filters); |
||||
} |
||||
}; |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setOnClickListener(listener); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setOnClickListener(listener); |
||||
StationDetailItem stationItem = getStationItem(); |
||||
if (stationItem != null) { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.INVISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.VISIBLE); |
||||
} else { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.VISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.INVISIBLE); |
||||
} |
||||
} else if (StationDetailItem.ITEM_TYPE_POINT_GROUP.equals(item.getType())) { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setOnClickListener(v -> { |
||||
if (selectPointCallback != null) { |
||||
//收集信息
|
||||
PickPointResult pickPointResult = new PickPointResult(); |
||||
for (int index = 2; index < getItemCount(); index++) { |
||||
StationDetailItem o = getItem(index); |
||||
if (o == null) { |
||||
continue; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_POINT_ITEM.equals(o.getType())) { |
||||
pickPointResult.getSelectedIds().add(o.getOriginalPointId()); |
||||
pickPointResult.getSelectedNames().add(o.getName()); |
||||
} |
||||
} |
||||
String filterId = ""; |
||||
StationDetailItem filter = getStationItem(); |
||||
if (filter != null) { |
||||
filterId = filter.getOriginalPointId(); |
||||
} |
||||
ArrayList<String> filters = new ArrayList<>(); |
||||
if (!filterId.isEmpty()) { |
||||
filters.add(filterId); |
||||
} |
||||
selectPointCallback.onSelectSurveyorPoint(pickPointResult, filters); |
||||
} |
||||
}); |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
|
||||
@Override |
||||
public int getItemViewType(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (item == null) { |
||||
return -1; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_POINT_GROUP.equals(item.getType()) || |
||||
StationDetailItem.ITEM_TYPE_STATION_GROUP.equals(item.getType())) { |
||||
return ViewItemType.surveyorStationCreateStationGroupItem.ordinal(); |
||||
} |
||||
return super.getItemViewType(position); |
||||
} |
||||
|
||||
@Override |
||||
public boolean isItemSwipeAble(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (!adjustable || item == null) { |
||||
return false; |
||||
} |
||||
return !StationDetailItem.ITEM_TYPE_STATION_GROUP.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_POINT_GROUP.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_STATION_ITEM.equals(item.getType()); |
||||
} |
||||
|
||||
@Override |
||||
public boolean isItemDragAble(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (!adjustable || item == null) { |
||||
return false; |
||||
} |
||||
return !StationDetailItem.ITEM_TYPE_STATION_ITEM.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_STATION_GROUP.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_POINT_GROUP.equals(item.getType()); |
||||
} |
||||
|
||||
public List<SurveyorPoint> collectData() { |
||||
List<SurveyorPoint> stationItems = new ArrayList<>(); |
||||
for (int index = 0; index < getItemCount(); index++) { |
||||
StationDetailItem item = getItem(index); |
||||
if (item == null) { |
||||
continue; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_STATION_ITEM.equals(item.getType())) { |
||||
SurveyorPoint stationItem = new SurveyorPoint(); |
||||
stationItem.setOriginalPointId(item.getOriginalPointId()); |
||||
stationItem.setType(SurveyorPoint.TYPE_STATION); |
||||
stationItems.add(stationItem); |
||||
} else if (StationDetailItem.ITEM_TYPE_POINT_ITEM.equals(item.getType())) { |
||||
SurveyorPoint stationItem = new SurveyorPoint(); |
||||
stationItem.setOriginalPointId(item.getOriginalPointId()); |
||||
stationItem.setType(SurveyorPoint.TYPE_POINT); |
||||
stationItems.add(stationItem); |
||||
} |
||||
} |
||||
return stationItems; |
||||
} |
||||
|
||||
public int surveyorPointSize() { |
||||
int size = getItemCount(); |
||||
int count = 0; |
||||
for (int index = 0; index < size; index++) { |
||||
StationDetailItem item = getItem(index); |
||||
if (item == null || !StationDetailItem.ITEM_TYPE_POINT_ITEM.equals(item.getType())) { |
||||
continue; |
||||
} |
||||
count++; |
||||
} |
||||
return count; |
||||
} |
||||
|
||||
public interface IOnSelectPointDelegate { |
||||
void onSelectStationPoint(PickPointResult pickPointResult, ArrayList<String> filters); |
||||
|
||||
void onSelectSurveyorPoint(PickPointResult pickPointResult, ArrayList<String> filters); |
||||
} |
||||
} |
@ -0,0 +1,11 @@ |
||||
package com.bingce.controlnetwork.adapter.stationdetail; |
||||
|
||||
import com.bingce.controlapphelper.model.StationDetailItem; |
||||
|
||||
import java.util.List; |
||||
|
||||
public class EditableStationDetailAdapter extends BaseStationDetailAdapter { |
||||
public EditableStationDetailAdapter(IOnSelectPointDelegate selectPointCallback, List<StationDetailItem> items) { |
||||
super(selectPointCallback, items, true); |
||||
} |
||||
} |
@ -0,0 +1,11 @@ |
||||
package com.bingce.controlnetwork.adapter.stationdetail; |
||||
|
||||
import com.bingce.controlapphelper.model.StationDetailItem; |
||||
|
||||
import java.util.List; |
||||
|
||||
public class NoEditableStationDetailAdapter extends BaseStationDetailAdapter { |
||||
public NoEditableStationDetailAdapter(List<StationDetailItem> items) { |
||||
super(null, items, false); |
||||
} |
||||
} |
@ -0,0 +1,354 @@ |
||||
package com.bingce.controlnetwork.adapter.stationdetail; |
||||
|
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.PickPointResult; |
||||
import com.bingce.controlapphelper.model.StationDetailItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlnetwork.ui.vh.DraggableTextViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.StationGroupItemViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.recyclerview.AbstractDraggableRecycleViewAdapter; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
/** |
||||
* (复合、无定向)导线创建 known1-unknown-known2格式 |
||||
*/ |
||||
public class StationCreateLineKnownUnknownKnownAdapter extends AbstractDraggableRecycleViewAdapter<StationDetailItem> { |
||||
private final IOnSelectPointDelegate selectPointCallback; |
||||
|
||||
public StationCreateLineKnownUnknownKnownAdapter(IOnSelectPointDelegate selectPointCallback, |
||||
List<StationDetailItem> items) { |
||||
super(items); |
||||
this.selectPointCallback = selectPointCallback; |
||||
} |
||||
|
||||
public void setKnownPoints1(List<String> ids, List<String> names) { |
||||
if (ids == null || names == null || ids.size() != names.size()) { |
||||
return; |
||||
} |
||||
//先移除之前known point
|
||||
List<StationDetailItem> knownItems = knownItems1(); |
||||
for (StationDetailItem item : knownItems) { |
||||
remove(item); |
||||
} |
||||
//添加新的known point
|
||||
for (int index = 0; index < ids.size(); index++) { |
||||
insert( |
||||
1 + index, |
||||
new StationDetailItem( |
||||
names.get(index), |
||||
StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM1, |
||||
ids.get(index))); |
||||
} |
||||
//通知变化
|
||||
if (knownItems.size() == ids.size()) { |
||||
notifyItemRangeChanged(1, ids.size()); |
||||
} else { |
||||
notifyItemRangeChanged(1, getItemCount() - 1); |
||||
} |
||||
} |
||||
|
||||
public void setUnknownPoints(List<String> ids, List<String> names) { |
||||
if (ids == null || names == null || ids.size() != names.size()) { |
||||
return; |
||||
} |
||||
//先移除之前unknown point
|
||||
List<StationDetailItem> unknowns = unknownItems(); |
||||
for (StationDetailItem item : unknowns) { |
||||
remove(item); |
||||
} |
||||
//搜索unknown-group索引
|
||||
int targetIndex = -1; |
||||
for (int index = 0; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj != null && StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(obj.getType())) { |
||||
targetIndex = index; |
||||
break; |
||||
} |
||||
} |
||||
if (targetIndex >= 0) { |
||||
//添加新的unknown point
|
||||
for (int index = 0; index < ids.size(); index++) { |
||||
insert( |
||||
targetIndex + 1 + index, |
||||
new StationDetailItem( |
||||
names.get(index), |
||||
StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM, |
||||
ids.get(index))); |
||||
} |
||||
} |
||||
//通知变化
|
||||
if (unknowns.size() == ids.size()) { |
||||
notifyItemRangeChanged(targetIndex + 1, ids.size()); |
||||
} else { |
||||
notifyItemRangeChanged(targetIndex + 1, getItemCount() - 1); |
||||
} |
||||
} |
||||
|
||||
public void setKnownPoints2(List<String> ids, List<String> names) { |
||||
if (ids == null || names == null || ids.size() != names.size()) { |
||||
return; |
||||
} |
||||
//搜索known-group2索引
|
||||
int targetIndex = -1; |
||||
for (int index = 0; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj != null && StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP2.equals(obj.getType())) { |
||||
targetIndex = index; |
||||
break; |
||||
} |
||||
} |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
for (int index = 0; index < ids.size(); index++) { |
||||
StationDetailItem item = new StationDetailItem( |
||||
names.get(index), StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM2, ids.get(index)); |
||||
items.add(item); |
||||
} |
||||
if (targetIndex > 0) { |
||||
replace(targetIndex + 1, items); |
||||
notifyItemRangeChanged(targetIndex + 1, items.size()); |
||||
} |
||||
} |
||||
|
||||
public List<StationDetailItem> knownItems1() { |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
for (int index = 1; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj == null || !StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM1.equals(obj.getType())) { |
||||
break; |
||||
} |
||||
items.add(obj); |
||||
} |
||||
return items; |
||||
} |
||||
|
||||
public List<StationDetailItem> unknownItems() { |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
for (int index = 1; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj == null || !StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM.equals(obj.getType())) { |
||||
continue; |
||||
} |
||||
items.add(obj); |
||||
} |
||||
return items; |
||||
} |
||||
|
||||
public List<StationDetailItem> knownItems2() { |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
int targetIndex = -1; |
||||
for (int index = getItemCount() - 1; index >= 0; index--) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj != null && StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP2.equals(obj.getType())) { |
||||
targetIndex = index; |
||||
break; |
||||
} |
||||
} |
||||
if (targetIndex < 0) { |
||||
return items; |
||||
} |
||||
for (int index = targetIndex + 1; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj == null || !StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM2.equals(obj.getType())) { |
||||
break; |
||||
} |
||||
items.add(obj); |
||||
} |
||||
return items; |
||||
} |
||||
|
||||
@Override |
||||
protected void bindItem(StationDetailItem item, RecyclerView.ViewHolder viewHolder) { |
||||
if (viewHolder instanceof DraggableTextViewHolder) { |
||||
DraggableTextViewHolder draggableTextViewHolder = (DraggableTextViewHolder) viewHolder; |
||||
DraggableTextViewHolder.update(draggableTextViewHolder, item, true); |
||||
} else if (viewHolder instanceof StationGroupItemViewHolder) { |
||||
StationGroupItemViewHolder surveyorStationSetupGroupParentViewHolder = ((StationGroupItemViewHolder) viewHolder); |
||||
StationGroupItemViewHolder.update( |
||||
surveyorStationSetupGroupParentViewHolder, |
||||
item, |
||||
true, |
||||
(itemType, surveyorStationSetupGroupParentViewHolder1) -> { |
||||
if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP1.equals(item.getType())) { |
||||
View.OnClickListener listener = v -> { |
||||
if (selectPointCallback != null) { |
||||
//收集信息
|
||||
PickPointResult pickPointResult = new PickPointResult(); |
||||
for (StationDetailItem obj : knownItems1()) { |
||||
pickPointResult.getSelectedIds().add(obj.getOriginalPointId()); |
||||
pickPointResult.getSelectedNames().add(obj.getName()); |
||||
} |
||||
ArrayList<String> filters = new ArrayList<>(); |
||||
for (StationDetailItem obj : unknownItems()) { |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
for (StationDetailItem obj : knownItems2()) { |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
selectPointCallback.onSelectKnownPoint1(pickPointResult, filters); |
||||
} |
||||
}; |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setOnClickListener(listener); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setOnClickListener(listener); |
||||
|
||||
List<StationDetailItem> knownItems = knownItems1(); |
||||
if (knownItems.isEmpty()) { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.VISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.INVISIBLE); |
||||
} else { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.INVISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.VISIBLE); |
||||
} |
||||
} else if (StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType())) { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setOnClickListener(v -> { |
||||
if (selectPointCallback != null) { |
||||
//收集信息
|
||||
PickPointResult pickPointResult = new PickPointResult(); |
||||
for (int index = 2; index < getItemCount(); index++) { |
||||
StationDetailItem o = getItem(index); |
||||
if (o == null) { |
||||
continue; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM.equals(o.getType())) { |
||||
pickPointResult.getSelectedIds().add(o.getOriginalPointId()); |
||||
pickPointResult.getSelectedNames().add(o.getName()); |
||||
} |
||||
} |
||||
ArrayList<String> filters = new ArrayList<>(); |
||||
for (StationDetailItem obj : knownItems1()) { |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
for (StationDetailItem obj : knownItems2()) { |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
selectPointCallback.onSelectUnknownPoint(pickPointResult, filters); |
||||
} |
||||
}); |
||||
} else if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP2.equals(item.getType())) { |
||||
View.OnClickListener listener = v -> { |
||||
if (selectPointCallback != null) { |
||||
//收集信息
|
||||
PickPointResult pickPointResult = new PickPointResult(); |
||||
for (StationDetailItem obj : knownItems2()) { |
||||
pickPointResult.getSelectedIds().add(obj.getOriginalPointId()); |
||||
pickPointResult.getSelectedNames().add(obj.getName()); |
||||
} |
||||
ArrayList<String> filters = new ArrayList<>(); |
||||
for (StationDetailItem obj : knownItems1()) { |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
for (StationDetailItem obj : unknownItems()) { |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
selectPointCallback.onSelectKnownPoint2(pickPointResult, filters); |
||||
} |
||||
}; |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setOnClickListener(listener); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setOnClickListener(listener); |
||||
|
||||
List<StationDetailItem> knownItems = knownItems2(); |
||||
if (knownItems.isEmpty()) { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.VISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.INVISIBLE); |
||||
} else { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.INVISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.VISIBLE); |
||||
} |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
|
||||
private static final int ITEM_TYPE_KNOWN_POINT1 = 11; |
||||
private static final int ITEM_TYPE_UNKNOWN_POINT = ITEM_TYPE_KNOWN_POINT1 + 1; |
||||
private static final int ITEM_TYPE_KNOWN_POINT2 = ITEM_TYPE_UNKNOWN_POINT + 1; |
||||
|
||||
@Override |
||||
public int getItemViewType(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (item == null) { |
||||
return -1; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP1.equals(item.getType()) || |
||||
StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType()) || |
||||
StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP2.equals(item.getType())) { |
||||
return ViewItemType.surveyorStationCreateStationGroupItem.ordinal(); |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM1.equals(item.getType())) { |
||||
return ITEM_TYPE_KNOWN_POINT1; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM.equals(item.getType())) { |
||||
return ITEM_TYPE_UNKNOWN_POINT; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM2.equals(item.getType())) { |
||||
return ITEM_TYPE_KNOWN_POINT2; |
||||
} |
||||
return super.getItemViewType(position); |
||||
} |
||||
|
||||
@NonNull |
||||
@NotNull |
||||
@Override |
||||
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull @NotNull ViewGroup parent, int viewType) { |
||||
if (ITEM_TYPE_KNOWN_POINT1 == viewType || ITEM_TYPE_UNKNOWN_POINT == viewType || ITEM_TYPE_KNOWN_POINT2 == viewType) { |
||||
return super.onCreateViewHolder(parent, ViewItemType.draggableItem.ordinal()); |
||||
} |
||||
return super.onCreateViewHolder(parent, viewType); |
||||
} |
||||
|
||||
@Override |
||||
public boolean isItemSwipeAble(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (item == null) { |
||||
return false; |
||||
} |
||||
return !StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP1.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP2.equals(item.getType()); |
||||
} |
||||
|
||||
@Override |
||||
public boolean isItemDragAble(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (item == null) { |
||||
return false; |
||||
} |
||||
return !StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP1.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP2.equals(item.getType()); |
||||
} |
||||
|
||||
public interface IOnSelectPointDelegate { |
||||
void onSelectKnownPoint1(PickPointResult pickPointResult, ArrayList<String> filters); |
||||
|
||||
void onSelectUnknownPoint(PickPointResult pickPointResult, ArrayList<String> filters); |
||||
|
||||
void onSelectKnownPoint2(PickPointResult pickPointResult, ArrayList<String> filters); |
||||
} |
||||
} |
@ -0,0 +1,238 @@ |
||||
package com.bingce.controlnetwork.adapter.stationdetail; |
||||
|
||||
import android.view.View; |
||||
import android.view.ViewGroup; |
||||
|
||||
import androidx.annotation.NonNull; |
||||
import androidx.recyclerview.widget.RecyclerView; |
||||
|
||||
import com.bingce.controlapphelper.model.PickPointResult; |
||||
import com.bingce.controlapphelper.model.StationDetailItem; |
||||
import com.bingce.controlapphelper.model.ViewItemType; |
||||
import com.bingce.controlnetwork.ui.vh.DraggableTextViewHolder; |
||||
import com.bingce.controlnetwork.ui.vh.StationGroupItemViewHolder; |
||||
import com.bingce.controlnetwork.ui.widget.recyclerview.AbstractDraggableRecycleViewAdapter; |
||||
|
||||
import org.jetbrains.annotations.NotNull; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
/** |
||||
* 支导线创建 |
||||
*/ |
||||
public class StationCreateLineSingleAdapter extends AbstractDraggableRecycleViewAdapter<StationDetailItem> { |
||||
private final IOnSelectPointDelegate selectPointCallback; |
||||
|
||||
public StationCreateLineSingleAdapter(IOnSelectPointDelegate selectPointCallback, |
||||
List<StationDetailItem> items) { |
||||
super(items); |
||||
this.selectPointCallback = selectPointCallback; |
||||
} |
||||
|
||||
public void setKnownPoints(List<String> ids, List<String> names) { |
||||
if (ids == null || names == null || ids.size() != names.size()) { |
||||
return; |
||||
} |
||||
//先移除之前known point
|
||||
List<StationDetailItem> knownItems = knownItems(); |
||||
for (StationDetailItem item : knownItems) { |
||||
remove(item); |
||||
} |
||||
//添加新的known point
|
||||
for (int index = 0; index < ids.size(); index++) { |
||||
insert( |
||||
1 + index, |
||||
new StationDetailItem( |
||||
names.get(index), |
||||
StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM, |
||||
ids.get(index))); |
||||
} |
||||
//通知变化
|
||||
if (knownItems.size() == ids.size()) { |
||||
notifyItemRangeChanged(1, ids.size()); |
||||
} else { |
||||
notifyItemRangeChanged(1, getItemCount() - 1); |
||||
} |
||||
} |
||||
|
||||
public void setUnknownPoints(List<String> ids, List<String> names) { |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
for (int index = 0; index < ids.size(); index++) { |
||||
StationDetailItem item = new StationDetailItem( |
||||
names.get(index), StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM, ids.get(index)); |
||||
items.add(item); |
||||
} |
||||
|
||||
int index = -1; |
||||
for (int i = 0; i < getItemCount(); i++) { |
||||
StationDetailItem item = getItem(i); |
||||
if (item == null || !StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType())) { |
||||
continue; |
||||
} |
||||
index = i; |
||||
break; |
||||
} |
||||
if (index > 0) { |
||||
replace(index + 1, items); |
||||
notifyItemRangeChanged(index + 1, items.size()); |
||||
} |
||||
} |
||||
|
||||
public List<StationDetailItem> knownItems() { |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
for (int index = 1; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj == null || !StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM.equals(obj.getType())) { |
||||
break; |
||||
} |
||||
items.add(obj); |
||||
} |
||||
return items; |
||||
} |
||||
|
||||
public List<StationDetailItem> unknownItems() { |
||||
List<StationDetailItem> items = new ArrayList<>(); |
||||
for (int index = 1; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj == null || !StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM.equals(obj.getType())) { |
||||
continue; |
||||
} |
||||
items.add(obj); |
||||
} |
||||
return items; |
||||
} |
||||
|
||||
@Override |
||||
protected void bindItem(StationDetailItem item, RecyclerView.ViewHolder viewHolder) { |
||||
if (viewHolder instanceof DraggableTextViewHolder) { |
||||
DraggableTextViewHolder draggableTextViewHolder = (DraggableTextViewHolder) viewHolder; |
||||
DraggableTextViewHolder.update(draggableTextViewHolder, item, true); |
||||
} else if (viewHolder instanceof StationGroupItemViewHolder) { |
||||
StationGroupItemViewHolder surveyorStationSetupGroupParentViewHolder = ((StationGroupItemViewHolder) viewHolder); |
||||
StationGroupItemViewHolder.update( |
||||
surveyorStationSetupGroupParentViewHolder, |
||||
item, |
||||
true, |
||||
(itemType, surveyorStationSetupGroupParentViewHolder1) -> { |
||||
if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP.equals(item.getType())) { |
||||
View.OnClickListener listener = v -> { |
||||
if (selectPointCallback != null) { |
||||
//收集信息
|
||||
PickPointResult pickPointResult = new PickPointResult(); |
||||
for (StationDetailItem obj : knownItems()) { |
||||
pickPointResult.getSelectedIds().add(obj.getOriginalPointId()); |
||||
pickPointResult.getSelectedNames().add(obj.getName()); |
||||
} |
||||
ArrayList<String> filters = new ArrayList<>(); |
||||
for (int index = 2; index < getItemCount(); index++) { |
||||
StationDetailItem obj = getItem(index); |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM.equals(obj.getType())) { |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
} |
||||
selectPointCallback.onSelectKnownPoint(pickPointResult, filters); |
||||
} |
||||
}; |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setOnClickListener(listener); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setOnClickListener(listener); |
||||
|
||||
List<StationDetailItem> knownItems = knownItems(); |
||||
if (knownItems.isEmpty()) { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.VISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.INVISIBLE); |
||||
} else { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setVisibility(View.INVISIBLE); |
||||
surveyorStationSetupGroupParentViewHolder1.switchView.setVisibility(View.VISIBLE); |
||||
} |
||||
} else if (StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType())) { |
||||
surveyorStationSetupGroupParentViewHolder1.pick.setOnClickListener(v -> { |
||||
if (selectPointCallback != null) { |
||||
//收集信息
|
||||
PickPointResult pickPointResult = new PickPointResult(); |
||||
for (int index = 2; index < getItemCount(); index++) { |
||||
StationDetailItem o = getItem(index); |
||||
if (o == null) { |
||||
continue; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM.equals(o.getType())) { |
||||
pickPointResult.getSelectedIds().add(o.getOriginalPointId()); |
||||
pickPointResult.getSelectedNames().add(o.getName()); |
||||
} |
||||
} |
||||
ArrayList<String> filters = new ArrayList<>(); |
||||
for (StationDetailItem obj : knownItems()) { |
||||
if (obj == null) { |
||||
continue; |
||||
} |
||||
filters.add(obj.getOriginalPointId()); |
||||
} |
||||
selectPointCallback.onSelectUnknownPoint(pickPointResult, filters); |
||||
} |
||||
}); |
||||
} |
||||
}); |
||||
} |
||||
} |
||||
|
||||
private static final int ITEM_TYPE_KNOWN_POINT = 11; |
||||
private static final int ITEM_TYPE_UNKNOWN_POINT = ITEM_TYPE_KNOWN_POINT + 1; |
||||
|
||||
@Override |
||||
public int getItemViewType(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (item == null) { |
||||
return -1; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP.equals(item.getType()) || |
||||
StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType())) { |
||||
return ViewItemType.surveyorStationCreateStationGroupItem.ordinal(); |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_KNOWN_POINT_ITEM.equals(item.getType())) { |
||||
return ITEM_TYPE_KNOWN_POINT; |
||||
} |
||||
if (StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_ITEM.equals(item.getType())) { |
||||
return ITEM_TYPE_UNKNOWN_POINT; |
||||
} |
||||
return super.getItemViewType(position); |
||||
} |
||||
|
||||
@NonNull |
||||
@NotNull |
||||
@Override |
||||
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull @NotNull ViewGroup parent, int viewType) { |
||||
if (ITEM_TYPE_KNOWN_POINT == viewType || ITEM_TYPE_UNKNOWN_POINT == viewType) { |
||||
return super.onCreateViewHolder(parent, ViewItemType.draggableItem.ordinal()); |
||||
} |
||||
return super.onCreateViewHolder(parent, viewType); |
||||
} |
||||
|
||||
@Override |
||||
public boolean isItemSwipeAble(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (item == null) { |
||||
return false; |
||||
} |
||||
return !StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType()); |
||||
} |
||||
|
||||
@Override |
||||
public boolean isItemDragAble(int position) { |
||||
StationDetailItem item = getItem(position); |
||||
if (item == null) { |
||||
return false; |
||||
} |
||||
return !StationDetailItem.ITEM_TYPE_KNOWN_POINT_GROUP.equals(item.getType()) && |
||||
!StationDetailItem.ITEM_TYPE_UN_KNOWN_POINT_GROUP.equals(item.getType()); |
||||
} |
||||
|
||||
public interface IOnSelectPointDelegate { |
||||
void onSelectKnownPoint(PickPointResult pickPointResult, ArrayList<String> filters); |
||||
|
||||
void onSelectUnknownPoint(PickPointResult pickPointResult, ArrayList<String> filters); |
||||
} |
||||
} |
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in new issue