blob: 73090549cb8edb26d90517c5dc6fdab1eff56276 [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;
Martijn Coenen7fe9fa12014-01-29 17:28:04 -080021import android.content.Intent;
Nick Pelly1d7e9062012-04-03 17:46:00 -070022import android.net.Uri;
Martijn Coenen5b1e0322013-09-02 20:38:47 -070023import android.nfc.NfcAdapter.ReaderCallback;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -070024import android.os.Binder;
Nick Pelly8ce7a272012-03-21 15:14:09 -070025import android.os.Bundle;
Nick Pellyc84c89a2011-08-22 22:27:11 -070026import android.os.RemoteException;
27import android.util.Log;
28
Nick Pelly8ce7a272012-03-21 15:14:09 -070029import java.util.ArrayList;
30import java.util.LinkedList;
31import java.util.List;
Nick Pellyc84c89a2011-08-22 22:27:11 -070032
33/**
34 * Manages NFC API's that are coupled to the life-cycle of an Activity.
35 *
Nick Pelly8ce7a272012-03-21 15:14:09 -070036 * <p>Uses {@link Application#registerActivityLifecycleCallbacks} to hook
37 * into activity life-cycle events such as onPause() and onResume().
Nick Pellyc84c89a2011-08-22 22:27:11 -070038 *
39 * @hide
40 */
Martijn Coenen5b1e0322013-09-02 20:38:47 -070041public final class NfcActivityManager extends IAppCallback.Stub
Nick Pelly8ce7a272012-03-21 15:14:09 -070042 implements Application.ActivityLifecycleCallbacks {
Nick Pellyc84c89a2011-08-22 22:27:11 -070043 static final String TAG = NfcAdapter.TAG;
44 static final Boolean DBG = false;
45
46 final NfcAdapter mAdapter;
Nick Pelly8ce7a272012-03-21 15:14:09 -070047 final NfcEvent mDefaultEvent; // cached NfcEvent (its currently always the same)
48
49 // All objects in the lists are protected by this
50 final List<NfcApplicationState> mApps; // Application(s) that have NFC state. Usually one
51 final List<NfcActivityState> mActivities; // Activities that have NFC state
52
53 /**
54 * NFC State associated with an {@link Application}.
55 */
56 class NfcApplicationState {
57 int refCount = 0;
58 final Application app;
59 public NfcApplicationState(Application app) {
60 this.app = app;
61 }
62 public void register() {
63 refCount++;
64 if (refCount == 1) {
65 this.app.registerActivityLifecycleCallbacks(NfcActivityManager.this);
66 }
67 }
68 public void unregister() {
69 refCount--;
70 if (refCount == 0) {
71 this.app.unregisterActivityLifecycleCallbacks(NfcActivityManager.this);
72 } else if (refCount < 0) {
73 Log.e(TAG, "-ve refcount for " + app);
74 }
75 }
76 }
77
78 NfcApplicationState findAppState(Application app) {
79 for (NfcApplicationState appState : mApps) {
80 if (appState.app == app) {
81 return appState;
82 }
83 }
84 return null;
85 }
86
87 void registerApplication(Application app) {
88 NfcApplicationState appState = findAppState(app);
89 if (appState == null) {
90 appState = new NfcApplicationState(app);
91 mApps.add(appState);
92 }
93 appState.register();
94 }
95
96 void unregisterApplication(Application app) {
97 NfcApplicationState appState = findAppState(app);
98 if (appState == null) {
99 Log.e(TAG, "app was not registered " + app);
100 return;
101 }
102 appState.unregister();
103 }
Nick Pellyc84c89a2011-08-22 22:27:11 -0700104
105 /**
106 * NFC state associated with an {@link Activity}
107 */
108 class NfcActivityState {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700109 boolean resumed = false;
110 Activity activity;
111 NdefMessage ndefMessage = null; // static NDEF message
112 NfcAdapter.CreateNdefMessageCallback ndefMessageCallback = null;
113 NfcAdapter.OnNdefPushCompleteCallback onNdefPushCompleteCallback = null;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700114 NfcAdapter.CreateBeamUrisCallback uriCallback = null;
115 Uri[] uris = null;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800116 int flags = 0;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700117 int readerModeFlags = 0;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700118 NfcAdapter.ReaderCallback readerCallback = null;
119 Bundle readerModeExtras = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700120 Binder token;
121
Nick Pelly8ce7a272012-03-21 15:14:09 -0700122 public NfcActivityState(Activity activity) {
123 if (activity.getWindow().isDestroyed()) {
124 throw new IllegalStateException("activity is already destroyed");
125 }
Martijn Coenen20fe5372012-04-05 10:50:05 -0700126 // Check if activity is resumed right now, as we will not
127 // immediately get a callback for that.
128 resumed = activity.isResumed();
129
Nick Pelly8ce7a272012-03-21 15:14:09 -0700130 this.activity = activity;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700131 this.token = new Binder();
Nick Pelly8ce7a272012-03-21 15:14:09 -0700132 registerApplication(activity.getApplication());
133 }
134 public void destroy() {
135 unregisterApplication(activity.getApplication());
136 resumed = false;
137 activity = null;
138 ndefMessage = null;
139 ndefMessageCallback = null;
140 onNdefPushCompleteCallback = null;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700141 uriCallback = null;
142 uris = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700143 readerModeFlags = 0;
144 token = null;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700145 }
Nick Pellyc84c89a2011-08-22 22:27:11 -0700146 @Override
147 public String toString() {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700148 StringBuilder s = new StringBuilder("[").append(" ");
Nick Pellyc84c89a2011-08-22 22:27:11 -0700149 s.append(ndefMessage).append(" ").append(ndefMessageCallback).append(" ");
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700150 s.append(uriCallback).append(" ");
151 if (uris != null) {
152 for (Uri uri : uris) {
153 s.append(onNdefPushCompleteCallback).append(" ").append(uri).append("]");
154 }
155 }
Nick Pellyc84c89a2011-08-22 22:27:11 -0700156 return s.toString();
157 }
158 }
159
Nick Pelly8ce7a272012-03-21 15:14:09 -0700160 /** find activity state from mActivities */
161 synchronized NfcActivityState findActivityState(Activity activity) {
162 for (NfcActivityState state : mActivities) {
163 if (state.activity == activity) {
164 return state;
165 }
166 }
167 return null;
Nick Pellyc84c89a2011-08-22 22:27:11 -0700168 }
169
Nick Pelly8ce7a272012-03-21 15:14:09 -0700170 /** find or create activity state from mActivities */
171 synchronized NfcActivityState getActivityState(Activity activity) {
172 NfcActivityState state = findActivityState(activity);
173 if (state == null) {
174 state = new NfcActivityState(activity);
175 mActivities.add(state);
Nick Pellyc84c89a2011-08-22 22:27:11 -0700176 }
177 return state;
178 }
179
Nick Pelly8ce7a272012-03-21 15:14:09 -0700180 synchronized NfcActivityState findResumedActivityState() {
181 for (NfcActivityState state : mActivities) {
182 if (state.resumed) {
183 return state;
184 }
185 }
186 return null;
187 }
188
189 synchronized void destroyActivityState(Activity activity) {
190 NfcActivityState activityState = findActivityState(activity);
191 if (activityState != null) {
192 activityState.destroy();
193 mActivities.remove(activityState);
194 }
195 }
196
197 public NfcActivityManager(NfcAdapter adapter) {
198 mAdapter = adapter;
199 mActivities = new LinkedList<NfcActivityState>();
200 mApps = new ArrayList<NfcApplicationState>(1); // Android VM usually has 1 app
201 mDefaultEvent = new NfcEvent(mAdapter);
202 }
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 Coenen1fa2aff2013-02-27 09:21:22 -0800355 public BeamShareData createBeamShareData() {
356 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;
Nick Pelly1d7e9062012-04-03 17:46:00 -0700362 synchronized (NfcActivityManager.this) {
363 NfcActivityState state = findResumedActivityState();
364 if (state == null) return null;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800365
366 ndefCallback = state.ndefMessageCallback;
367 urisCallback = state.uriCallback;
368 message = state.ndefMessage;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700369 uris = state.uris;
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800370 flags = state.flags;
Martijn Coenen7fe9fa12014-01-29 17:28:04 -0800371 activity = state.activity;
Martijn Coenen20e8dd92012-04-12 16:37:18 -0700372 }
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800373
374 // Make callbacks without lock
375 if (ndefCallback != null) {
376 message = ndefCallback.createNdefMessage(mDefaultEvent);
377 }
378 if (urisCallback != null) {
379 uris = urisCallback.createBeamUris(mDefaultEvent);
Martijn Coenen2c103112012-05-15 10:32:15 -0700380 if (uris != null) {
381 for (Uri uri : uris) {
382 if (uri == null) {
383 Log.e(TAG, "Uri not allowed to be null.");
384 return null;
385 }
386 String scheme = uri.getScheme();
387 if (scheme == null || (!scheme.equalsIgnoreCase("file") &&
388 !scheme.equalsIgnoreCase("content"))) {
389 Log.e(TAG, "Uri needs to have " +
390 "either scheme file or scheme content");
391 return null;
392 }
393 }
394 }
Nick Pelly1d7e9062012-04-03 17:46:00 -0700395 }
Martijn Coenen7fe9fa12014-01-29 17:28:04 -0800396 if (uris != null && uris.length > 0) {
397 for (Uri uri : uris) {
398 // Grant the NFC process permission to read these URIs
399 activity.grantUriPermission("com.android.nfc", uri,
400 Intent.FLAG_GRANT_READ_URI_PERMISSION);
401 }
402 }
Martijn Coenen1fa2aff2013-02-27 09:21:22 -0800403 return new BeamShareData(message, uris, flags);
Nick Pelly1d7e9062012-04-03 17:46:00 -0700404 }
Nick Pelly1d7e9062012-04-03 17:46:00 -0700405
Nick Pelly1d7e9062012-04-03 17:46:00 -0700406 /** Callback from NFC service, usually on binder thread */
407 @Override
Nick Pellyc84c89a2011-08-22 22:27:11 -0700408 public void onNdefPushComplete() {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700409 NfcAdapter.OnNdefPushCompleteCallback callback;
Nick Pellyc84c89a2011-08-22 22:27:11 -0700410 synchronized (NfcActivityManager.this) {
Nick Pelly8ce7a272012-03-21 15:14:09 -0700411 NfcActivityState state = findResumedActivityState();
412 if (state == null) return;
413
414 callback = state.onNdefPushCompleteCallback;
Nick Pellyc84c89a2011-08-22 22:27:11 -0700415 }
416
Nick Pelly8ce7a272012-03-21 15:14:09 -0700417 // Make callback without lock
Nick Pellyc84c89a2011-08-22 22:27:11 -0700418 if (callback != null) {
419 callback.onNdefPushComplete(mDefaultEvent);
420 }
421 }
Martijn Coenen3433a8a2011-09-01 19:18:02 -0700422
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700423 @Override
424 public void onTagDiscovered(Tag tag) throws RemoteException {
425 NfcAdapter.ReaderCallback callback;
426 synchronized (NfcActivityManager.this) {
427 NfcActivityState state = findResumedActivityState();
428 if (state == null) return;
429
430 callback = state.readerCallback;
431 }
432
433 // Make callback without lock
434 if (callback != null) {
435 callback.onTagDiscovered(tag);
436 }
437
438 }
Nick Pelly8ce7a272012-03-21 15:14:09 -0700439 /** Callback from Activity life-cycle, on main thread */
440 @Override
441 public void onActivityCreated(Activity activity, Bundle savedInstanceState) { /* NO-OP */ }
442
443 /** Callback from Activity life-cycle, on main thread */
444 @Override
445 public void onActivityStarted(Activity activity) { /* NO-OP */ }
446
447 /** Callback from Activity life-cycle, on main thread */
448 @Override
449 public void onActivityResumed(Activity activity) {
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700450 int readerModeFlags = 0;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700451 Bundle readerModeExtras = null;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700452 Binder token;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700453 synchronized (NfcActivityManager.this) {
454 NfcActivityState state = findActivityState(activity);
455 if (DBG) Log.d(TAG, "onResume() for " + activity + " " + state);
456 if (state == null) return;
457 state.resumed = true;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700458 token = state.token;
459 readerModeFlags = state.readerModeFlags;
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700460 readerModeExtras = state.readerModeExtras;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700461 }
462 if (readerModeFlags != 0) {
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700463 setReaderMode(token, readerModeFlags, readerModeExtras);
Nick Pelly8ce7a272012-03-21 15:14:09 -0700464 }
Martijn Coenen1360c552013-01-07 16:34:20 -0800465 requestNfcServiceCallback();
Nick Pelly8ce7a272012-03-21 15:14:09 -0700466 }
467
468 /** Callback from Activity life-cycle, on main thread */
469 @Override
470 public void onActivityPaused(Activity activity) {
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700471 boolean readerModeFlagsSet;
472 Binder token;
Nick Pelly8ce7a272012-03-21 15:14:09 -0700473 synchronized (NfcActivityManager.this) {
474 NfcActivityState state = findActivityState(activity);
475 if (DBG) Log.d(TAG, "onPause() for " + activity + " " + state);
476 if (state == null) return;
477 state.resumed = false;
Martijn Coenenc20ed2f2013-08-27 14:32:53 -0700478 token = state.token;
479 readerModeFlagsSet = state.readerModeFlags != 0;
480 }
481 if (readerModeFlagsSet) {
482 // Restore default p2p modes
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700483 setReaderMode(token, 0, null);
Nick Pelly8ce7a272012-03-21 15:14:09 -0700484 }
Nick Pelly8ce7a272012-03-21 15:14:09 -0700485 }
486
487 /** Callback from Activity life-cycle, on main thread */
488 @Override
489 public void onActivityStopped(Activity activity) { /* NO-OP */ }
490
491 /** Callback from Activity life-cycle, on main thread */
492 @Override
493 public void onActivitySaveInstanceState(Activity activity, Bundle outState) { /* NO-OP */ }
494
495 /** Callback from Activity life-cycle, on main thread */
496 @Override
497 public void onActivityDestroyed(Activity activity) {
498 synchronized (NfcActivityManager.this) {
499 NfcActivityState state = findActivityState(activity);
500 if (DBG) Log.d(TAG, "onDestroy() for " + activity + " " + state);
501 if (state != null) {
502 // release all associated references
503 destroyActivityState(activity);
504 }
505 }
506 }
Martijn Coenen5b1e0322013-09-02 20:38:47 -0700507
Nick Pellyc84c89a2011-08-22 22:27:11 -0700508}