Making GPS tacking app. LocationRequest deprecated. Don't know how to solve - java

I'm making a location-tracking app. This is the first time I'm programming in Java and I have no idea how to update the deprecated methods. I see that Android Studio is trying its best to explain how to use the current methods, but I still keep messing it up.
LocationRequest locationRequest;
locationRequest = new LocationRequest(); // LocationRequest() is deprecated
// How often does the default location check occur?
locationRequest.setInterval(1000 * DEFAULT_UPDATE_INTERVAL); //.setInterval() is deprecated
// How often does the location check occur when set to the most frequent update?
locationRequest.setFastestInterval(1000 * FAST_UPDATE_INTERVAL); // setFastestInterval is deprecated
locationRequest.setPriority(LocationRequest.PRIORITY_BALANCED_POWER_ACCURACY);
// setPriority() is deprecated
// PRIORITY_BALANCED_POWER_ACCURACY constant is deprecated
sw_gps.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
if (sw_gps.isChecked()) {
// most accurate - use GPS
locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
// .setPriority method deprecated and PRIORITY_HIGH_ACCURACY constant deprecated
tv_sensor.setText("Using GPS sensors");
} else {
locationRequest.setPriority(LocationRequest.PRIORITY_BALANCED_POWER_ACCURACY);
tv_sensor.setText("Using Towers + WiFi");
// .setPriority and PRIORITY_BALANCED_POWER_ACCURACY are deprecated
}
}
});
So how do I fix this? The error messages I'm get when hovering over setPriority, and the constants is:
This method is deprecated. Use LocationRequest.Builder.setIntervalMillis(long) instead. May be removed in a future release.
This constant is deprecated. Use Priority.PRIORITY_HIGH_ACCURACY instead.
This constant is deprecated. Use Priority.PRIORITY_BALANCED_POWER_ACCURACY instead.
I'm sorry if this is not very readable. It's my first time using Java to build an android app and this is the best way I could formulate the question.
Thanks in advance.

Try using LocationRequest.Builder
Below code for creating location request
Kotlin
LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 10000)
.apply {
setWaitForAccurateLocation(false)
setMinUpdateIntervalMillis(IMPLICIT_MIN_UPDATE_INTERVAL)
setMaxUpdateDelayMillis(100000)
}.build()
Java
new LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 10000)
.setWaitForAccurateLocation(false)
.setMinUpdateIntervalMillis(IMPLICIT_MIN_UPDATE_INTERVAL)
.setMaxUpdateDelayMillis(100000)
.build()
Read more about here https://developers.google.com/android/reference/com/google/android/gms/location/LocationRequest.Builder

Related

SpeechRecognizerListener giving Bundle[EMPTY_PARCEL] in onResults(Bundle results) majority devices which have android 11

