当前位置: 首页 > 知识库问答 >
问题:

是否可以通过意图在活动之间传递URL?

熊烨
2023-03-14

我正在开发一个Android应用程序,它读取NFC标签,检索NDEF消息,然后将其传递给WebView activity以显示那个URL网站。我正在检查Logcat,并且正在读取URL,但我认为URL没有被传递,因为我得到以下错误:

Attempt to cast generated internal exception:
    java.lang.ClassCastException: android.os.Parcelable[] cannot be cast to java.lang.String

这是主要活动:

class MainActivity : AppCompatActivity() {
    // NFC adapter for checking NFC state in the device
    private var nfcAdapter: NfcAdapter? = null

    // Pending intent for NFC intent foreground dispatch.
    // Used to read all NDEF tags while the app is running in the foreground.
    private var nfcPendingIntent: PendingIntent? = null
    // Optional: filter NDEF tags this app receives through the pending intent.
    //private var nfcIntentFilters: Array<IntentFilter>? = null

    private val KEY_LOG_TEXT = "logText"

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        // Restore saved text if available
        if (savedInstanceState != null) {
            dahcor.text = savedInstanceState.getCharSequence(KEY_LOG_TEXT)
        }

        // Check if NFC is supported and enabled
        nfcAdapter = NfcAdapter.getDefaultAdapter(this)
        Log.i("NFC supported", (nfcAdapter != null).toString())
        Log.i("NFC enabled", (nfcAdapter?.isEnabled).toString())


        // Read all tags when app is running and in the foreground
        // Create a generic PendingIntent that will be deliver to this activity. The NFC stack
        // will fill in the intent with the details of the discovered tag before delivering to
        // this activity.
        nfcPendingIntent = PendingIntent.getActivity(this, 0,
                Intent(this, javaClass).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0)

        // Optional: Setup an intent filter from code for a specific NDEF intent
        // Use this code if you are only interested in a specific intent and don't want to
        // interfere with other NFC tags.
        // In this example, the code is commented out so that we get all NDEF messages,
        // in order to analyze different NDEF-formatted NFC tag contents.
        //val ndef = IntentFilter(NfcAdapter.ACTION_NDEF_DISCOVERED)
        //ndef.addCategory(Intent.CATEGORY_DEFAULT)
        //ndef.addDataScheme("https")
        //ndef.addDataAuthority("*.andreasjakl.com", null)
        //ndef.addDataPath("/", PatternMatcher.PATTERN_PREFIX)
        // More information: https://stackoverflow.com/questions/30642465/nfc-tag-is-not-discovered-for-action-ndef-discovered-action-even-if-it-contains
        //nfcIntentFilters = arrayOf(ndef)

        if (intent != null) {
            // Check if the app was started via an NDEF intent
            Log.i("Found intent in onCreate", intent.action.toString())
            processIntent(intent)
        }

        // Make sure the text view is scrolled down so that the latest messages are visible
    }

    override fun onResume() {
        super.onResume()
        // Get all NDEF discovered intents
        // Makes sure the app gets all discovered NDEF messages as long as it's in the foreground.
        nfcAdapter?.enableForegroundDispatch(this, nfcPendingIntent, null, null);
        // Alternative: only get specific HTTP NDEF intent
        //nfcAdapter?.enableForegroundDispatch(this, nfcPendingIntent, nfcIntentFilters, null);
    }

    override fun onPause() {
        super.onPause()
        // Disable foreground dispatch, as this activity is no longer in the foreground
        nfcAdapter?.disableForegroundDispatch(this);
    }

    override fun onNewIntent(intent: Intent?) {
        super.onNewIntent(intent)
        Log.i("Found intent in onNewIntent", intent?.action.toString())
        // If we got an intent while the app is running, also check if it's a new NDEF message
        // that was discovered
        if (intent != null) processIntent(intent)
    }

    /**
     * Check if the Intent has the action "ACTION_NDEF_DISCOVERED". If yes, handle it
     * accordingly and parse the NDEF messages.
     * @param checkIntent the intent to parse and handle if it's the right type
     */
    private fun processIntent(checkIntent: Intent) {
        // Check if intent has the action of a discovered NFC tag
        // with NDEF formatted contents
        if (checkIntent.action == NfcAdapter.ACTION_NDEF_DISCOVERED) {
            Log.i("New NDEF intent", checkIntent.toString())

            // Retrieve the raw NDEF message from the tag
            val rawMessages = checkIntent.getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES)
            if (rawMessages != null) {
                Log.i("Raw messages", rawMessages.size.toString())
            }

            // Complete variant: parse NDEF messages
            if (rawMessages != null) {
                val messages = arrayOfNulls<NdefMessage?>(rawMessages.size)// Array<NdefMessage>(rawMessages.size, {})
                for (i in rawMessages.indices) {
                    messages[i] = rawMessages[i] as NdefMessage
                    val intent = Intent(this, Webview::class.java)
                    intent.putExtra("Url", rawMessages)
                    startActivity(intent)
                }
                // Process the messages array.
                processNdefMessages(messages)
            }

            // Simple variant: assume we have 1x URI record
            //if (rawMessages != null && rawMessages.isNotEmpty()) {
            //    val ndefMsg = rawMessages[0] as NdefMessage
            //    if (ndefMsg.records != null && ndefMsg.records.isNotEmpty()) {
            //        val ndefRecord = ndefMsg.records[0]
            //        if (ndefRecord.toUri() != null) {
            //            logMessage("URI detected", ndefRecord.toUri().toString())
            //        } else {
            //            // Other NFC Tags
            //            logMessage("Payload", ndefRecord.payload.contentToString())
            //        }
            //    }
            //}

        }
    }

