09. Nested Navigation Graphs

İç içe gezinme grafikleri diye çevirebileceğimiz bu başlıkta, farklı senaryo yapılarına göre hedefleri nasıl düzenleyeceğimizi inceleyeceğiz.

Öncelikle Nested Navigation kavramı nedir? Neden ihtiyaç duyarız? Hangi durumlarda kullanmalıyız? gibi soruları aklımızda bulundurarak ihtiyacı anlamaya çalışalım.

Eğer uygulamanız içerisinde farklı akışlarınız olacaksa ve uygulamanızın içerisinde sayfa gezintisi sırasında yaptığınız ileri-geri işlemlerini bu akış üzerinden sürdürecekseniz Nested Navigation'a ihtiyacınız var demektir ve daha iyi bir navigasyon deneyimi için kullanmanız önerilir.

Peki yukarıda bahsettiğimiz farklı akış kavramı ne demek? Onu bir detaylandıralım. Örneğin; uygulamanızın 5 sayfadan oluştuğunu farzedelim ve aşağıdaki graph'ta olduğu gibi bir yapısı olduğunu düşünelim.

Yukarıdaki graph'te de görüleceği üzere blankFragment'in 2 action'ı bulunuyor. blankFragment2 ve blankFragment4.

Aynı şekilde blankFragment2'in blankFragmnet3'e bir action'ı ve blankFragment4'ün de blankFragment5'e bir action'ı bulunuyor.

blankFragment > blankFragment2 > blankFragment3 gidişini 1. Akış,

blankFragment > blankFragment4 > blankFragment5 gidişini 2. Akış olduğunu kabul edelim.

Graph'ın metin sekmesin göz attığımızda şöyle bir yapı göreceğiz.

<?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/nav_graph"
    app:startDestination="@id/blankFragment">

    <fragment
        android:id="@+id/blankFragment"
        android:name="com.etiya.jpnavigation1.BlankFragment"
        android:label="fragment_blank"
        tools:layout="@layout/fragment_blank" >
        <action
            android:id="@+id/action_blankFragment_to_blankFragment2"
            app:destination="@id/blankFragment2" />
        <action
            android:id="@+id/action_blankFragment_to_blankFragment4"
            app:destination="@id/blankFragment4" />
    </fragment>
    <fragment
        android:id="@+id/blankFragment2"
        android:name="com.etiya.jpnavigation1.BlankFragment2"
        android:label="fragment_blank_fragment2"
        tools:layout="@layout/fragment_blank_fragment2" >
        <action
            android:id="@+id/action_blankFragment2_to_blankFragment3"
            app:destination="@id/blankFragment3" />
    </fragment>
    <fragment
        android:id="@+id/blankFragment3"
        android:name="com.etiya.jpnavigation1.BlankFragment3"
        android:label="fragment_blank_fragment3"
        tools:layout="@layout/fragment_blank_fragment3" />
    <fragment
        android:id="@+id/blankFragment4"
        android:name="com.etiya.jpnavigation1.BlankFragment4"
        android:label="fragment_blank_fragment4"
        tools:layout="@layout/fragment_blank_fragment4" >
        <action
            android:id="@+id/action_blankFragment4_to_blankFragment5"
            app:destination="@id/blankFragment5" />
    </fragment>
    <fragment
        android:id="@+id/blankFragment5"
        android:name="com.etiya.jpnavigation1.BlankFragment5"
        android:label="fragment_blank_fragment5"
        tools:layout="@layout/fragment_blank_fragment5" />
</navigation>

Şimdi ilk akışımız olan blankFragment > blankFragment2 > blankFragment3 için blankFragment2 ve blankFragment3'ü nested hale getirelim.

Hedefleri (destination) iç içe bir grafikte (nested graph) gruplamak için aşağıdakileri yapın:

  1. Navigation Editor'nde Shift tuşunu basılı tutun ve iç içe grafiğe (nested graph.) dahil etmek istediğiniz hedefleri tıklatın.

  2. context menu'sünü açmak için sağ tıklayın ve Move to Nested Graph > New Graph'ı seçin. Hedefler iç içe bir grafik içine alınır. Aşağıdaki ekran görüntüsünde, Navigation Editor'ünde iç içe bir grafik göstermektedir.

