سؤال

How can I find out for sure that device really has gsm, cdma or other cellular network equipment (not just WiFi)? I don't want to check current connected network state, because device can be offline in the moment. And I don't want to check device id via ((TelephonyManager) act.getSystemService(Context.TELEPHONY_SERVICE)).getDeviceId() because some devices would just give you polymorphic or dummy device ID.

Actualy, I need to check cell equipment exactly for skipping TelephonyManager.getDeviceId and performing Settings.Secure.ANDROID_ID check on those devices that don't have cellular radio. I have at least one tablet (Storage Options Scroll Excel 7") which returns different IMEIs every time you ask it, although it should return null as it has no cell radio (the same situation here: Android: getDeviceId() returns an IMEI, adb shell dumpsys iphonesubinfo returns Device ID=NULL). But I need to have reliable device id that is the same every time I ask.

I'd be glad to hear your thoughts!

هل كانت مفيدة؟

المحلول 2

Just in case somebody needs complete solution for this: Reflection is used because some things may not exist on some firmware versions. MainContext - main activity context.

    static public int getSDKVersion()
{
    Class<?> build_versionClass = null;

    try
    {
        build_versionClass = android.os.Build.VERSION.class;
    }
    catch (Exception e)
    {
    }

    int retval = -1;
    try
    {
        retval = (Integer) build_versionClass.getField("SDK_INT").get(build_versionClass);
    }
    catch (Exception e)
    {
    }

    if (retval == -1)
        retval = 3; //default 1.5

    return retval;
}

static public boolean hasTelephony()
{
    TelephonyManager tm = (TelephonyManager) Hub.MainContext.getSystemService(Context.TELEPHONY_SERVICE);
    if (tm == null)
        return false;

    //devices below are phones only
    if (Utils.getSDKVersion() < 5)
        return true;

    PackageManager pm = MainContext.getPackageManager();

    if (pm == null)
        return false;

    boolean retval = false;
    try
    {
        Class<?> [] parameters = new Class[1];
        parameters[0] = String.class;
        Method method = pm.getClass().getMethod("hasSystemFeature", parameters);
        Object [] parm = new Object[1];
        parm[0] = "android.hardware.telephony";
        Object retValue = method.invoke(pm, parm);
        if (retValue instanceof Boolean)
            retval = ((Boolean) retValue).booleanValue();
        else
            retval = false;
    }
    catch (Exception e)
    {
        retval = false;
    }

    return retval;
}

نصائح أخرى

If you're publishing in the store, and you want to limit your application only being visible to actual phones, you could add a <uses-feature> into your manifest that asks for android.hardware.telephony. Check out if that works for you from the documentation.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top