So the code is following:
public static ActionBarHelper createInstance(Activity activity) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) {
return new ActionBarHelperICS(activity);
} else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
return new ActionBarHelperHoneycomb(activity);
} else {
return new ActionBarHelperBase(activity);
}
}
If my device is 2.3 (api 9) it shouldn't support Build.VERSION_CODES.ICE_CREAM_SANDWICH but yet it runs, why is that? If it had been a method I called it would have crashed. Is it because it is a public static final int and therefor added from to my code? Please give some general detail and not just a yes/no answer :)
As Stefan pointed out, the api level used to compile the code determines the constants visible at compile time. For my case this doesn't give any problems as I just compare simple values. This only give problems if you use a set method that uses different constants and you happent to use a constant that wasn't possible to handle for your api version.
Related
How to get the device is supported for Dual Sim for Below Android R.
I am using the following code. But I am getting a deprecated warning for telephony.getPhoneCount().
How to get for below Android R. Or do we need to add #SuppressWarnings( "deprecation" )?
public boolean isDuelSim(Context pContext) {
TelephonyManager telephony = (TelephonyManager) pContext.getSystemService(Context.TELEPHONY_SERVICE);
if (telephony != null) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
return telephony.getActiveModemCount() == 2; //Dual SIM functionality
} else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
return telephony.getPhoneCount() == 2;
}
}
return false;
}
The getPhoneCount() method seems to be the right way of checking if the device supports dual SIM on api levels from M to Q. If you are compiling your project for R or greater, you will get the deprecation lint warning.
IMO, your implementation is correct and if you need to suppress that warning then either add the #SuppressWarnings("deprecation") annotation to your isDualSim() method signature or the //noinspect comment above the telephony.getPhoneCount() call.
BTW, I'd also suggest considering the case when getActiveModemCount() or getPhoneCount() returns a 3. Whether a tri SIM phone should pass your dualSIM test or not depends on your use case, of course.
I am trying to use #ChecksSdkIntAtLeast annotation to convert our java utility functions into kotlin properties that would not require #SuppressLint("NewApi").
But anyway I write the property, it stops red underlining code for both branches of if.
Demo:
#get:ChecksSdkIntAtLeast(api = Build.VERSION_CODES.O)
val isAtLeastOreo: Boolean
get() = Build.VERSION.SDK_INT >= Build.VERSION_CODES.O
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
manager.getNotificationChannel("general")
} else {
manager.getNotificationChannel("general") // CORRECTLY UNDERLINED
}
if (isAtLeastOreo) {
manager.getNotificationChannel("general")
} else {
manager.getNotificationChannel("general") // NOT UNDERLINED - WHY??
}
Same thing happens if I make it into function instead of getter. The only working one would be using lambda, but then I am losing if-else construct and would require massive amount of places to refactor.
Issue has been reported on Aug 23. Waiting for response
https://issuetracker.google.com/issues/197428342
Basically I want to run a code if the OS is Honeycomb or latter, and a different code if not. Should I compare using > or >= ?
if(Build.VERSION.SDK_INT > Build.VERSION_CODES.HONEYCOMB) {
} else {
}
To use HoneyComb use >=
i.e. code as
if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
} else {
}
For more info see at Android Check for HoneyComb
As per your requirement used >= means with HoneyComb
I have some code that compiles successfully using ViewTreeObserver#removeOnGlobalLayoutListener(...) and when it runs, this method throws NoSuchMethodError. Why?
There are two methods in ViewTreeObserver with almost the same name.
removeOnGlobalLayoutListener(ViewTreeObserver.OnGlobalLayoutListener victim)
(on then global) is a method that was added in API 16. It replaces
removeGlobalOnLayoutListener(ViewTreeObserver.OnGlobalLayoutListener victim)
(global then on) which has existed since API 1, but which is now deprecated.
Both methods can appear present at compile-time (if you're building against Jellybean or higher) but the newer one will fail on pre-Jellybean devices.
This code thwarts the error:
try {
thing.removeOnGlobalLayoutListener(victim);
} catch (NoSuchMethodError x) {
thing.removeGlobalOnLayoutListener(victim);
}
So does this code:
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
thing.removeGlobalOnLayoutListener(victim);
} else {
thing.removeOnGlobalLayoutListener(victim);
}
I assume you are talking about removeOnGlobalLayoutListener from ViewTreeObserver class. This method was added in API level 16. My best guess is that you try to use it on a device running an old version of Android that's why it can't be found.
I have working code
public static void removeOnGlobalLayoutListener(View v, ViewTreeObserver.OnGlobalLayoutListener listener){
if (Build.VERSION.SDK_INT < 16) {
v.getViewTreeObserver().removeGlobalOnLayoutListener(listener);
} else {
v.getViewTreeObserver().removeOnGlobalLayoutListener(listener);
}
}
I would like to write an application that uses live wallpapers for insatnce. this feature is supported only in version 7 and up. Is it posiible, that the application checks the version of the android phone and depending on that runs different code (e.g. uses live wallpaper or static background.)
Do you have a code example for that? Does that require special permissions?
Assuming you're requiring Android 1.6 or newer:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ECLAIR_MR1) {
...
}
Yes there is. Look at the Build class in Android. You can use it like so Build.VERSION.SDK_INT
public static final int ECLAIR_MR1 =7;
public static final int FROYO =8;
if(Build.VERSION.SDK_INT==FROYO){
Toast.makeText(getApplicationContext(), "Iam a FROYO-Phone", 1).show();
}else if(Build.VERSION.SDK_INT==ECLAIR_MR1){
Toast.makeText(getApplicationContext(), "Iam an ECLAIR-Phone", 1).show();
}
SDK_INT is not available on very early builds. So if your manifest has for instance:
android:minSdkVersion="1"
you can use something like this:
#TargetApi(Build.VERSION_CODES.DONUT)
static boolean getPreHoneyComb() {
try {
Build.VERSION.class.getField("SDK_INT");
}
catch (NoSuchFieldException e) {
return true;
}
return Build.VERSION.SDK_INT < Build.VERSION_CODES.HONEYCOMB;
}