blob: 76bd0ece384a4fb8e05f03001fdf1f098596518d [file] [log] [blame]
Nick Pellyc84c89a2011-08-22 22:27:11 -07001/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package android.nfc;
18
19import android.app.Activity;
Nick Pelly8ce7a272012-03-21 15:14:09 -070020import android.app.Application;
Andres Morales56f299b2014-10-31 08:26:33 -070021import android.content.ContentProvider;
Martijn Coenen7fe9fa12014-01-29 17:28:04 -080022import android.content.Intent;
Nick Pelly1d7e9062012-04-03 17:46:00 -070023import android.net.Uri;
Martijn Coenen5b1e0322013-09-02 20:38:47 -070024import android.nfc.NfcAdapter.ReaderCallback;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -070025import android.os.Binder;
Nick Pelly8ce7a272012-03-21 15:14:09 -070026import android.os.Bundle;
Nick Pellyc84c89a2011-08-22 22:27:11 -070027import android.os.RemoteException;
Andres Morales56f299b2014-10-31 08:26:33 -070028import android.os.UserHandle;
Nick Pellyc84c89a2011-08-22 22:27:11 -070029import android.util.Log;
30
Nick Pelly8ce7a272012-03-21 15:14:09 -070031import java.util.ArrayList;
32import java.util.LinkedList;
33import java.util.List;
Nick Pellyc84c89a2011-08-22 22:27:11 -070034
35/**
36 * Manages NFC API's that are coupled to the life-cycle of an Activity.
37 *
Nick Pelly8ce7a272012-03-21 15:14:09 -070038 * <p>Uses {@link Application#registerActivityLifecycleCallbacks} to hook
39 * into activity life-cycle events such as onPause() and onResume().
Nick Pellyc84c89a2011-08-22 22:27:11 -070040 *
41 * @hide
42 */
Martijn Coenen5b1e0322013-09-02 20:38:47 -070043public final class NfcActivityManager extends IAppCallback.Stub
Nick Pelly8ce7a272012-03-21 15:14:09 -070044 implements Application.ActivityLifecycleCallbacks {
Nick Pellyc84c89a2011-08-22 22:27:11 -070045 static final String TAG = NfcAdapter.TAG;
46 static final Boolean DBG = false;
47
48 final NfcAdapter mAdapter;
Nick Pelly8ce7a272012-03-21 15:14:09 -070049
50 // All objects in the lists are protected by this
51 final List<NfcApplicationState> mApps; // Application(s) that have NFC state. Usually one
52 final List<NfcActivityState> mActivities; // Activities that have NFC state
53
54 /**
55 * NFC State associated with an {@link Application}.
56 */
57 class NfcApplicationState {
58 int refCount = 0;
59 final Application app;
60 public NfcApplicationState(Application app) {
61 this.app = app;
62 }
63 public void register() {
64 refCount++;
65 if (refCount == 1) {
66 this.app.registerActivityLifecycleCallbacks(NfcActivityManager.this);
67 }
68 }
69 public void unregister() {
70 refCount--;
71 if (refCount == 0) {
72 this.app.unregisterActivityLifecycleCallbacks(NfcActivityManager.this);
73 } else if (refCount < 0) {
74 Log.e(TAG, "-ve refcount for " + app);
75 }
76 }
77 }
78
79 NfcApplicationState findAppState(Application app) {
80 for (NfcApplicationState appState : mApps) {
81 if (appState.app == app) {
82 return appState;
83 }
84 }
85 return null;
86 }
87
88 void registerApplication(Application app) {
89 NfcApplicationState appState = findAppState(app);
90 if (appState == null) {
91 appState = new NfcApplicationState(app);
92 mApps.add(appState);
93 }
94 appState.register();
95 }
96
97 void unregisterApplication(Application app) {
98 NfcApplicationState appState = findAppState(app);
99 if (appState == null) {
100 Log.e(TAG, "app was not registered " + app);
101 return;
102 }
103 appState.unregister();
104 }
Nick Pellyc84c89a2011-08-22 22:27:11 -0700105
106 /**
107 * NFC state associated with an {@link Activity}
108 */
109 class NfcActivityState {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700110 boolean resumed = false;
111 Activity activity;
112 NdefMessage ndefMessage = null; // static NDEF message
113 NfcAdapter.CreateNdefMessageCallback ndefMessageCallback = null;
114 NfcAdapter.OnNdefPushCompleteCallback onNdefPushCompleteCallback = null;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700115 NfcAdapter.CreateBeamUrisCallback uriCallback = null;
116 Uri[] uris = null;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800117 int flags = 0;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700118 int readerModeFlags = 0;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700119 NfcAdapter.ReaderCallback readerCallback = null;
120 Bundle readerModeExtras = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700121 Binder token;
122
Nick Pelly8ce7a272012-03-21 15:14:09 -0700123 public NfcActivityState(Activity activity) {
124 if (activity.getWindow().isDestroyed()) {
125 throw new IllegalStateException("activity is already destroyed");
126 }
Martijn Coenen20fe5372012-04-05 10:50:05 -0700127 // Check if activity is resumed right now, as we will not
128 // immediately get a callback for that.
129 resumed = activity.isResumed();
130
Nick Pelly8ce7a272012-03-21 15:14:09 -0700131 this.activity = activity;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700132 this.token = new Binder();
Nick Pelly8ce7a272012-03-21 15:14:09 -0700133 registerApplication(activity.getApplication());
134 }
135 public void destroy() {
136 unregisterApplication(activity.getApplication());
137 resumed = false;
138 activity = null;
139 ndefMessage = null;
140 ndefMessageCallback = null;
141 onNdefPushCompleteCallback = null;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700142 uriCallback = null;
143 uris = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700144 readerModeFlags = 0;
145 token = null;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700146 }
Nick Pellyc84c89a2011-08-22 22:27:11 -0700147 @Override
148 public String toString() {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700149 StringBuilder s = new StringBuilder("[").append(" ");
Nick Pellyc84c89a2011-08-22 22:27:11 -0700150 s.append(ndefMessage).append(" ").append(ndefMessageCallback).append(" ");
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700151 s.append(uriCallback).append(" ");
152 if (uris != null) {
153 for (Uri uri : uris) {
154 s.append(onNdefPushCompleteCallback).append(" ").append(uri).append("]");
155 }
156 }
Nick Pellyc84c89a2011-08-22 22:27:11 -0700157 return s.toString();
158 }
159 }
160
Nick Pelly8ce7a272012-03-21 15:14:09 -0700161 /** find activity state from mActivities */
162 synchronized NfcActivityState findActivityState(Activity activity) {
163 for (NfcActivityState state : mActivities) {
164 if (state.activity == activity) {
165 return state;
166 }
167 }
168 return null;
Nick Pellyc84c89a2011-08-22 22:27:11 -0700169 }
170
Nick Pelly8ce7a272012-03-21 15:14:09 -0700171 /** find or create activity state from mActivities */
172 synchronized NfcActivityState getActivityState(Activity activity) {
173 NfcActivityState state = findActivityState(activity);
174 if (state == null) {
175 state = new NfcActivityState(activity);
176 mActivities.add(state);
Nick Pellyc84c89a2011-08-22 22:27:11 -0700177 }
178 return state;
179 }
180
Nick Pelly8ce7a272012-03-21 15:14:09 -0700181 synchronized NfcActivityState findResumedActivityState() {
182 for (NfcActivityState state : mActivities) {
183 if (state.resumed) {
184 return state;
185 }
186 }
187 return null;
188 }
189
190 synchronized void destroyActivityState(Activity activity) {
191 NfcActivityState activityState = findActivityState(activity);
192 if (activityState != null) {
193 activityState.destroy();
194 mActivities.remove(activityState);
195 }
196 }
197
198 public NfcActivityManager(NfcAdapter adapter) {
199 mAdapter = adapter;
200 mActivities = new LinkedList<NfcActivityState>();
201 mApps = new ArrayList<NfcApplicationState>(1); // Android VM usually has 1 app
Nick Pelly8ce7a272012-03-21 15:14:09 -0700202 }
203
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700204 public void enableReaderMode(Activity activity, ReaderCallback callback, int flags,
205 Bundle extras) {
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700206 boolean isResumed;
207 Binder token;
208 synchronized (NfcActivityManager.this) {
209 NfcActivityState state = getActivityState(activity);
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700210 state.readerCallback = callback;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700211 state.readerModeFlags = flags;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700212 state.readerModeExtras = extras;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700213 token = state.token;
214 isResumed = state.resumed;
215 }
216 if (isResumed) {
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700217 setReaderMode(token, flags, extras);
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700218 }
219 }
220
221 public void disableReaderMode(Activity activity) {
222 boolean isResumed;
223 Binder token;
224 synchronized (NfcActivityManager.this) {
225 NfcActivityState state = getActivityState(activity);
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700226 state.readerCallback = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700227 state.readerModeFlags = 0;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700228 state.readerModeExtras = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700229 token = state.token;
230 isResumed = state.resumed;
231 }
232 if (isResumed) {
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700233 setReaderMode(token, 0, null);
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700234 }
235
236 }
237
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700238 public void setReaderMode(Binder token, int flags, Bundle extras) {
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700239 if (DBG) Log.d(TAG, "Setting reader mode");
240 try {
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700241 NfcAdapter.sService.setReaderMode(token, this, flags, extras);
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700242 } catch (RemoteException e) {
243 mAdapter.attemptDeadServiceRecovery(e);
244 }
245 }
246
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700247 public void setNdefPushContentUri(Activity activity, Uri[] uris) {
Nick Pelly1d7e9062012-04-03 17:46:00 -0700248 boolean isResumed;
249 synchronized (NfcActivityManager.this) {
250 NfcActivityState state = getActivityState(activity);
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700251 state.uris = uris;
252 isResumed = state.resumed;
253 }
254 if (isResumed) {
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800255 // requestNfcServiceCallback() verifies permission also
Martijn Coenen1360c552013-01-07 16:34:20 -0800256 requestNfcServiceCallback();
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800257 } else {
258 // Crash API calls early in case NFC permission is missing
259 verifyNfcPermission();
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700260 }
261 }
262
263
264 public void setNdefPushContentUriCallback(Activity activity,
265 NfcAdapter.CreateBeamUrisCallback callback) {
266 boolean isResumed;
267 synchronized (NfcActivityManager.this) {
268 NfcActivityState state = getActivityState(activity);
269 state.uriCallback = callback;
Nick Pelly1d7e9062012-04-03 17:46:00 -0700270 isResumed = state.resumed;
271 }
272 if (isResumed) {
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800273 // requestNfcServiceCallback() verifies permission also
Martijn Coenen1360c552013-01-07 16:34:20 -0800274 requestNfcServiceCallback();
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800275 } else {
276 // Crash API calls early in case NFC permission is missing
277 verifyNfcPermission();
Nick Pelly1d7e9062012-04-03 17:46:00 -0700278 }
279 }
280
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800281 public void setNdefPushMessage(Activity activity, NdefMessage message, int flags) {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700282 boolean isResumed;
283 synchronized (NfcActivityManager.this) {
284 NfcActivityState state = getActivityState(activity);
285 state.ndefMessage = message;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800286 state.flags = flags;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700287 isResumed = state.resumed;
288 }
289 if (isResumed) {
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800290 // requestNfcServiceCallback() verifies permission also
Martijn Coenen1360c552013-01-07 16:34:20 -0800291 requestNfcServiceCallback();
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800292 } else {
293 // Crash API calls early in case NFC permission is missing
294 verifyNfcPermission();
Nick Pelly8ce7a272012-03-21 15:14:09 -0700295 }
296 }
297
298 public void setNdefPushMessageCallback(Activity activity,
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800299 NfcAdapter.CreateNdefMessageCallback callback, int flags) {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700300 boolean isResumed;
301 synchronized (NfcActivityManager.this) {
302 NfcActivityState state = getActivityState(activity);
303 state.ndefMessageCallback = callback;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800304 state.flags = flags;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700305 isResumed = state.resumed;
306 }
307 if (isResumed) {
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800308 // requestNfcServiceCallback() verifies permission also
Martijn Coenen1360c552013-01-07 16:34:20 -0800309 requestNfcServiceCallback();
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800310 } else {
311 // Crash API calls early in case NFC permission is missing
312 verifyNfcPermission();
Nick Pelly8ce7a272012-03-21 15:14:09 -0700313 }
314 }
315
316 public void setOnNdefPushCompleteCallback(Activity activity,
317 NfcAdapter.OnNdefPushCompleteCallback callback) {
318 boolean isResumed;
319 synchronized (NfcActivityManager.this) {
320 NfcActivityState state = getActivityState(activity);
321 state.onNdefPushCompleteCallback = callback;
322 isResumed = state.resumed;
323 }
324 if (isResumed) {
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800325 // requestNfcServiceCallback() verifies permission also
Martijn Coenen1360c552013-01-07 16:34:20 -0800326 requestNfcServiceCallback();
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800327 } else {
328 // Crash API calls early in case NFC permission is missing
329 verifyNfcPermission();
Nick Pellyc84c89a2011-08-22 22:27:11 -0700330 }
331 }
332
333 /**
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700334 * Request or unrequest NFC service callbacks.
Nick Pelly8ce7a272012-03-21 15:14:09 -0700335 * Makes IPC call - do not hold lock.
Nick Pellyc84c89a2011-08-22 22:27:11 -0700336 */
Martijn Coenen1360c552013-01-07 16:34:20 -0800337 void requestNfcServiceCallback() {
Nick Pellyc84c89a2011-08-22 22:27:11 -0700338 try {
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700339 NfcAdapter.sService.setAppCallback(this);
Nick Pellyc84c89a2011-08-22 22:27:11 -0700340 } catch (RemoteException e) {
341 mAdapter.attemptDeadServiceRecovery(e);
342 }
343 }
344
Martijn Coenend8bcfba2014-11-13 15:00:56 -0800345 void verifyNfcPermission() {
346 try {
347 NfcAdapter.sService.verifyNfcPermission();
348 } catch (RemoteException e) {
349 mAdapter.attemptDeadServiceRecovery(e);
350 }
351 }
352
Nick Pelly8ce7a272012-03-21 15:14:09 -0700353 /** Callback from NFC service, usually on binder thread */
Nick Pellyc84c89a2011-08-22 22:27:11 -0700354 @Override
Martijn Coenenfd70bb12015-04-14 11:38:21 +0200355 public BeamShareData createBeamShareData(byte peerLlcpVersion) {
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800356 NfcAdapter.CreateNdefMessageCallback ndefCallback;
357 NfcAdapter.CreateBeamUrisCallback urisCallback;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700358 NdefMessage message;
Martijn Coenen7fe9fa12014-01-29 17:28:04 -0800359 Activity activity;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700360 Uri[] uris;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800361 int flags;
Martijn Coenenfd70bb12015-04-14 11:38:21 +0200362 NfcEvent event = new NfcEvent(mAdapter, peerLlcpVersion);
Nick Pelly1d7e9062012-04-03 17:46:00 -0700363 synchronized (NfcActivityManager.this) {
364 NfcActivityState state = findResumedActivityState();
365 if (state == null) return null;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800366
367 ndefCallback = state.ndefMessageCallback;
368 urisCallback = state.uriCallback;
369 message = state.ndefMessage;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700370 uris = state.uris;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800371 flags = state.flags;
Martijn Coenen7fe9fa12014-01-29 17:28:04 -0800372 activity = state.activity;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700373 }
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800374
375 // Make callbacks without lock
376 if (ndefCallback != null) {
Martijn Coenenfd70bb12015-04-14 11:38:21 +0200377 message = ndefCallback.createNdefMessage(event);
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800378 }
379 if (urisCallback != null) {
Martijn Coenenfd70bb12015-04-14 11:38:21 +0200380 uris = urisCallback.createBeamUris(event);
Martijn Coenen2c103112012-05-15 10:32:15 -0700381 if (uris != null) {
Andres Morales56f299b2014-10-31 08:26:33 -0700382 ArrayList<Uri> validUris = new ArrayList<Uri>();
Martijn Coenen2c103112012-05-15 10:32:15 -0700383 for (Uri uri : uris) {
384 if (uri == null) {
385 Log.e(TAG, "Uri not allowed to be null.");
Andres Morales56f299b2014-10-31 08:26:33 -0700386 continue;
Martijn Coenen2c103112012-05-15 10:32:15 -0700387 }
388 String scheme = uri.getScheme();
389 if (scheme == null || (!scheme.equalsIgnoreCase("file") &&
390 !scheme.equalsIgnoreCase("content"))) {
391 Log.e(TAG, "Uri needs to have " +
392 "either scheme file or scheme content");
Andres Morales56f299b2014-10-31 08:26:33 -0700393 continue;
Martijn Coenen2c103112012-05-15 10:32:15 -0700394 }
Andres Morales56f299b2014-10-31 08:26:33 -0700395 uri = ContentProvider.maybeAddUserId(uri, UserHandle.myUserId());
396 validUris.add(uri);
Martijn Coenen2c103112012-05-15 10:32:15 -0700397 }
Andres Morales56f299b2014-10-31 08:26:33 -0700398
399 uris = validUris.toArray(new Uri[validUris.size()]);
Martijn Coenen2c103112012-05-15 10:32:15 -0700400 }
Nick Pelly1d7e9062012-04-03 17:46:00 -0700401 }
Martijn Coenen7fe9fa12014-01-29 17:28:04 -0800402 if (uris != null && uris.length > 0) {
403 for (Uri uri : uris) {
404 // Grant the NFC process permission to read these URIs
405 activity.grantUriPermission("com.android.nfc", uri,
406 Intent.FLAG_GRANT_READ_URI_PERMISSION);
407 }
408 }
Andres Morales56f299b2014-10-31 08:26:33 -0700409 return new BeamShareData(message, uris, UserHandle.CURRENT, flags);
Nick Pelly1d7e9062012-04-03 17:46:00 -0700410 }
Nick Pelly1d7e9062012-04-03 17:46:00 -0700411
Nick Pelly1d7e9062012-04-03 17:46:00 -0700412 /** Callback from NFC service, usually on binder thread */
413 @Override
Martijn Coenenfd70bb12015-04-14 11:38:21 +0200414 public void onNdefPushComplete(byte peerLlcpVersion) {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700415 NfcAdapter.OnNdefPushCompleteCallback callback;
Nick Pellyc84c89a2011-08-22 22:27:11 -0700416 synchronized (NfcActivityManager.this) {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700417 NfcActivityState state = findResumedActivityState();
418 if (state == null) return;
419
420 callback = state.onNdefPushCompleteCallback;
Nick Pellyc84c89a2011-08-22 22:27:11 -0700421 }
Martijn Coenenfd70bb12015-04-14 11:38:21 +0200422 NfcEvent event = new NfcEvent(mAdapter, peerLlcpVersion);
Nick Pelly8ce7a272012-03-21 15:14:09 -0700423 // Make callback without lock
Nick Pellyc84c89a2011-08-22 22:27:11 -0700424 if (callback != null) {
Martijn Coenenfd70bb12015-04-14 11:38:21 +0200425 callback.onNdefPushComplete(event);
Nick Pellyc84c89a2011-08-22 22:27:11 -0700426 }
427 }
Martijn Coenen3433a8a2011-09-01 19:18:02 -0700428
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700429 @Override
430 public void onTagDiscovered(Tag tag) throws RemoteException {
431 NfcAdapter.ReaderCallback callback;
432 synchronized (NfcActivityManager.this) {
433 NfcActivityState state = findResumedActivityState();
434 if (state == null) return;
435
436 callback = state.readerCallback;
437 }
438
439 // Make callback without lock
440 if (callback != null) {
441 callback.onTagDiscovered(tag);
442 }
443
444 }
Nick Pelly8ce7a272012-03-21 15:14:09 -0700445 /** Callback from Activity life-cycle, on main thread */
446 @Override
447 public void onActivityCreated(Activity activity, Bundle savedInstanceState) { /* NO-OP */ }
448
449 /** Callback from Activity life-cycle, on main thread */
450 @Override
451 public void onActivityStarted(Activity activity) { /* NO-OP */ }
452
453 /** Callback from Activity life-cycle, on main thread */
454 @Override
455 public void onActivityResumed(Activity activity) {
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700456 int readerModeFlags = 0;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700457 Bundle readerModeExtras = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700458 Binder token;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700459 synchronized (NfcActivityManager.this) {
460 NfcActivityState state = findActivityState(activity);
461 if (DBG) Log.d(TAG, "onResume() for " + activity + " " + state);
462 if (state == null) return;
463 state.resumed = true;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700464 token = state.token;
465 readerModeFlags = state.readerModeFlags;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700466 readerModeExtras = state.readerModeExtras;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700467 }
468 if (readerModeFlags != 0) {
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700469 setReaderMode(token, readerModeFlags, readerModeExtras);
Nick Pelly8ce7a272012-03-21 15:14:09 -0700470 }
Martijn Coenen1360c552013-01-07 16:34:20 -0800471 requestNfcServiceCallback();
Nick Pelly8ce7a272012-03-21 15:14:09 -0700472 }
473
474 /** Callback from Activity life-cycle, on main thread */
475 @Override
476 public void onActivityPaused(Activity activity) {
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700477 boolean readerModeFlagsSet;
478 Binder token;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700479 synchronized (NfcActivityManager.this) {
480 NfcActivityState state = findActivityState(activity);
481 if (DBG) Log.d(TAG, "onPause() for " + activity + " " + state);
482 if (state == null) return;
483 state.resumed = false;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700484 token = state.token;
485 readerModeFlagsSet = state.readerModeFlags != 0;
486 }
487 if (readerModeFlagsSet) {
488 // Restore default p2p modes
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700489 setReaderMode(token, 0, null);
Nick Pelly8ce7a272012-03-21 15:14:09 -0700490 }
Nick Pelly8ce7a272012-03-21 15:14:09 -0700491 }
492
493 /** Callback from Activity life-cycle, on main thread */
494 @Override
495 public void onActivityStopped(Activity activity) { /* NO-OP */ }
496
497 /** Callback from Activity life-cycle, on main thread */
498 @Override
499 public void onActivitySaveInstanceState(Activity activity, Bundle outState) { /* NO-OP */ }
500
501 /** Callback from Activity life-cycle, on main thread */
502 @Override
503 public void onActivityDestroyed(Activity activity) {
504 synchronized (NfcActivityManager.this) {
505 NfcActivityState state = findActivityState(activity);
506 if (DBG) Log.d(TAG, "onDestroy() for " + activity + " " + state);
507 if (state != null) {
508 // release all associated references
509 destroyActivityState(activity);
510 }
511 }
512 }
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700513
Nick Pellyc84c89a2011-08-22 22:27:11 -0700514}