如何为 gps 使用特定对话框?
How can I use a specific dialog for gps?
当我尝试在不进入 phone 设置的情况下打开 gps 时,出现此对话框:
如何显示包含此类描述的对话框?
这是我的代码示例:
viewModel.onEnableGpsEvent.observe(this, Observer { event ->
event.getContentIfNotHandled()?.let {
activity?.let {
val locationRequest = LocationRequest.create()
locationRequest.priority = LocationRequest.PRIORITY_HIGH_ACCURACY
val builder = LocationSettingsRequest.Builder().addLocationRequest(locationRequest)
val task = LocationServices.getSettingsClient(it).checkLocationSettings(builder.build())
task.addOnSuccessListener { response ->
val states = response.locationSettingsStates
if (states.isLocationPresent) {
//TODO: Do something if need it
}
}
task.addOnFailureListener { e ->
if (e is ResolvableApiException) {
try {
// Handle result in onActivityResult()
e.startResolutionForResult(
it,
LOCATION_SETTING_REQUEST
)
} catch (sendEx: IntentSender.SendIntentException) {
}
}
}
}
我还有下一个依赖:
implementation 'com.google.android.gms:play-services-location:18.0.0'
使用下一个解决方案解决了这个问题:
override fun enableGps(activity: FragmentActivity) {
if (googleApiClient == null) {
googleApiClient = GoogleApiClient.Builder(context)
.addApi(LocationServices.API)
.addConnectionCallbacks(object : GoogleApiClient.ConnectionCallbacks {
override fun onConnected(bundle: Bundle?) {}
override fun onConnectionSuspended(i: Int) {
googleApiClient?.connect()
}
})
.addOnConnectionFailedListener { connectionResult ->
Timber.e("${connectionResult.errorCode}")
}.build()
googleApiClient?.connect()
}
val locationRequest = LocationRequest.create()
locationRequest.priority = LocationRequest.PRIORITY_HIGH_ACCURACY
locationRequest.interval = 10000
locationRequest.fastestInterval = 5000
val builder = LocationSettingsRequest.Builder().addLocationRequest(locationRequest)
builder.setAlwaysShow(true)
val result: PendingResult<LocationSettingsResult> = LocationServices.SettingsApi.checkLocationSettings(googleApiClient, builder.build())
result.setResultCallback { result ->
val status: Status = result.status
when (status.statusCode) {
LocationSettingsStatusCodes.RESOLUTION_REQUIRED -> try {
// Show the dialog by calling startResolutionForResult(),
status.startResolutionForResult(
activity,
REQUEST_LOCATION
)
} catch (e: IntentSender.SendIntentException) {
Timber.e(e)
}
LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE -> {
activity.startActivity(Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS))
}
}
}
}
这是我在Fragment
中使用的方法:
创建用于请求 GPS 功能的扩展函数:
fun Fragment.requestGPSOn(request: ActivityResultLauncher<IntentSenderRequest>) { //new api
val locationRequest = LocationRequest.create().apply {
priority = LocationRequest.PRIORITY_BALANCED_POWER_ACCURACY //GPS accuracy
}
val settingRequest = LocationSettingsRequest.Builder().run {
addLocationRequest(locationRequest)
build()
}
val settingsClient = LocationServices.getSettingsClient(requireContext())
val task = settingsClient.checkLocationSettings(settingRequest) //【fire and receive result】
task.addOnFailureListener { //if GPS is not on currently
val intentSender = (it as ResolvableApiException).resolution.intentSender
val intentSenderRequest = IntentSenderRequest.Builder(intentSender).build()
request.launch(intentSenderRequest)
}
}
Fragment
中的设置:
class FirstFragment : Fragment() {
private lateinit var binding: FragmentFirstBinding
private lateinit var gpsOnRequest: ActivityResultLauncher<IntentSenderRequest>
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
binding = DataBindingUtil.inflate(inflater, R.layout.fragment_first, container, false)
gpsOnRequest = getGPSOnRequest()
binding.gpsOnButton.setOnClickListener {
requestGPSOn(gpsOnRequest) //extension function, 【will apply specified accuracy even already on!!】
}
return binding.root
}
private fun getGPSOnRequest() = registerForActivityResult(ActivityResultContracts.StartIntentSenderForResult()) { result ->
if (result.resultCode != RESULT_OK) {
//do your stuff
}
}
}
演示:https://youtu.be/nWsSADUmGzM
用于检查 GPS 状态:
fun Fragment.isGPSOn(): Boolean {
val locationManager = requireContext().getSystemService(Context.LOCATION_SERVICE) as LocationManager
return locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER)
}
请记住,startActivityForResult()
和 startIntentSenderForResult()
已被弃用,新结果 api 观看此官方视频:https://youtu.be/oP-zXjkT0C0。
当我尝试在不进入 phone 设置的情况下打开 gps 时,出现此对话框:
如何显示包含此类描述的对话框?
这是我的代码示例:
viewModel.onEnableGpsEvent.observe(this, Observer { event ->
event.getContentIfNotHandled()?.let {
activity?.let {
val locationRequest = LocationRequest.create()
locationRequest.priority = LocationRequest.PRIORITY_HIGH_ACCURACY
val builder = LocationSettingsRequest.Builder().addLocationRequest(locationRequest)
val task = LocationServices.getSettingsClient(it).checkLocationSettings(builder.build())
task.addOnSuccessListener { response ->
val states = response.locationSettingsStates
if (states.isLocationPresent) {
//TODO: Do something if need it
}
}
task.addOnFailureListener { e ->
if (e is ResolvableApiException) {
try {
// Handle result in onActivityResult()
e.startResolutionForResult(
it,
LOCATION_SETTING_REQUEST
)
} catch (sendEx: IntentSender.SendIntentException) {
}
}
}
}
我还有下一个依赖:
implementation 'com.google.android.gms:play-services-location:18.0.0'
使用下一个解决方案解决了这个问题:
override fun enableGps(activity: FragmentActivity) {
if (googleApiClient == null) {
googleApiClient = GoogleApiClient.Builder(context)
.addApi(LocationServices.API)
.addConnectionCallbacks(object : GoogleApiClient.ConnectionCallbacks {
override fun onConnected(bundle: Bundle?) {}
override fun onConnectionSuspended(i: Int) {
googleApiClient?.connect()
}
})
.addOnConnectionFailedListener { connectionResult ->
Timber.e("${connectionResult.errorCode}")
}.build()
googleApiClient?.connect()
}
val locationRequest = LocationRequest.create()
locationRequest.priority = LocationRequest.PRIORITY_HIGH_ACCURACY
locationRequest.interval = 10000
locationRequest.fastestInterval = 5000
val builder = LocationSettingsRequest.Builder().addLocationRequest(locationRequest)
builder.setAlwaysShow(true)
val result: PendingResult<LocationSettingsResult> = LocationServices.SettingsApi.checkLocationSettings(googleApiClient, builder.build())
result.setResultCallback { result ->
val status: Status = result.status
when (status.statusCode) {
LocationSettingsStatusCodes.RESOLUTION_REQUIRED -> try {
// Show the dialog by calling startResolutionForResult(),
status.startResolutionForResult(
activity,
REQUEST_LOCATION
)
} catch (e: IntentSender.SendIntentException) {
Timber.e(e)
}
LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE -> {
activity.startActivity(Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS))
}
}
}
}
这是我在Fragment
中使用的方法:
创建用于请求 GPS 功能的扩展函数:
fun Fragment.requestGPSOn(request: ActivityResultLauncher<IntentSenderRequest>) { //new api val locationRequest = LocationRequest.create().apply { priority = LocationRequest.PRIORITY_BALANCED_POWER_ACCURACY //GPS accuracy } val settingRequest = LocationSettingsRequest.Builder().run { addLocationRequest(locationRequest) build() } val settingsClient = LocationServices.getSettingsClient(requireContext()) val task = settingsClient.checkLocationSettings(settingRequest) //【fire and receive result】 task.addOnFailureListener { //if GPS is not on currently val intentSender = (it as ResolvableApiException).resolution.intentSender val intentSenderRequest = IntentSenderRequest.Builder(intentSender).build() request.launch(intentSenderRequest) } }
Fragment
中的设置:class FirstFragment : Fragment() { private lateinit var binding: FragmentFirstBinding private lateinit var gpsOnRequest: ActivityResultLauncher<IntentSenderRequest> override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View { binding = DataBindingUtil.inflate(inflater, R.layout.fragment_first, container, false) gpsOnRequest = getGPSOnRequest() binding.gpsOnButton.setOnClickListener { requestGPSOn(gpsOnRequest) //extension function, 【will apply specified accuracy even already on!!】 } return binding.root } private fun getGPSOnRequest() = registerForActivityResult(ActivityResultContracts.StartIntentSenderForResult()) { result -> if (result.resultCode != RESULT_OK) { //do your stuff } } }
演示:https://youtu.be/nWsSADUmGzM
用于检查 GPS 状态:
fun Fragment.isGPSOn(): Boolean {
val locationManager = requireContext().getSystemService(Context.LOCATION_SERVICE) as LocationManager
return locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER)
}
请记住,startActivityForResult()
和 startIntentSenderForResult()
已被弃用,新结果 api 观看此官方视频:https://youtu.be/oP-zXjkT0C0。