I am Using
speech = SpeechRecognizer.createSpeechRecognizer(getReactApplicationContext().getApplicationContext());
speech.setRecognitionListener(VoiceAppModule.this);
recognizerIntent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH);
recognizerIntent.putExtra(RecognizerIntent.EXTRA_SPEECH_INPUT_MINIMUM_LENGTH_MILLIS, 100000000);
recognizerIntent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_PREFERENCE, "en");
recognizerIntent.putExtra(RecognizerIntent.EXTRA_CALLING_PACKAGE, "com.languageacademy");
recognizerIntent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL, RecognizerIntent.LANGUAGE_MODEL_WEB_SEARCH);
recognizerIntent.putExtra(RecognizerIntent.EXTRA_MAX_RESULTS, 3);
recognizerIntent.putExtra(RecognizerIntent.EXTRA_SPEECH_INPUT_COMPLETE_SILENCE_LENGTH_MILLIS, 10000);
recognizerIntent.putExtra(RecognizerIntent.EXTRA_SPEECH_INPUT_POSSIBLY_COMPLETE_SILENCE_LENGTH_MILLIS, 10000);
The Above code for Speech recognition.
#Override
public void onResults(Bundle results) {
in about On Result the result is giving Bundle[EMPTY_PARCEL] in Result.
ArrayList matches = results.getStringArrayList(SpeechRecognizer.RESULTS_RECOGNITION);
I tried in many of the Devices it is mainly giving problem in MI phones having android 11 and also some samsung phones.
Same problem here, this bug started to occur like few days ago.
I think the reason of this bug is the new version of "Google"
app (https://play.google.com/store/apps/details?id=com.google.android.googlequicksearchbox), as SpeechRecognizer uses this app to recognize voice.
If you click uinstall "Google"
app, it will roll back to older version and onResult callback will work fine.
Solution that fixed my problem was removing:
EXTRA_SPEECH_INPUT_MINIMUM_LENGTH_MILLIS extras
Note that it is extremely rare you'd want to specify this value in an intent. Generally, it should be specified only when it is also used as the value for EXTRA_SEGMENTED_SESSION to enable segmented session mode. Note also that certain values may cause undesired or unexpected results - use judiciously!
https://developer.android.com/reference/android/speech/RecognizerIntent#EXTRA_SEGMENTED_SESSION
I confirm the answer gave by Seba, only in my case I have to remove also
RecognizerIntent.EXTRA_MAX_RESULTS RecognizerIntent.EXTRA_SPEECH_INPUT_COMPLETE_SILENCE_LENGTH_MILLIS RecognizerIntent.EXTRA_SPEECH_INPUT_MINIMUM_LENGTH_MILLIS RecognizerIntent.EXTRA_SPEECH_INPUT_POSSIBLY_COMPLETE_SILENCE_LENGTH_MILLIS
and affected also Huawei and Samsung devices with Android 9, so it seems the issues's propagating day by day.
I was also facing the same issue. After removing the below intent it started working.
putExtra(RecognizerIntent.EXTRA_SPEECH_INPUT_COMPLETE_SILENCE_LENGTH_MILLIS, 3000)
Previous intent :
recognizerIntent = Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH).apply {
putExtra(RecognizerIntent.EXTRA_LANGUAGE_PREFERENCE, "en")
putExtra(RecognizerIntent.EXTRA_CALLING_PACKAGE, packageName)
putExtra(
RecognizerIntent.EXTRA_LANGUAGE_MODEL,
RecognizerIntent.LANGUAGE_MODEL_WEB_SEARCH
)
putExtra(RecognizerIntent.EXTRA_SPEECH_INPUT_COMPLETE_SILENCE_LENGTH_MILLIS, 3000)
putExtra(RecognizerIntent.EXTRA_MAX_RESULTS, 1)
}
Modified Intent:
recognizerIntent = Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH).apply {
putExtra(RecognizerIntent.EXTRA_LANGUAGE_PREFERENCE, "en")
putExtra(RecognizerIntent.EXTRA_CALLING_PACKAGE, packageName)
putExtra(
RecognizerIntent.EXTRA_LANGUAGE_MODEL,
RecognizerIntent.LANGUAGE_MODEL_WEB_SEARCH
)
putExtra(RecognizerIntent.EXTRA_MAX_RESULTS, 1)
}

Is it impossible to call mediaplayer.setpreparedlistener when mediapler.create method is used?

I'm trying to learn kotlin with a media player project in Android studio.
So I create a media player using create method.
val mediaplayer : MediaPlayer
mediaplayer= MediaPlayer.create(this,R.raw.song)
mediaplayer.start()
But the problem come when I use this:
mediaplayer.setOnPreparedListener(object: MediaPlayer.onPreparedListener{
override fun onPrepared(MediaPlayer mp){
val max = mp.max
Seekbar.max = max
textview.text = convertToSeconde(max) // a function I define
mp.start()
}
})
The problem is that, when I run the app my implementation of onpreparedlistener have never been called. And any error is raise to tell me what the cause.
Can you help me on this please?
No. It is not possible. But, why do you want to do so? It is prepared immediately after that file is created. But, in some cases it might not get prepared due to some issue with the file or uri. So, you can use this alternate after the .create() function:
if(mediaplayer != null){
// it was not created or prepared.
}else{
// good news. it got prepared successfully
}

Android FusedLocationProviderClient problem