Bu işlemi tamamladıktan sonra metin sekmesine geçtiğimizde XML'imizin yeni hali aşağıdaki gibi olacaktır.

<?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/nav_graph"
    app:startDestination="@id/blankFragment">

    <fragment
        android:id="@+id/blankFragment"
        android:name="com.etiya.jpnavigation1.BlankFragment"
        android:label="fragment_blank"
        tools:layout="@layout/fragment_blank" >
        <action
            android:id="@+id/action_blankFragment_to_blankFragment2"
            app:destination="@id/navigation" />
        <action
            android:id="@+id/action_blankFragment_to_blankFragment4"
            app:destination="@id/blankFragment4" />
    </fragment>
    <fragment
        android:id="@+id/blankFragment4"
        android:name="com.etiya.jpnavigation1.BlankFragment4"
        android:label="fragment_blank_fragment4"
        tools:layout="@layout/fragment_blank_fragment4" >
        <action
            android:id="@+id/action_blankFragment4_to_blankFragment5"
            app:destination="@id/blankFragment5" />
    </fragment>
    <fragment
        android:id="@+id/blankFragment5"
        android:name="com.etiya.jpnavigation1.BlankFragment5"
        android:label="fragment_blank_fragment5"
        tools:layout="@layout/fragment_blank_fragment5" />
    <navigation
        android:id="@+id/navigation"
        app:startDestination="@id/blankFragment2" >
        <fragment
            android:id="@+id/blankFragment2"
            android:name="com.etiya.jpnavigation1.BlankFragment2"
            android:label="fragment_blank_fragment2"
            tools:layout="@layout/fragment_blank_fragment2">
            <action
                android:id="@+id/action_blankFragment2_to_blankFragment3"
                app:destination="@id/blankFragment3" />
        </fragment>
        <fragment
            android:id="@+id/blankFragment3"
            android:name="com.etiya.jpnavigation1.BlankFragment3"
            android:label="fragment_blank_fragment3"
            tools:layout="@layout/fragment_blank_fragment3" />
    </navigation>
</navigation>

Dikkat edecek olursanız, ana root'ta olduğu gibi yeni bir navigation elementi daha oluştu ve kendine ait bir startDestination'ı bulunuyor ve blankFragment2 ve blankFragment3'ü kapsüllemiş durumda. Bunun anlamı nested graph’ın dışındaki hedefler, nested graph’a yalnızca başlangıç hedefi (startDestination) üzerinden erişebilir. Yani nested graph dışından blankFragment3 için bir action tanımlanamaz.

Root graph'ın hazırladığımız navigation isimli Nested Graph'a olan aksiyonuna dikkat edin. Destination'ı navigation olarak verildi ve o da blankFragment2'ye startDestination üzerinden erişebilecek.

<action
    android:id="@+id/action_blankFragment_to_blankFragment2"
    app:destination="@id/navigation" />

O zaman nested graph kullanmak bize ne sağlayacak? sorusuna artık verilecek en güzel cevap sanırım "modüler navigasyon akışını sağlamak olacaktır" diyebiliriz. Nested graph'lar ile uygulama akışının belli bölümlerini modüler hale getirmek, hem düzenlenmesi hem de yeniden kullanımını çok kullanışlı hale getirecektir.

Dizayn sekmesindeyken nested graph'ların üzerinde çift tıklarsanız, içeriğini oluşturan destination'ları görebilirsiniz.

Buraya kadar nested navigation graph'ların nasıl çalıştığı, neden kullanmamız gerektiği, hangi durumlarda ihtiyaç duyulacağı gibi konularda bilgi edinmiş ve hem dizayn hem de text ortamındaki değişikliklerin neler olduğunu irdelemiş olduk.

Last updated