Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Android: Changing NFC settings (on/off) programmatically

I trying to change NFC settings (on/off) programmatically on Android 2.3.3.

On the phone, under the "Wireless & network settings",
you can choose to set whether you want to use NFC to read and exchange tags or not.

So I would like to toggle this setting in my application.
But I can't seem to find an api for this.

I'm looking for some code that would probably look like this:

WifiManager wifi = (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
wifi.setWifiEnabled( on/off );
like image 860
dosa Avatar asked May 10 '11 04:05

dosa


People also ask

How do I change NFC settings on Android?

If you have a Samsung Android phone, check under settings > connections > tap NFC and contactless payments > tap the switch to turn NFC on. Once this is turned on for your device, you can adjust your settings for contactless payments and select your preferred mobile payment service, such as Google Pay or Samsung Pay.

How do I disable default Android NFC app when NFC is used in my app?

The solution is simple: Go to App Manager, select ALL, search for NFC Tag or whatever is the name of Samcung NFC Tag writer and disable the app. Now when you read NFC it will simple do the action, no questions asked.

What is near field communication Android?

Near Field Communication (NFC) is a set of short-range wireless technologies, typically requiring a distance of 4cm or less to initiate a connection. NFC allows you to share small payloads of data between an NFC tag and an Android-powered device, or between two Android-powered devices. Tags can range in complexity.


3 Answers

It's not possible programatically without rooting device. But you can start NFC Settings Activity by intent action Settings.ACTION_NFC_SETTINGS for api level 16 and above. For api < 16 use Settings.ACTION_WIRELESS_SETTINGS

Previous selected answer suggests to use WIFI_SETTINGS but we can directly move to NFC_SETTINGS

Here's the example :

android.nfc.NfcAdapter mNfcAdapter= android.nfc.NfcAdapter.getDefaultAdapter(v.getContext());              if (!mNfcAdapter.isEnabled()) {                  AlertDialog.Builder alertbox = new AlertDialog.Builder(v.getContext());                 alertbox.setTitle("Info");                 alertbox.setMessage(getString(R.string.msg_nfcon));                 alertbox.setPositiveButton("Turn On", new DialogInterface.OnClickListener() {                     @Override                     public void onClick(DialogInterface dialog, int which) {                         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {                             Intent intent = new Intent(Settings.ACTION_NFC_SETTINGS);                             startActivity(intent);                         } else {                             Intent intent = new Intent(Settings.ACTION_WIRELESS_SETTINGS);                             startActivity(intent);                         }                     }                 });                 alertbox.setNegativeButton("Close", new DialogInterface.OnClickListener() {                      @Override                     public void onClick(DialogInterface dialog, int which) {                      }                 });                 alertbox.show();              } 
like image 179
Kishan Raval Avatar answered Sep 23 '22 04:09

Kishan Raval


if you want to do it programmatically, apperently this Q holds the answer:

How can I enable NFC reader via API?

Edit

it didn't hold the answer, but it held the key to the answer, on which I based my code I answered with in the Q.

I will paste it here as well in case anyone's interested.

I got it working through reflection

This code works on API 15, haven't checked it against other verions yet

public boolean changeNfcEnabled(Context context, boolean enabled) {
    // Turn NFC on/off
    final boolean desiredState = enabled;
    mNfcAdapter = NfcAdapter.getDefaultAdapter(context);

    if (mNfcAdapter == null) {
        // NFC is not supported
        return false;
    }

    new Thread("toggleNFC") {
        public void run() {
            Log.d(TAG, "Setting NFC enabled state to: " + desiredState);
            boolean success = false;
            Class<?> NfcManagerClass;
            Method setNfcEnabled, setNfcDisabled;
            boolean Nfc;
            if (desiredState) {
                try {
                    NfcManagerClass = Class.forName(mNfcAdapter.getClass().getName());
                    setNfcEnabled   = NfcManagerClass.getDeclaredMethod("enable");
                    setNfcEnabled.setAccessible(true);
                    Nfc             = (Boolean) setNfcEnabled.invoke(mNfcAdapter);
                    success         = Nfc;
                } catch (ClassNotFoundException e) {
                } catch (NoSuchMethodException e) {
                } catch (IllegalArgumentException e) {
                } catch (IllegalAccessException e) {
                } catch (InvocationTargetException e) {
                }
            } else {
                try {
                    NfcManagerClass = Class.forName(mNfcAdapter.getClass().getName());
                    setNfcDisabled  = NfcManagerClass.getDeclaredMethod("disable");
                    setNfcDisabled.setAccessible(true);
                    Nfc             = (Boolean) setNfcDisabled.invoke(mNfcAdapter);
                    success         = Nfc;
                } catch (ClassNotFoundException e) {
                } catch (NoSuchMethodException e) {
                } catch (IllegalArgumentException e) {
                } catch (IllegalAccessException e) {
                } catch (InvocationTargetException e) {
                }
            }
            if (success) {
                Log.d(TAG, "Successfully changed NFC enabled state to "+ desiredState);
            } else {
                Log.w(TAG, "Error setting NFC enabled state to "+ desiredState);
            }
        }
    }.start();
    return false;
}//end method

This requires 2 permissions though, put them in the manifest:

 <!-- change NFC status toggle -->
    <uses-permission android:name="android.permission.NFC" />
    <uses-permission android:name="android.permission.WRITE_SECURE_SETTINGS" />

The NFC button's state switches accordingly when the code is used, so there are no issues when doing it manually in the seetings menu.


To clarify: This code doesn't work on normal devices. There are ways around, but at least it requires root.

like image 21
slinden77 Avatar answered Sep 20 '22 04:09

slinden77


You can not turn it on/off manually but you can send the user to the preferences if it is off:

    if (!nfcForegroundUtil.getNfc().isEnabled())
    {
        Toast.makeText(getApplicationContext(), "Please activate NFC and press Back to return to the application!", Toast.LENGTH_LONG).show();
        startActivity(new Intent(android.provider.Settings.ACTION_WIRELESS_SETTINGS));
    }

Method getNfc() just returns the nfcadapter:

nfc = NfcAdapter.getDefaultAdapter(activity.getApplicationContext());

like image 40
Sven Haiges Avatar answered Sep 22 '22 04:09

Sven Haiges