I have been following a tutorial however it is quite old and uses the deprecated googleApiClient. Weirdly though, when I use
implementation 'com.google.android.gms:play-services-maps:17.0.0'
implementation 'com.google.android.gms:play-services-location:17.0.0'
It works as should do by displaying the location on the map. I assumed it wouldn't work and when debugging before it wouldn't build.
I have tried to impelement a new way using the updating version whereby the fusedLocationApi isn't included.
Attached are the working version with fusedLocationApi & googleClientApi, and the newer code which builds but isn't showing the location on the map when the app builds.
Maybe there is something missing in the updated code that isn't producing the location to show on the map??
I'm new to Android to any help appreciated :)
Old Working Version - https://pastebin.com/VG4AUJrv
Updated Not Working Version - https://pastebin.com/xa674c5f
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M)
{
if (ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED)
{
// add here
fusedLocationProviderClient?.requestLocationUpdates(locationRequest, locationCallback, Looper.myLooper())
mMap.isMyLocationEnabled = true
}else
{
checkLocationPermission()
}
}
Your problem is here.
When you grant an application permission it will not perform a location search so you need to write a method to do it if you have granted it permission.

Get User Android Version

is there any way for my application to get the user's Android Version or API Level ? .. because i am working on an app that supports API 9 (2.3 Gingerbread) .. and since API 9 does not support DialogFragments even with android.support.v4.app.DialogFragment imported, i decided to do an if else statement instead
if (the users Android Version is Lower than API 11)
{
i will show a new class instead of a Dialog Fragment containing all information about the developer
}
else if (the users Android Version is Higher than or equal to API 11)
{
my dialog fragment will show up containing all information about the developer
}
i hope anyone can help me out about this, thanks :)
Use Build.VERSION.SDK_INT to get the API level. You can then compare it against values in Build.VERSION_CODES:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
// do something cool
}
Standard how to execute code for different versions.
Android provides a unique code for each platform version in the Build constants class. Use these codes within your app to build conditions that ensure the code that depends on higher API levels is executed only when those APIs are available on the system.
#SuppressWarnings("deprecation")
// We use the new method when supported
#SuppressLint("NewApi")
// We check which build version we are using.
#Override
public void onGlobalLayout() {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
mapView.getViewTreeObserver()
.removeGlobalOnLayoutListener(this);
} else {
mapView.getViewTreeObserver()
.removeOnGlobalLayoutListener(this);
}
Try this:
Build.VERSTION.RELEASE
http://developer.android.com/reference/android/os/Build.VERSION.html

How to support multiple android version in your code?

