У меня есть приложение, которое запускается в режиме киоска и должно читать и реагировать на NFCTags. Он использует enableReaderMode
на NFCAdapter
в onResume
, чтобы начать их чтение. Все работает нормально, если приложение, например, (повторно) запущено во время разработки. Однако, если я перезагружаю устройство (и действие запускается автоматически), то действие только иногда переводится в правильный режим, но часто только воспроизводит системный звук NF C, а мой handleTag
не вызывается.
Из того, что я зарегистрировал, код установки NFCAdapter, который у меня есть, правильно вызывается при любых обстоятельствах
Я также пытался enableForegroundDispatch
, но эффект тот же. Я также пытался периодически вспоминать enableReaderMode
, но это также имеет тот же эффект.
У кого-нибудь есть идеи, что происходит?
Обновление
I я вижу это сообщение об ошибке в журналах, когда я пытаюсь установить режим считывателя в тех случаях, когда он выходит из строя
NfcService: setReaderMode: Caller is not in foreground and is not system process.
Несмотря на то, что активность отчетливо видна в забвении.
Телефон такое Google Pixel 3
Приложение является владельцем устройства через
adb shell dpm set-device-owner ...
Манифест приложения
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme"
android:testOnly="true">
<!-- snip DeviceAdminReceiver -->
<activity
android:name=".FullscreenActivity"
android:screenOrientation="reverseLandscape"
android:configChanges="orientation|keyboardHidden|screenSize"
android:label="@string/app_name"
android:theme="@style/FullscreenTheme">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.HOME" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
<uses-permission android:name="android.permission.NFC" />
<uses-feature android:name="android.hardware.nfc" />
FullscreenActivity, которая должна обрабатывать метку NF C
public class FullscreenActivity extends AppCompatActivity {
NfcAdapter mAdapter;
private DevicePolicyManager mDevicePolicyManager;
private ComponentName mAdminComponentName;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mDevicePolicyManager = (DevicePolicyManager) getSystemService(
Context.DEVICE_POLICY_SERVICE);
if (mDevicePolicyManager.isDeviceOwnerApp(getPackageName())) {
mAdminComponentName = MyDeviceAdminReceiver.getComponentName(this);
IntentFilter intentFilter = new IntentFilter(Intent.ACTION_MAIN);
intentFilter.addCategory(Intent.CATEGORY_HOME);
intentFilter.addCategory(Intent.CATEGORY_DEFAULT);
mDevicePolicyManager.addPersistentPreferredActivity(
mAdminComponentName, intentFilter,
new ComponentName(getPackageName(),
FullscreenActivity.class.getName()));
mDevicePolicyManager.setLockTaskPackages(mAdminComponentName,
new String[]{getPackageName()});
mDevicePolicyManager.setKeyguardDisabled(mAdminComponentName, true);
}
startLockTask();
}
@Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
if (hasFocus) {
setFullscreenFlags();
}
}
private void setFullscreenFlags() {
getWindow().getDecorView()
.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LOW_PROFILE
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| View.SYSTEM_UI_FLAG_FULLSCREEN
| View.SYSTEM_UI_FLAG_LAYOUT_STABLE
| View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
| View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_HIDE_NAVIGATION);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
}
@Override
protected void onResume() {
super.onResume();
setFullscreenFlags();
mAdapter = NfcAdapter.getDefaultAdapter(this);
setupNfcAdapter();
}
private void setupNfcAdapter() {
if (mAdapter == null) return;
Bundle options = new Bundle();
// No sure this is needed
options.putInt(NfcAdapter.EXTRA_READER_PRESENCE_CHECK_DELAY, 50000);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0,
new Intent(this, getClass())
.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);
mAdapter.enableReaderMode(this, this::handleTag,
NfcAdapter.FLAG_READER_NO_PLATFORM_SOUNDS |
NfcAdapter.FLAG_READER_NFC_A |
NfcAdapter.FLAG_READER_NFC_B |
NfcAdapter.FLAG_READER_NFC_F |
NfcAdapter.FLAG_READER_NFC_V, options);
}
@Override
protected void onPause() {
super.onPause();
if (mAdapter != null) {
mAdapter.disableReaderMode(this);
}
}
private void handleTag(Tag tag) {
Log.d("NFCADAPTER", "tag detected");
}
}