Unable To Trigger Intent On Nfc Read Using With Locktaskmode
Solution 1:
Update:
Based on the comment that the App is in LockTaskMode
this might change the systems ability to re-launch Apps to deliver an intent
to it (I have no experience of LockTaskMode
)
I suggest that you don't use the old NFC API's that have to use launching or re-launching Apps when you are in the restrictive LockTaskMode
.
I suggest that you try the newer and much better enableReaderMode
NFC API to read cards.
https://developer.android.com/reference/android/nfc/NfcAdapter#enableReaderMode(android.app.Activity,%20android.nfc.NfcAdapter.ReaderCallback,%20int,%20android.os.Bundle)
This enableReaderMode
NFC API causes a callback in your App that starts a new thread to handle the incoming NFC data, there is no launch or re-launching of you App and therefore might not have a problem with LockTaskMode
.
example of enableReaderMode
API use.
publicclassMainActivityextendsAppCompatActivityimplementsNfcAdapter.ReaderCallback{
private NfcAdapter mNfcAdapter;
@OverrideprotectedvoidonResume() {
super.onResume();
enableNfc();
}
privatevoidenableNfc(){
mNfcAdapter = NfcAdapter.getDefaultAdapter(this);
if(mNfcAdapter!= null && mNfcAdapter.isEnabled()) {
// READER_PRESENCE_CHECK_DELAY is a work around for a Bug in some NFC implementations.Bundleoptions=newBundle();
options.putInt(NfcAdapter.EXTRA_READER_PRESENCE_CHECK_DELAY, 250);
// Ask for all type of cards to be sent to the App as they all might contain NDEF data
mNfcAdapter.enableReaderMode(this,
this,
NfcAdapter.FLAG_READER_NFC_A |
NfcAdapter.FLAG_READER_NFC_B |
NfcAdapter.FLAG_READER_NFC_F |
NfcAdapter.FLAG_READER_NFC_V |
NfcAdapter.FLAG_READER_NO_PLATFORM_SOUNDS,
options);
} else {
NfcMessage();
}
}
@OverrideprotectedvoidonPause() {
super.onPause();
if(mNfcAdapter!= null)
mNfcAdapter.disableReaderMode(this);
}
// This gets run in a new thread on Tag detection// Thus cannot directly interact with the UI ThreadpublicvoidonTagDiscovered(Tag tag) {
// Get the Tag as an NDEF tag TechnologyNdefmNdef= Ndef.get(tag);
// only process if there is NDEF data on the cardif (mNdef != null) {
NdefMessagemNdefMessage= mNdef.getCachedNdefMessage();
// Now process the Ndef message
....
// If success of reading the correct Ndef message// Make a notification sound (as we disabled PLATFORM_SOUNDS when enabling reader Mode)// As getting a confirmation sound too early causes bad user behaviour especial when trying to write to cards
}
// Ignore other Tag types.
}
....
Original
I'll leave the original answer here as it shows here the working of the System NFC App which with enableForegroundDispatch
directly delivers the an intent with the NFC data in it to your App by re-launching it and Pausing and Resuming it which fires the onNewIntent
It also explains if you have not enableForegroundDispatch
then the system NFC App passes the NFC intent to the Android OS which causes it to find an App that can handle this type of Intent, which it does by looking at all the App's manifest files for Intent filter to match.
So the Manifest Intent filters will cause Android to launch your App if a matching Tag is scanned by the system.
onNewIntent
is for
the activity is re-launched while at the top of the activity stack instead of a new instance of the activity being started, onNewIntent() will be called on the existing instance with the Intent that was used to re-launch it.
From https://developer.android.com/reference/android/app/Activity#onNewIntent(android.content.Intent)
So in this scenario where your App is not running it cannot be re-launched thus the Intent has to be captured in onCreate
Instead.
So in onCreate
put something like
Intentintent= getIntent();
// Check to see if the App was started because of the Intent filter in the manifest, if yes read the data from the Intentif (NfcAdapter.ACTION_NDEF_DISCOVERED.equals(intent.getAction())) {
readFromIntent(intent);
}
Now if you want to cover receiving NFC data while the App is running you need to use enableForegroundDispatch
and onNewIntent
https://developer.android.com/guide/topics/connectivity/nfc/advanced-nfc#foreground-dispatch
Which can be done creating a Intent Filter in onResume
and enabling foreground dispatch (foreground dispatch should be disabled when your app is not in the foreground i.e in onPause
as shown).
e.g. something like
private NfcAdapter adapter;
publicvoidonResume() {
super.onResume();
pendingIntent = PendingIntent.getActivity(this, 0, newIntent(this,
getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);
IntentFilterndef=newIntentFilter(NfcAdapter.ACTION_NDEF_DISCOVERED);
try {
// Only look for plain text mime type
ndef.addDataType("text/plain");
}
catch (MalformedMimeTypeException e) {
thrownewRuntimeException("fail", e);
}
intentFiltersArray = newIntentFilter[] {ndef, };
adapter = NfcAdapter.getDefaultAdapter(this);
adapter.enableForegroundDispatch(this, pendingIntent, intentFiltersArray, null);
}
@OverridepublicvoidonPause() {
super.onPause();
adapter.disableForegroundDispatch(this);
}
Post a Comment for "Unable To Trigger Intent On Nfc Read Using With Locktaskmode"