Take accessing contacts in android
android.jar for versions 1.6 has People.CONTENT_URI for invoking contacts related info whereas in later versions we need to have api support for RawContacts.CONTENT_URI.
Same thing is true for accessing calendar for instance as its URI is changed in android 2.2.
Is there a best practice to manage all different changes without adding additional application or build separately for each version of changes?
For my money, a very good answer is at http://android-developers.blogspot.co.uk/2010/07/how-to-have-your-cupcake-and-eat-it-too.html. However, the example there is a little more complicated than need be, so based on that, here is an example of how to cope with it when building notifications. The underlying reason this works is a consequence of how java engines interpret classes: it only looks at them when needed, so if you wrap version specific code up in a class and only create it when you know you are using that version, it all works ...
There are, as far as I can tell, two generations of approaches to creating notification, and a naming change along the way in the second. So that gives three ways to do it. For each way, create a class with the notification generation in it:
The first approach (used through to Gingerbread):
public class MyNotificationBuilderToGingerBread {
Notification notification = null;
MyNotificationBuilderToGingerBread(Context myContext, int icon, String ticker, String title, String info, Long timeStamp, PendingIntent pendingIntent, int flags) {
notification = new Notification(R.drawable.ic_sb, ticker, timeStamp);
notification.setLatestEventInfo(myContext, title, info, pendingIntent);
notification.flags |= flags;
}
Notification get() {
return notification;
}
}
The second approach, Honeycomb to IceCreamSandwich:
public class MyNotificationBuilderHoneyCombToIceCreamSandwich {
Notification.Builder mb = null;
MyNotificationBuilderHoneyCombToIceCreamSandwich(Context myContext, int icon, String ticker, String title, String info, Long timeStamp, PendingIntent pendingIntent, boolean onGoing) {
mb = new Notification.Builder(myContext);
mb.setSmallIcon(icon);
mb.setContentIntent(pendingIntent);
mb.setContentTitle(title);
mb.setContentText(info);
mb.setWhen(timeStamp);
if (ticker != null) mb.setTicker(ticker);
mb.setOngoing(onGoing);
}
Notification get() {
return mb.getNotification();
}
}
The second generation, with the name change, Jellybean (onwards, so far ...):
public class MyNotificationBuilderJellyBean {
Notification.Builder mb = null;
MyNotificationBuilderJellyBean(Context myContext, int icon, String ticker, String title, String info, Long timeStamp, PendingIntent pendingIntent, boolean onGoing) {
mb = new Notification.Builder(myContext);
mb.setSmallIcon(icon);
mb.setContentIntent(pendingIntent);
mb.setContentTitle(title);
mb.setContentText(info);
mb.setWhen(timeStamp);
if (ticker != null) mb.setTicker(ticker);
mb.setOngoing(onGoing);
}
Notification get() {
return mb.build();
}
}
Then, you just need to pick which class to instantiate on the fly:
// System information
private final int sdkVersion = Build.VERSION.SDK_INT;
// If you want to go really old:
// (actually, there is a question about how this issue should be handled
// systematically. Suggestions welcome.)
// final int sdkVersion = Integer.parseInt(Build.VERSION.SDK);
// This is for a permanent notification. Change the final argument (flags or boolean) if it isn't meant ot be
// For meaning of other variable, see notification documentation on the android website.
if (sdkVersion < Build.VERSION_CODES.HONEYCOMB) {
MyNotificationBuilderToGingerBread mnb = new MyNotificationBuilderToGingerBread(myContext, R.drawable.notification_icon, ticketText, title, infoText, timeStampMillis, pendingIntentForTapOnFullNotitifcation, Notification.FLAG_ONGOING_EVENT | Notification.FLAG_NO_CLEAR);
notification = mnb.get();
}
else if (sdkVersion < Build.VERSION_CODES.JELLY_BEAN) {
MyNotificationBuilderHoneyCombToIceCreamSandwich mnb = new MyNotificationBuilderHoneyCombToIceCreamSandwich(myContext, R.drawable.notification_icon, ticketText, title, infoText, timeStampMillis, pendingIntentForTapOnFullNotitifcation, true);
notification = mnb.get();
}
else {
MyNotificationBuilderJellyBean mnb = new MyNotificationBuilderJellyBean(myContext, R.drawable.notification_icon, ticketText, title, infoText, timeStampMillis, pendingIntentForTapOnFullNotitifcation, true);
notification = mnb.get();
}
// Send the notification.
notificationManager.notify(idForNotificationManager, notification);
Hope this helps!
There are many resources for you to utilize to help support multiple versions of android.
Read this blog post here and
then read this one here, they
will help you address API level
version support issues.
Read this blog post on multiple
screen support, especially how the
asset hierarchy in parsed in res
folder. This will help you
understand and design how to do
asset folder structure to support
different screen size/densities and
android versions.
Lastly write your own custom ant build
scripts so that you can compile with
all versions of android.
Quite Honestly, it's a pain.
I usually, just isolate parts of code that are different and access them using abstract classes. So technically creating different version for different OS.
But there are other ways. The best one i've seen involves using reflection.
If you don't really need the new functionnalities, and really have to support old Android versions, drop it. Build your app for the oldest version, and don't bother with this kind of thing.
In the other case, you can detect the version using Build, and use reflection to load the classes you need. An example of that can be found in the source code of the K9Mail app
There's a nice article on android.com about it:
http://developer.android.com/resources/articles/backward-compatibility.html
Personally I would suggest the wrapper class or wrapper library solution. But in small cases the reflection should be fine (and in case performance is not a problem for you).
If you need more info, ask in comments.
This is a great article for when you have to do reflection in Android (to support multiple API levels).
And when you have to have different resources for different API Levels, this is the reference to use (see the section on "Platform Version (API level)").
If on Eclipse, from ADT version 17 you can specify code to run with some version simply as described in Lint API Check.
The code word is #TargetAPI(XX)
Hope it helps
Best practice (though not for Android, but for J2ME) to my knowledge is to use preprocessing C/C++ styled statements, like:
//#if S40
...
//#else
...
//#endif
Some IDE's support these kind of preprocessing, e.g. Netbeans. To my knowledge Eclipse has some plugins to enable preprocessing also. I don't really know are they applicable to Android development. Try to google yourself.

Categories