Android:在NDEF_DISCOVERED操作上注册的活动将被忽略

时间:2012-01-06 15:11:35

标签: android android-intent nfc android-activity

我正在开发一款能够从NFC标签中读取和处理特定URI的应用。我在NDEF_DISCOVERED上注册了一个“读者”活动( A ),它从标签中读取数据,然后启动一个“数据处理”活动( B )数据

目前我有三个标签,每个标签都有不同的URI,更具体地说是具有相同的架构和路径,但具有不同的查询数据 - > tagID:

T-1: mySchema://gman.com/path ?id = T-1
T-2: mySchema://gman.com/path ?id = T-2
T-3: mySchema://gman.com/path ?id = T-3

清单:

   <activity
        android:label="@string/reader_nfc"
        android:name=".reader.nfc.NfcReaderActivity"
        android:stateNotNeeded="true" >
        <intent-filter>
            <action android:name="android.nfc.action.NDEF_DISCOVERED" />
            <category android:name="android.intent.category.DEFAULT" />
            <data android:scheme="mySchema" />
        </intent-filter>
    </activity>
    <activity
        android:label="@string/data_manager_name"
        android:name=".data.handlers.DataHandlerActivity" >
    </activity>

所以,解决问题。当我从第一个标签读取数据时,例如T-1,读取器活动通常在生命周期内进行,并启动执行其工作并显示正确输出的数据处理活动。当我从下一个标签(T-2或T-3)读取时会发生同样的事情,但是当我返回到第一个标签时,我得到了从上次扫描的标签生成的输出。

日志显示如下:

ActivityManager 使用正确的数据(来自T-1)记录意图的开始,但是活动A的生命周期没有开始,而是活动B重新启动,而前一个意图的数据是接收和处理(通过在活动B中调用getIntent()。getData()。

在T-2和T-3之间切换时,一切正常。

如果有人解释我发生了什么,我真的很感激。我在设置singleTask启动模式时看到了类似的行为,但我没有使用它。

我正在使用API​​ v.2.3.3开发,使用Android版本2.3.6在Nexus-S上进行测试

日Thnx!

=============================================== ===================================

编辑:我找到了符合我需求的问题解决方案,但我还有一个问题。

我专注于读者活动,并评论了处理和其他正在发生的事情。这是代码snipet:

public class NfcReaderActivity extends Activity {

private static final String TAG = "NfcReaderActivity";

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    Log.d(TAG, "onCreate");
    setContentView(R.layout.nfc_reader);
}

@Override
protected void onStart() {
    super.onStart();
    Log.d(TAG, "onStart");

    readAndHandleData();
}

protected void readAndHandleData() {
    NdefMessage[] srcObj = readSource();

    if (srcObj != null) {
        Uri srcData = getSrcData(srcObj);
        launchSourceManagerActivity(srcData);
    } else {
        Log.w(TAG, "srcObj was null!");
    }
}

public NdefMessage[] readSource() {

    Parcelable[] rawMsgs = getIntent().getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES);
    NdefMessage[] ndefMsgs = null;
    // store NdefMessage-s from rawMsgs in ndefMsgs
    return ndefMsgs ;
}

public void launchSourceManagerActivity(Uri srcData) {
    // launches DataHandlerActivity with srcData
}

public Uri getSrcData(NdefMessage[] src) {
    // returns the data from the tag rapresented as Uri
}

}

执行此操作后,我得到了一些额外的日志(不知道原因,但我想这并不重要),并且看到当我返回第一个标签时,活动重新启动(onRestart()是在另外两种情况下,当扫描第二个和第三个标签时,重新创建活动(调用onCreate())。

当调用onRestart()并从intent(readSource方法)检索数据时,getIntent()方法返回扫描前一个标记时收到的相同意图。

我刚刚开始在Android上开发,我对这些概念不是很熟悉,所以这可能是这里的核心问题;)。我试图解决这个问题,但我无法得到合乎逻辑的解释。 如果有人能在这里向我解释工作流程,我将非常感激。

然而,这就是我解决问题的方法......因为读者活动可以作为单身人士我将启动模式设置为singleTask

<activity
        android:label="@string/reader_nfc"
        android:name=".reader.nfc.NfcReaderActivity"
        android:stateNotNeeded="true"
        android:launchMode="singleTask"  >

并在NfcReaderActivity中完成以下更改:

public class NfcReaderActivity extends Activity {

private static final String TAG = "NfcReaderActivity";

/**
 * override onNewIntent method and store the new intent as the current intent
 */
@Override
protected void onNewIntent(Intent intent) {
    super.onNewIntent(intent);
    Log.d(TAG, "onNewIntent");
    // set the intent as the current intent, so new data (EXTRA_NDEF_MESSAGES) can
 //be accessed when calling getIntent() in readSource method
    setIntent(intent);
}

这对我来说很好,但我仍然想了解究竟发生了什么,所以欢迎任何有用的(当然;))评论。

1 个答案:

答案 0 :(得分:1)

您可能想要了解活动生命周期和堆栈:

http://developer.android.com/guide/topics/fundamentals/tasks-and-back-stack.html