这是Webview activity,它应该获取URL并加载它:

class Webview : AppCompatActivity() {

    private lateinit var webview: Webview1
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_webview)

        val myWebView: WebView = findViewById(R.id.webview)
        val url = intent.getStringExtra("Url").toString()
        if (url != null) {
            Log.i("Url", url)
        }
        myWebView.webViewClient = object : WebViewClient () {
            override fun shouldOverrideUrlLoading(view: WebView?, url: String?): Boolean {

                if (url != null) {
                    view?.loadUrl(url)
                }
                return true
            }
        }
        myWebView.loadUrl(url)
        myWebView.settings.javaScriptEnabled=true
        myWebView.settings.allowContentAccess=true
        myWebView.settings.domStorageEnabled=true
        myWebView.settings.useWideViewPort=true
    }
}

我想获取从标记接收到的URL到

myWebView.loadUrl()

稍后将加载网站。谢谢你的帮助。

共有2个答案

郎弘业
2023-03-14

与:

val messages = arrayOfNulls<NdefMessage?>(rawMessages.size);

您将得到一个ndefmessage数组。每个“ndefmessage”都扩展了Parcelable,因此扩展了Parcelable的任何对象都可以很容易地在一个Bundle中put()。在这种特殊情况下,您有“ndefmessage[]”,表示“parcelable[]”,因此您必须执行以下操作:

intent.putParcelableArray("urls", rawMessages);

和activity:

Parcelable[] parcelables = b.getParcelableArray("urls");
  //just to be sure only NdefMessages can be used
final ArrayList<NdefMessage> ndefMessages = new ArrayList<>();
if (parcelables != null) {
  for (Parcelable parcelable : parcelables) {
      if (!(parcelable instanceof NdefMessage)) continue;
      ndefMessages.add(parcelable);
  }
}
  //HERE: "ndefMessages" contains all NdefMessages received

我从来没有使用过Kotlin但它应该可以工作(当我将Java代码复制/粘贴到KT文件时,AndroidStudio问我是否要将其转换为Kotlin...):

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    val parcelables = savedInstanceState?.getParcelableArray("urls")
    val ndefMessages = ArrayList<NdefMessage>();
    if (parcelables != null) {
        for (parcelable in parcelables) {
            if (parcelable !is NdefMessage) continue
            ndefMessages.add(parcelable)
        }
    }
}
姜俊民
2023-03-14

您正在有意传递可Parcelable对象

intent.putExtra("Url", rawMessages)

rawmessages获取字符串url,然后您将在Webview activity中收到该url

 类似资料:
  • 我正在尝试在活动之间传递数据 我使用intents在常规活动之间传递数据 请考虑以下代码:: 假设我将来自名为的其他活动的数据作为意图发送到 现在,如何接收中的数据,这些数据是从获得的,然后再将其传递到中 象形表示为:: {EDIT}--如果根据答案可以这样做--不明确,因为AndroidTabRestaurantDescearchListView是一个选项卡活动

  • 我试图通过在自定义对象上实现序列化将这个简单的对象从主要活动传递到主要活动。它会导致错误。我提到了类似的堆栈溢出问题。没有任何帮助。 主2活动 错误信息: 07-30 13:58:58.352 26489-26489/? E/AndroidRuntime:致命异常:主进程:gct.venkatesh.com。杂乱无章的,PID:26489 java.lang.RuntimeException:无法

  • 我正在开发一个由多个活动组成的Android应用程序,我必须在它们之间传递ab对象,但我不能通过使用意图传递它,因为对象的类没有实现可序列化,我怎么做?我无法修改我的类的源代码。谢谢:)

  • 我目前正在制作一个有edittext和2个按钮的应用程序,每次我在edittext中写一些东西,然后按下按钮1,就会添加一个新的textview。这是代码: 基本上,我正在做的是添加新的“玩家”,一旦我添加了他们,我想按下按钮2。Button2打开一个新活动,新活动应该读取我在前一个活动中添加的所有textviews。

  • 我有两项活动。两者都已实现surfaceview。在第一个活动中,我有一个名为score1的变量,我想将score1中的值传递给第二个活动。 每次我运行应用程序时,它在完成第一个活动后崩溃,并尝试加载第二个活动。在我编写代码以获取第二个活动中的额外意图之前,一切都很好。 我的第一个活动有这样的意图: 在我的第二个活动中,以下代码试图获取score1变量的值: 我不明白为什么每次activity o

  • 是否有办法在静态编程语言和Android中捆绑函数引用,以便可以从其他片段调用函数?例如,我的片段工厂方法如下所示: 我希望能够将我的tryAgainFunction保存在包中,以便进一步检索。 非常感谢! 编辑 最后,最合适的解决方案是使用热键的答案,然后在onViewCreated中使用传递的函数初始化监听器。完整代码如下: 谢谢大家的帮助!