From c0afc9f5291839a63a67d0e685aa58d0adf2c8a9 Mon Sep 17 00:00:00 2001 From: pppscn <35696959@qq.com> Date: Sun, 11 Feb 2024 11:19:33 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E5=A4=8D=EF=BC=9A=E6=89=8B=E6=9C=BAGP?= =?UTF-8?q?S=E7=A6=81=E7=94=A8=E6=97=B6=EF=BC=8C=E5=90=AF=E7=94=A8?= =?UTF-8?q?=E5=A2=9E=E5=BC=BA=E5=8A=9F=E8=83=BD`GPS=E5=AE=9A=E4=BD=8D?= =?UTF-8?q?=E6=9C=8D=E5=8A=A1`=E5=AF=BC=E8=87=B4SmsF=E5=90=AF=E5=8A=A8?= =?UTF-8?q?=E5=A5=94=E6=BA=83?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../forwarder/fragment/SettingsFragment.kt | 60 ++++----- .../sms/forwarder/service/LocationService.kt | 123 ++++++++++-------- app/src/main/res/layout/fragment_settings.xml | 117 ++++++++++------- app/src/main/res/values-en/strings.xml | 4 +- app/src/main/res/values-zh-rCN/strings.xml | 4 +- app/src/main/res/values-zh-rTW/strings.xml | 4 +- app/src/main/res/values/strings.xml | 4 +- 7 files changed, 175 insertions(+), 141 deletions(-) diff --git a/app/src/main/java/com/idormy/sms/forwarder/fragment/SettingsFragment.kt b/app/src/main/java/com/idormy/sms/forwarder/fragment/SettingsFragment.kt index b6f8fb3684..c99c326667 100644 --- a/app/src/main/java/com/idormy/sms/forwarder/fragment/SettingsFragment.kt +++ b/app/src/main/java/com/idormy/sms/forwarder/fragment/SettingsFragment.kt @@ -7,6 +7,7 @@ import android.content.Context import android.content.Intent import android.content.pm.PackageManager import android.location.Criteria +import android.location.LocationManager import android.net.Uri import android.os.Build import android.os.Environment @@ -112,7 +113,7 @@ class SettingsFragment : BaseFragment(), View.OnClickL switchEnableAppNotify(binding!!.sbEnableAppNotify, binding!!.scbCancelAppNotify, binding!!.scbNotUserPresent) //启用GPS定位功能 - switchEnableLocation(binding!!.sbEnableLocation, binding!!.layoutLocationSetting, binding!!.rgAccuracy, binding!!.rgPowerRequirement, binding!!.etMinInterval, binding!!.etMinDistance) + switchEnableLocation(binding!!.sbEnableLocation, binding!!.layoutLocationSetting, binding!!.rgAccuracy, binding!!.rgPowerRequirement, binding!!.xsbMinInterval, binding!!.xsbMinDistance) //短信指令 switchEnableSmsCommand(binding!!.sbEnableSmsCommand, binding!!.etSafePhone) //启动时异步获取已安装App信息 @@ -513,7 +514,7 @@ class SettingsFragment : BaseFragment(), View.OnClickL } //启用定位功能 - private fun switchEnableLocation(@SuppressLint("UseSwitchCompatOrMaterialCode") sbEnableLocation: SwitchButton, layoutLocationSetting: LinearLayout, rgAccuracy: RadioGroup, rgPowerRequirement: RadioGroup, etMinInterval: EditText, etMinDistance: EditText) { + private fun switchEnableLocation(@SuppressLint("UseSwitchCompatOrMaterialCode") sbEnableLocation: SwitchButton, layoutLocationSetting: LinearLayout, rgAccuracy: RadioGroup, rgPowerRequirement: RadioGroup, xsbMinInterval: XSeekBar, xsbMinDistance: XSeekBar) { //是否启用定位功能 sbEnableLocation.isChecked = SettingUtils.enableLocation layoutLocationSetting.visibility = if (SettingUtils.enableLocation) View.VISIBLE else View.GONE @@ -560,7 +561,7 @@ class SettingsFragment : BaseFragment(), View.OnClickL R.id.rb_accuracy_no_requirement -> Criteria.NO_REQUIREMENT else -> Criteria.ACCURACY_FINE } - restartLocationService("rgAccuracy") + restartLocationService() } //设置电量消耗:低电耗(默认) @@ -581,49 +582,38 @@ class SettingsFragment : BaseFragment(), View.OnClickL R.id.rb_power_requirement_no_requirement -> Criteria.NO_REQUIREMENT else -> Criteria.POWER_LOW } - restartLocationService("rgPowerRequirement") + restartLocationService() } //设置位置更新最小时间间隔(单位:毫秒); 默认间隔:10000毫秒,最小间隔:1000毫秒 - etMinInterval.setText((SettingUtils.locationMinInterval / 1000).toString()) - etMinInterval.addTextChangedListener(object : TextWatcher { - override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {} - override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) {} - override fun afterTextChanged(s: Editable) { - val changedText = s.toString() - if (changedText.isEmpty() || changedText == "0") { - etMinInterval.setText("1") - etMinInterval.setSelection(etMinInterval.text.length) // 将光标移至文本末尾 - return - } - SettingUtils.locationMinInterval = changedText.toLong() * 1000 - restartLocationService() - } - }) + xsbMinInterval.setDefaultValue((SettingUtils.locationMinInterval / 1000).toInt()) + xsbMinInterval.setOnSeekBarListener { _: XSeekBar?, newValue: Int -> + SettingUtils.locationMinInterval = newValue * 1000L + restartLocationService() + } //设置位置更新最小距离(单位:米);默认距离:0米 - etMinDistance.setText(SettingUtils.locationMinDistance.toString()) - etMinDistance.addTextChangedListener(object : TextWatcher { - override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {} - override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) {} - override fun afterTextChanged(s: Editable) { - val changedText = s.toString() - if (changedText.isEmpty()) { - etMinDistance.setText("0") - etMinDistance.setSelection(etMinInterval.text.length) // 将光标移至文本末尾 - return - } - SettingUtils.locationMinDistance = changedText.toInt() - restartLocationService() - } - }) + xsbMinDistance.setDefaultValue(SettingUtils.locationMinDistance) + xsbMinDistance.setOnSeekBarListener { _: XSeekBar?, newValue: Int -> + SettingUtils.locationMinDistance = newValue + restartLocationService() + } } //重启定位服务 private fun restartLocationService(action: String = "RESTART") { Log.d(TAG, "restartLocationService, action: $action") val serviceIntent = Intent(requireContext(), LocationService::class.java) - serviceIntent.action = action + val locationManager = App.context.getSystemService(Context.LOCATION_SERVICE) as LocationManager? + val isGpsEnabled = locationManager?.isProviderEnabled(LocationManager.GPS_PROVIDER) == true + if (!isGpsEnabled && SettingUtils.enableLocation) { + XToastUtils.error(getString(R.string.toast_gps_not_enabled)) + SettingUtils.enableLocation = false + binding!!.sbEnableLocation.isChecked = false + serviceIntent.action = "STOP" + } else { + serviceIntent.action = action + } requireContext().startService(serviceIntent) } diff --git a/app/src/main/java/com/idormy/sms/forwarder/service/LocationService.kt b/app/src/main/java/com/idormy/sms/forwarder/service/LocationService.kt index e3e7ccf3d5..6e6b6d2e9b 100644 --- a/app/src/main/java/com/idormy/sms/forwarder/service/LocationService.kt +++ b/app/src/main/java/com/idormy/sms/forwarder/service/LocationService.kt @@ -2,8 +2,12 @@ package com.idormy.sms.forwarder.service import android.annotation.SuppressLint import android.app.Service +import android.content.BroadcastReceiver +import android.content.Context import android.content.Intent +import android.content.IntentFilter import android.location.Location +import android.location.LocationManager import android.os.IBinder import androidx.work.OneTimeWorkRequestBuilder import androidx.work.WorkManager @@ -23,14 +27,20 @@ import com.king.location.LocationErrorCode import com.king.location.OnExceptionListener import com.king.location.OnLocationListener import com.xuexiang.xaop.util.PermissionUtils -import com.yanzhenjie.andserver.Server import java.util.Date @SuppressLint("SimpleDateFormat") @Suppress("PrivatePropertyName", "DEPRECATION") -class LocationService : Service(), Server.ServerListener { +class LocationService : Service() { private val TAG: String = LocationService::class.java.simpleName + private val gpsStatusReceiver = object : BroadcastReceiver() { + override fun onReceive(context: Context?, intent: Intent?) { + if (intent?.action == LocationManager.PROVIDERS_CHANGED_ACTION) { + handleGpsStatusChanged() + } + } + } companion object { var isRunning = false @@ -45,13 +55,16 @@ class LocationService : Service(), Server.ServerListener { super.onCreate() if (!SettingUtils.enableLocation) return + + //注册广播接收器 + registerReceiver(gpsStatusReceiver, IntentFilter(LocationManager.PROVIDERS_CHANGED_ACTION)) startService() } override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int { super.onStartCommand(intent, flags, startId) - if (!SettingUtils.enableLocation || intent == null) return START_NOT_STICKY + if (intent == null) return START_NOT_STICKY Log.i(TAG, "onStartCommand: ${intent.action}") @@ -60,11 +73,10 @@ class LocationService : Service(), Server.ServerListener { } else if (intent.action == "STOP" && isRunning) { stopService() } else if (intent.action == "RESTART") { - stopService() - startService() + restartLocation() } - return START_NOT_STICKY + return START_STICKY } override fun onDestroy() { @@ -73,18 +85,8 @@ class LocationService : Service(), Server.ServerListener { if (!SettingUtils.enableLocation) return stopService() - } - - override fun onException(e: Exception?) { - Log.i(TAG, "onException: ") - } - - override fun onStarted() { - Log.i(TAG, "onStarted: ") - } - - override fun onStopped() { - Log.i(TAG, "onStopped: ") + //在 Service 销毁时记得注销广播接收器 + unregisterReceiver(gpsStatusReceiver) } private fun startService() { @@ -94,16 +96,6 @@ class LocationService : Service(), Server.ServerListener { TaskUtils.locationInfoOld = LocationInfo() if (SettingUtils.enableLocation && PermissionUtils.isGranted(android.Manifest.permission.ACCESS_COARSE_LOCATION, android.Manifest.permission.ACCESS_FINE_LOCATION)) { - //可根据具体需求设置定位配置参数(这里只列出一些主要的参数) - val locationOption = App.LocationClient.getLocationOption().setAccuracy(SettingUtils.locationAccuracy)//设置位置精度:高精度 - .setPowerRequirement(SettingUtils.locationPowerRequirement) //设置电量消耗:低电耗 - .setMinTime(SettingUtils.locationMinInterval)//设置位置更新最小时间间隔(单位:毫秒); 默认间隔:10000毫秒,最小间隔:1000毫秒 - .setMinDistance(SettingUtils.locationMinDistance)//设置位置更新最小距离(单位:米);默认距离:0米 - .setOnceLocation(false)//设置是否只定位一次,默认为 false,当设置为 true 时,则只定位一次后,会自动停止定位 - .setLastKnownLocation(false)//设置是否获取最后一次缓存的已知位置,默认为 true - //设置定位配置参数 - App.LocationClient.setLocationOption(locationOption) - App.LocationClient.startLocation() //设置定位监听 App.LocationClient.setOnLocationListener(object : OnLocationListener() { @@ -125,7 +117,7 @@ class LocationService : Service(), Server.ServerListener { HttpServerUtils.apiLocationCache = locationInfoNew TaskUtils.locationInfoNew = locationInfoNew - //TODO: 触发自动任务 + //触发自动任务 val locationInfoOld = TaskUtils.locationInfoOld if (locationInfoOld.longitude != locationInfoNew.longitude || locationInfoOld.latitude != locationInfoNew.latitude || locationInfoOld.address != locationInfoNew.address) { Log.d(TAG, "locationInfoOld = $locationInfoOld") @@ -139,34 +131,18 @@ class LocationService : Service(), Server.ServerListener { TaskUtils.locationInfoOld = locationInfoNew } } - - override fun onProviderEnabled(provider: String) { - super.onProviderEnabled(provider) - Log.d(TAG, "onProviderEnabled(provider = ${provider})") - } - - override fun onProviderDisabled(provider: String) { - super.onProviderDisabled(provider) - Log.d(TAG, "onProviderDisabled(provider = ${provider})") - } - }) //设置异常监听 App.LocationClient.setOnExceptionListener(object : OnExceptionListener { override fun onException(@LocationErrorCode errorCode: Int, e: Exception) { - //定位出现异常 + //定位出现异常 && 尝试重启定位 Log.w(TAG, "onException(errorCode = ${errorCode}, e = ${e})") - - //TODO: 重启定位 - App.LocationClient.startLocation() + restartLocation() } }) - if (App.LocationClient.isStarted()) {//如果已经开始定位,则先停止定位 - App.LocationClient.stopLocation() - } - App.LocationClient.startLocation() + restartLocation() isRunning = true } else if (!SettingUtils.enableLocation && App.LocationClient.isStarted()) { Log.d(TAG, "stopLocation") @@ -200,20 +176,59 @@ class LocationService : Service(), Server.ServerListener { } } + private fun restartLocation() { + //如果已经开始定位,则先停止定位 + if (App.LocationClient.isStarted()) { + App.LocationClient.stopLocation() + } + if (isGpsEnabled()) { + //可根据具体需求设置定位配置参数(这里只列出一些主要的参数) + val locationOption = App.LocationClient.getLocationOption().setAccuracy(SettingUtils.locationAccuracy)//设置位置精度:高精度 + .setPowerRequirement(SettingUtils.locationPowerRequirement) //设置电量消耗:低电耗 + .setMinTime(SettingUtils.locationMinInterval)//设置位置更新最小时间间隔(单位:毫秒); 默认间隔:10000毫秒,最小间隔:1000毫秒 + .setMinDistance(SettingUtils.locationMinDistance)//设置位置更新最小距离(单位:米);默认距离:0米 + .setOnceLocation(false)//设置是否只定位一次,默认为 false,当设置为 true 时,则只定位一次后,会自动停止定位 + .setLastKnownLocation(false)//设置是否获取最后一次缓存的已知位置,默认为 true + //设置定位配置参数 + App.LocationClient.setLocationOption(locationOption) + App.LocationClient.startLocation() + } else { + Log.w(TAG, "onException: GPS未开启") + } + } + private fun enqueueLocationWorkerRequest( - conditionType: Int, - locationJsonOld: String, - locationJsonNew: String + conditionType: Int, locationJsonOld: String, locationJsonNew: String ) { val locationWorkerRequest = OneTimeWorkRequestBuilder().setInputData( workDataOf( - TaskWorker.conditionType to conditionType, - "locationJsonOld" to locationJsonOld, - "locationJsonNew" to locationJsonNew + TaskWorker.conditionType to conditionType, "locationJsonOld" to locationJsonOld, "locationJsonNew" to locationJsonNew ) ).build() WorkManager.getInstance(applicationContext).enqueue(locationWorkerRequest) } + private fun handleGpsStatusChanged() { + val isGpsEnabled = isGpsEnabled() + //处理 GPS 状态变化 + if (isGpsEnabled) { + //GPS 已启用 + Log.d(TAG, "handleGpsStatusChanged: GPS 已启用") + if (SettingUtils.enableLocation && !App.LocationClient.isStarted()) { + App.LocationClient.startLocation() + } + } else { + //GPS 已停用 + Log.d(TAG, "handleGpsStatusChanged: GPS 已停用") + if (SettingUtils.enableLocation && App.LocationClient.isStarted()) { + App.LocationClient.stopLocation() + } + } + } + + private fun isGpsEnabled(): Boolean { + val locationManager = getSystemService(Context.LOCATION_SERVICE) as LocationManager? + return locationManager?.isProviderEnabled(LocationManager.GPS_PROVIDER) == true + } } \ No newline at end of file diff --git a/app/src/main/res/layout/fragment_settings.xml b/app/src/main/res/layout/fragment_settings.xml index 6e9afc462d..843713b334 100644 --- a/app/src/main/res/layout/fragment_settings.xml +++ b/app/src/main/res/layout/fragment_settings.xml @@ -502,65 +502,86 @@ - + android:orientation="vertical"> - + - + - + - + + + + + + + + + + + + + + + diff --git a/app/src/main/res/values-en/strings.xml b/app/src/main/res/values-en/strings.xml index a177938f1e..bea3b4a7e2 100644 --- a/app/src/main/res/values-en/strings.xml +++ b/app/src/main/res/values-en/strings.xml @@ -1129,7 +1129,8 @@ Low Medium High - To Update: Min Interval + Location Update + Min Interval Min Distance m UID @@ -1339,4 +1340,5 @@ Union ID Chat ID Receive ID + GPS is not enabled, please enable GPS first! diff --git a/app/src/main/res/values-zh-rCN/strings.xml b/app/src/main/res/values-zh-rCN/strings.xml index 3c83aa258a..a30b1d3c04 100644 --- a/app/src/main/res/values-zh-rCN/strings.xml +++ b/app/src/main/res/values-zh-rCN/strings.xml @@ -1130,7 +1130,8 @@ - 位置更新:最小时间间隔 + 位置更新 + 最小时间间隔 最小距离间隔 UID @@ -1340,4 +1341,5 @@ Union ID Chat ID 消息接收者ID + GPS未开启,请先开启GPS! diff --git a/app/src/main/res/values-zh-rTW/strings.xml b/app/src/main/res/values-zh-rTW/strings.xml index f723800213..4cb89f4555 100644 --- a/app/src/main/res/values-zh-rTW/strings.xml +++ b/app/src/main/res/values-zh-rTW/strings.xml @@ -1130,7 +1130,8 @@ - 位置更新:最小時間間隔 + 位置更新 + 最小時間間隔 最小距離間隔 UID @@ -1341,4 +1342,5 @@ Union ID Chat ID 訊息接收者ID + GPS未開啟,請先開啟GPS! diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 9ed2c8d9b1..9cc45a4479 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1130,7 +1130,8 @@ - 位置更新:最小时间间隔 + 位置更新 + 最小时间间隔 最小距离间隔 UID @@ -1340,4 +1341,5 @@ Union ID Chat ID 消息接收者ID + GPS未开启,请先开启GPS!