使用Android导航组件的深层链接会打开错误的屏幕

时间:2019-11-08 21:21:39

标签: android android-intent android-architecture-navigation

您好,我正在学习如何使用Android的导航组件,为此,我正在制作一个非常基本的练习应用程序来尝试一些东西。我已经在两个屏幕之间建立了基本的导航和数据传输,但是我坚持的部分是建立一个深层链接。目前,我已经在目标(片段)中放置了一个深链接标记,而该目标目前无法通过其他任何方式到达。这基本上是与其他两个连接的屏幕分开的第三个屏幕,深链接是访问它的唯一方法。

我在下面和清单上共享了我的导航xml文件。

这是导航文件,相关的位是创意命名为“ firstDeepLinkFragment”的最后一个片段标签。


<?xml version="1.0" encoding="utf-8"?>
<navigation xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/navigation_graph"
    app:startDestination="@id/firstFragment">

    <fragment
        android:id="@+id/firstFragment"
        android:name="android.bignerdranch.navcontrollertest.FirstFragment"
        android:label="navigation_first_fragment"
        tools:layout="@layout/navigation_first_fragment" >
        <action
            android:id="@+id/action_firstFragment_to_secondFragment"
            app:destination="@id/secondFragment"
            app:enterAnim="@anim/nav_default_enter_anim"/>
    </fragment>

    <fragment
        android:id="@+id/secondFragment"
        android:name="android.bignerdranch.navcontrollertest.SecondFragment"
        android:label="navigation_second_fragment"
        tools:layout="@layout/navigation_second_fragment" />

    <fragment
        android:id="@+id/firstDeepLinkFragment"
        android:name="android.bignerdranch.navcontrollertest.FirstDeepLinkFragment"
        android:label="first_deeplink_fragment"
        tools:layout="@layout/first_deeplink_fragment" >
        <deepLink
            android:id="@+id/deepLink"
            app:uri="example://gizmos" />
    </fragment>
</navigation>

这是清单。

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="android.bignerdranch.navcontrollertest">

    <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">
        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>

            <nav-graph android:value="@navigation/navigation_graph"/>


        </activity>
    </application>

</manifest>

因此,根据我对导航组件下深层链接的工作方式的了解,我要做的就是将深层链接标签添加到要链接的目标位置,将URI建立为该标签的属性,然后添加清单中的nav-graph标记,并将其指向正确的导航图文件。如果我正确设置了这些内容,则应该建立适当的深层链接,并且一切顺利。问题是,当我输入以下命令来测试深层链接adb shell am start -W -a android.intent.action.VIEW -d "example://gizmos/"时,它会打开默认活动或默认目标(这是我在此处设置的其他目标的片段)。

老实说,我不确定我可能出了什么问题,并且现在没有关于此问题的大量信息,所以我希望已经对此有所了解的人们提供一些建议。我知道建立深层链接的旧方法涉及在意图链接到的活动的活动标签下的清单中编写意图过滤器。但是,在导航组件的框架下,我们现在只有一个主要活动,而我们所有其他屏幕/目的地都是片段。而且由于片段不必(也可能不应该/不可以?)注册到清单中,所以我什至不知道如何与旧方法建立深层次的联系。

是的,是的,如果有人可以帮助我指引正确的方向,指出我可能犯的任何愚蠢的错误,或者消除误解,我将不胜感激。谢谢。

1 个答案:

答案 0 :(得分:1)

根据this issue

  

intent filter documentation中所述:

     
    

如果过滤器指定一个方案和一个权限但没有路径,则所有具有相同方案和权限的URI都将匹配,无论它们的路径如何。

  

使用#include <chrono> bool UseFunction() { constexpr std::chrono::duration<double> interval_seconds{ 10.0 }; static std::chrono::time_point<std::chrono::steady_clock> last_call{ std::chrono::steady_clock::now() }; const auto now = std::chrono::steady_clock::now(); const auto elapsed_time = std::chrono::duration_cast<std::chrono::seconds>(now - last_call); const auto seconds_left = std::chrono::duration_cast<std::chrono::seconds>(interval_seconds - elapsed_time).count(); if (seconds_left > 0) { printf("Wait %lld seconds to use this\n", seconds_left); return false; } else { last_call = now; printf("Returning true.\n"); return true; } } 时,app:uri="example://gizmos"是方案,example://是授权者,但是缺少路径部分。通过将深层链接更改为也包含路径,导航将正确地将深层链接与目标匹配。