Merge "Fix API review comments, add remove callback." into nyc-dev
diff --git a/Android.mk b/Android.mk
index 2cfc9a2..b590761 100644
--- a/Android.mk
+++ b/Android.mk
@@ -215,6 +215,7 @@
core/java/android/nfc/INfcCardEmulation.aidl \
core/java/android/nfc/INfcFCardEmulation.aidl \
core/java/android/nfc/INfcUnlockHandler.aidl \
+ core/java/android/nfc/ITagRemovedCallback.aidl \
core/java/android/os/IBatteryPropertiesListener.aidl \
core/java/android/os/IBatteryPropertiesRegistrar.aidl \
core/java/android/os/ICancellationSignal.aidl \
diff --git a/api/current.txt b/api/current.txt
index 6fdd1bc..f0657c0 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -25011,6 +25011,7 @@
method public deprecated void enableForegroundNdefPush(android.app.Activity, android.nfc.NdefMessage);
method public void enableReaderMode(android.app.Activity, android.nfc.NfcAdapter.ReaderCallback, int, android.os.Bundle);
method public static android.nfc.NfcAdapter getDefaultAdapter(android.content.Context);
+ method public boolean ignore(android.nfc.Tag, int, android.nfc.NfcAdapter.OnTagRemovedListener, android.os.Handler);
method public boolean invokeBeam(android.app.Activity);
method public boolean isEnabled();
method public boolean isNdefPushEnabled();
@@ -25053,6 +25054,10 @@
method public abstract void onNdefPushComplete(android.nfc.NfcEvent);
}
+ public static abstract interface NfcAdapter.OnTagRemovedListener {
+ method public abstract void onTagRemoved();
+ }
+
public static abstract interface NfcAdapter.ReaderCallback {
method public abstract void onTagDiscovered(android.nfc.Tag);
}
@@ -25069,7 +25074,6 @@
public final class Tag implements android.os.Parcelable {
method public int describeContents();
- method public boolean done(int);
method public byte[] getId();
method public java.lang.String[] getTechList();
method public void writeToParcel(android.os.Parcel, int);
diff --git a/api/system-current.txt b/api/system-current.txt
index ddd9ad6..ba43ee4 100644
--- a/api/system-current.txt
+++ b/api/system-current.txt
@@ -27447,6 +27447,7 @@
method public boolean enableNdefPush();
method public void enableReaderMode(android.app.Activity, android.nfc.NfcAdapter.ReaderCallback, int, android.os.Bundle);
method public static android.nfc.NfcAdapter getDefaultAdapter(android.content.Context);
+ method public boolean ignore(android.nfc.Tag, int, android.nfc.NfcAdapter.OnTagRemovedListener, android.os.Handler);
method public boolean invokeBeam(android.app.Activity);
method public boolean isEnabled();
method public boolean isNdefPushEnabled();
@@ -27496,6 +27497,10 @@
method public abstract void onNdefPushComplete(android.nfc.NfcEvent);
}
+ public static abstract interface NfcAdapter.OnTagRemovedListener {
+ method public abstract void onTagRemoved();
+ }
+
public static abstract interface NfcAdapter.ReaderCallback {
method public abstract void onTagDiscovered(android.nfc.Tag);
}
@@ -27512,7 +27517,6 @@
public final class Tag implements android.os.Parcelable {
method public int describeContents();
- method public boolean done(int);
method public byte[] getId();
method public java.lang.String[] getTechList();
method public void writeToParcel(android.os.Parcel, int);
diff --git a/api/test-current.txt b/api/test-current.txt
index d40d0b8..2cbb566 100644
--- a/api/test-current.txt
+++ b/api/test-current.txt
@@ -25079,6 +25079,7 @@
method public deprecated void enableForegroundNdefPush(android.app.Activity, android.nfc.NdefMessage);
method public void enableReaderMode(android.app.Activity, android.nfc.NfcAdapter.ReaderCallback, int, android.os.Bundle);
method public static android.nfc.NfcAdapter getDefaultAdapter(android.content.Context);
+ method public boolean ignore(android.nfc.Tag, int, android.nfc.NfcAdapter.OnTagRemovedListener, android.os.Handler);
method public boolean invokeBeam(android.app.Activity);
method public boolean isEnabled();
method public boolean isNdefPushEnabled();
@@ -25121,6 +25122,10 @@
method public abstract void onNdefPushComplete(android.nfc.NfcEvent);
}
+ public static abstract interface NfcAdapter.OnTagRemovedListener {
+ method public abstract void onTagRemoved();
+ }
+
public static abstract interface NfcAdapter.ReaderCallback {
method public abstract void onTagDiscovered(android.nfc.Tag);
}
@@ -25137,7 +25142,6 @@
public final class Tag implements android.os.Parcelable {
method public int describeContents();
- method public boolean done(int);
method public byte[] getId();
method public java.lang.String[] getTechList();
method public void writeToParcel(android.os.Parcel, int);
diff --git a/core/java/android/nfc/INfcAdapter.aidl b/core/java/android/nfc/INfcAdapter.aidl
index 940565f..f991efe 100644
--- a/core/java/android/nfc/INfcAdapter.aidl
+++ b/core/java/android/nfc/INfcAdapter.aidl
@@ -28,6 +28,7 @@
import android.nfc.INfcCardEmulation;
import android.nfc.INfcFCardEmulation;
import android.nfc.INfcUnlockHandler;
+import android.nfc.ITagRemovedCallback;
import android.os.Bundle;
/**
@@ -55,6 +56,8 @@
oneway void invokeBeam();
oneway void invokeBeamInternal(in BeamShareData shareData);
+ boolean ignore(int nativeHandle, int debounceMs, ITagRemovedCallback callback);
+
void dispatch(in Tag tag);
void setReaderMode (IBinder b, IAppCallback callback, int flags, in Bundle extras);
diff --git a/core/java/android/nfc/INfcTag.aidl b/core/java/android/nfc/INfcTag.aidl
index 26d2bec..539fd4a 100644
--- a/core/java/android/nfc/INfcTag.aidl
+++ b/core/java/android/nfc/INfcTag.aidl
@@ -31,7 +31,6 @@
boolean isNdef(int nativeHandle);
boolean isPresent(int nativeHandle);
TransceiveResult transceive(int nativeHandle, in byte[] data, boolean raw);
- boolean done(int nativeHandle, int debounceMs);
NdefMessage ndefRead(int nativeHandle);
int ndefWrite(int nativeHandle, in NdefMessage msg);
diff --git a/core/java/android/nfc/ITagRemovedCallback.aidl b/core/java/android/nfc/ITagRemovedCallback.aidl
new file mode 100644
index 0000000..2a06ff3
--- /dev/null
+++ b/core/java/android/nfc/ITagRemovedCallback.aidl
@@ -0,0 +1,8 @@
+package android.nfc;
+
+/**
+ * @hide
+ */
+oneway interface ITagRemovedCallback {
+ void onTagRemoved();
+}
diff --git a/core/java/android/nfc/NfcAdapter.java b/core/java/android/nfc/NfcAdapter.java
index 6f911ce..8406bcf 100644
--- a/core/java/android/nfc/NfcAdapter.java
+++ b/core/java/android/nfc/NfcAdapter.java
@@ -35,11 +35,14 @@
import android.nfc.tech.NfcA;
import android.nfc.tech.NfcF;
import android.os.Bundle;
+import android.os.Handler;
import android.os.IBinder;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.util.Log;
+import java.io.IOException;
+
/**
* Represents the local NFC adapter.
* <p>
@@ -315,6 +318,8 @@
final HashMap<NfcUnlockHandler, INfcUnlockHandler> mNfcUnlockHandlers;
final Object mLock;
+ ITagRemovedCallback mTagRemovedListener; // protected by mLock
+
/**
* A callback to be invoked when the system finds a tag while the foreground activity is
* operating in reader mode.
@@ -386,6 +391,13 @@
}
/**
+ * A callback that is invoked when a tag is removed from the field.
+ */
+ public interface OnTagRemovedListener {
+ void onTagRemoved();
+ }
+
+ /**
* A callback to be invoked when an application has registered as a
* handler to unlock the device given an NFC tag at the lockscreen.
* @hide
@@ -541,6 +553,7 @@
mContext = context;
mNfcActivityManager = new NfcActivityManager(this);
mNfcUnlockHandlers = new HashMap<NfcUnlockHandler, INfcUnlockHandler>();
+ mTagRemovedListener = null;
mLock = new Object();
}
@@ -1494,6 +1507,75 @@
}
/**
+ * Signals that you are no longer interested in communicating with an NFC tag
+ * for as long as it remains in range.
+ *
+ * All future attempted communication to this tag will fail with {@link IOException}.
+ * The NFC controller will be put in a low-power polling mode, allowing the device
+ * to save power in cases where it's "attached" to a tag all the time (e.g. a tag in
+ * car dock).
+ *
+ * Additionally the debounceMs parameter allows you to specify for how long the tag needs
+ * to have gone out of range, before it will be dispatched again.
+ *
+ * Note: the NFC controller typically polls at a pretty slow interval (100 - 500 ms).
+ * This means that if the tag repeatedly goes in and out of range (for example, in
+ * case of a flaky connection), and the controller happens to poll every time the
+ * tag is out of range, it *will* re-dispatch the tag after debounceMs, despite the tag
+ * having been "in range" during the interval.
+ *
+ * Note 2: if a tag with another UID is detected after this API is called, its effect
+ * will be cancelled; if this tag shows up before the amount of time specified in
+ * debounceMs, it will be dispatched again.
+ *
+ * Note 3: some tags have a random UID, in which case this API won't work reliably.
+ *
+ * @param tag the {@link android.nfc.Tag Tag} to ignore.
+ * @param debounceMs minimum amount of time the tag needs to be out of range before being
+ * dispatched again.
+ * @param tagRemovedListener listener to be called when the tag is removed from the field.
+ * Note that this will only be called if the tag has been out of range
+ * for at least debounceMs, or if another tag came into range before
+ * debounceMs. May be null in case you don't want a callback.
+ * @param handler the {@link android.os.Handler Handler} that will be used for delivering
+ * the callback. if the handler is null, then the thread used for delivering
+ * the callback is unspecified.
+ * @return false if the tag couldn't be found (or has already gone out of range), true otherwise
+ */
+ public boolean ignore(final Tag tag, int debounceMs,
+ final OnTagRemovedListener tagRemovedListener, final Handler handler) {
+ ITagRemovedCallback.Stub iListener = null;
+ if (tagRemovedListener != null) {
+ iListener = new ITagRemovedCallback.Stub() {
+ @Override
+ public void onTagRemoved() throws RemoteException {
+ if (handler != null) {
+ handler.post(new Runnable() {
+ @Override
+ public void run() {
+ tagRemovedListener.onTagRemoved();
+ }
+ });
+ } else {
+ tagRemovedListener.onTagRemoved();
+ }
+ synchronized (mLock) {
+ mTagRemovedListener = null;
+ }
+ }
+ };
+ }
+ synchronized (mLock) {
+ mTagRemovedListener = iListener;
+ }
+ try {
+ return sService.ignore(tag.getServiceHandle(), debounceMs, iListener);
+ } catch (RemoteException e) {
+ return false;
+ }
+ }
+
+ /**
* Inject a mock NFC tag.<p>
* Used for testing purposes.
* <p class="note">Requires the
diff --git a/core/java/android/nfc/Tag.java b/core/java/android/nfc/Tag.java
index 40d5a8db..154d5a1 100644
--- a/core/java/android/nfc/Tag.java
+++ b/core/java/android/nfc/Tag.java
@@ -214,42 +214,6 @@
return techIntList;
}
- /**
- * Signals that you are no longer interested in communicating with this tag
- * for as long as it remains in range.
- *
- * All future attempted communication to this tag will fail with {@link IOException}.
- * The NFC controller will be put in a low-power polling mode, allowing the device
- * to save power in cases where it's "attached" to a tag all the time (eg a tag in
- * car dock).
- *
- * Additionally the debounceMs parameter allows you to specify for how long the tag needs
- * to have gone out of range, before it will be dispatched again.
- *
- * Note: the NFC controller typically polls at a pretty slow interval (100 - 500 ms).
- * This means that if the tag repeatedly goes in and out of range (for example, in
- * case of a flaky connection), and the controller happens to poll every time the
- * tag is out of range, it *will* re-dispatch the tag after debounceMs, despite the tag
- * having been "in range" during the interval.
- *
- * Note 2: if a tag with another UID is detected after this API is called, its effect
- * will be cancelled; if this tag shows up before the amount of time specified in
- * debounceMs, it will be dispatched again.
- *
- * Note 3: some tags have a random UID, in which case this API won't work.
- *
- * @param debounceMs minimum amount of time the tag needs to be out of range before being
- * dispatched again.
- * @return false if the Tag couldn't be found (or has gone out of range), true otherwise
- */
- public boolean done(int debounceMs) {
- try {
- return mTagService.done(getServiceHandle(), debounceMs);
- } catch (RemoteException e) {
- return false;
- }
- }
-
private static HashMap<String, Integer> getTechStringToCodeMap() {
HashMap<String, Integer> techStringToCodeMap = new HashMap<String, Integer>();