به مؤلفه Navigation مهاجرت کنید

مؤلفه ناوبری کتابخانه ای است که می تواند ناوبری پیچیده، انیمیشن انتقال، پیوند عمیق و آرگومان بررسی شده در زمان کامپایل را که بین صفحه های برنامه شما ارسال می شود، مدیریت کند.

این سند به عنوان یک راهنمای همه منظوره برای انتقال یک برنامه موجود برای استفاده از مؤلفه ناوبری عمل می کند.

در سطح بالا، مهاجرت شامل مراحل زیر است:

  1. انتقال منطق رابط کاربری خاص صفحه به خارج از فعالیت‌ها - منطق رابط کاربری برنامه خود را از فعالیت‌ها خارج کنید، اطمینان حاصل کنید که هر فعالیت فقط دارای منطق مؤلفه‌های رابط کاربری ناوبری جهانی، مانند Toolbar است، در حالی که اجرای هر صفحه را به یک قطعه یا سفارشی واگذار می‌کند. مقصد

  2. کامپوننت ناوبری را یکپارچه کنید - برای هر فعالیت، یک نمودار ناوبری بسازید که شامل یک یا چند بخش مدیریت شده توسط آن فعالیت است. تراکنش های قطعه را با عملیات جزء ناوبری جایگزین کنید.

  3. افزودن مقصدهای فعالیت - فراخوانی های startActivity() را با اقداماتی که از مقصدهای فعالیت استفاده می کنند جایگزین کنید.

  4. ترکیب فعالیت ها - نمودارهای ناوبری را در مواردی که چندین فعالیت یک طرح مشترک دارند ترکیب کنید.

پیش نیازها

این راهنما فرض می کند که شما قبلاً برنامه خود را برای استفاده از کتابخانه های AndroidX منتقل کرده اید. اگر این کار را نکرده اید، قبل از ادامه پروژه خود را برای استفاده از AndroidX انتقال دهید .

منطق UI مخصوص صفحه نمایش را از فعالیت ها خارج کنید

Activities اجزایی در سطح سیستم هستند که تعامل گرافیکی بین برنامه شما و Android را تسهیل می کنند. فعالیت‌ها در مانیفست برنامه شما ثبت می‌شوند تا Android بداند کدام فعالیت‌ها برای راه‌اندازی در دسترس هستند. کلاس اکتیویتی به برنامه شما امکان می دهد به تغییرات اندروید نیز واکنش نشان دهد، مانند زمانی که رابط کاربری برنامه شما در حال ورود یا خروج از پیش زمینه، چرخش و غیره است. این فعالیت همچنین می‌تواند به عنوان مکانی برای اشتراک‌گذاری حالت بین صفحه‌ها عمل کند.

در زمینه برنامه شما، فعالیت‌ها باید به عنوان میزبانی برای پیمایش عمل کنند و منطق و دانش نحوه انتقال بین صفحه‌ها، انتقال داده و غیره را در خود داشته باشند. با این حال، مدیریت جزئیات UI شما بهتر است به بخش کوچکتر و قابل استفاده مجدد از UI خود واگذار شود. پیاده سازی توصیه شده برای این الگو قطعات است. برای کسب اطلاعات بیشتر در مورد مزایای استفاده از قطعات، به Single Activity: Why, When, and How مراجعه کنید. ناوبری از قطعات از طریق وابستگی ناوبری-قطعه پشتیبانی می کند. ناوبری همچنین از انواع مقصد سفارشی پشتیبانی می کند.

اگر برنامه شما از قطعات استفاده نمی کند، اولین کاری که باید انجام دهید این است که هر صفحه در برنامه خود را برای استفاده از یک قطعه انتقال دهید. در این مرحله فعالیت را حذف نمی‌کنید. در عوض، شما یک قطعه ایجاد می کنید تا نمایشگر را نشان دهد و منطق UI خود را با مسئولیت از هم جدا کند.

معرفی قطعات

برای نشان دادن روند معرفی قطعات، اجازه دهید با مثالی از یک برنامه کاربردی شروع کنیم که از دو صفحه تشکیل شده است: صفحه لیست محصول و صفحه جزئیات محصول . با کلیک بر روی یک محصول در صفحه لیست کاربر را به صفحه جزئیات می برد تا اطلاعات بیشتری در مورد محصول کسب کند.

در این مثال، صفحه لیست و جزئیات در حال حاضر فعالیت های جداگانه ای هستند.

یک Layout جدید برای میزبانی رابط کاربری ایجاد کنید

برای معرفی یک قطعه، با ایجاد یک فایل طرح بندی جدید برای فعالیت شروع به میزبانی قطعه کنید. این جایگزین طرح نمای محتوای فعلی فعالیت می شود.

برای یک نمای ساده، می توانید از FrameLayout استفاده کنید، همانطور که در مثال زیر product_list_host نشان داده شده است:

<FrameLayout
   xmlns:app="http://schemas.android.com/apk/res-auto"
   xmlns:android="http://schemas.android.com/apk/res/android"
   android:id="@+id/main_content"
   android:layout_height="match_parent"
   android:layout_width="match_parent" />

ویژگی id به بخش محتوا اشاره دارد که بعداً قطعه را اضافه می کنیم.

سپس، در تابع onCreate() اکتیویتی خود، مرجع فایل طرح بندی را در تابع onCreate فعالیت خود تغییر دهید تا به این فایل طرح بندی جدید اشاره کند:

کاتلین

class ProductListActivity : AppCompatActivity() {
    ...
    override fun onCreate(savedInstanceState: Bundle?) {
        ...
        // Replace setContentView(R.layout.product_list) with the line below
        setContentView(R.layout.product_list_host)
        ...
    }
}

جاوا

public class ProductListActivity extends AppCompatActivity {
    ...
    @Override
    public void onCreate(@Nullable Bundle savedInstanceState) {
        ...
        // Replace setContentView(R.layout.product_list); with the line below
        setContentView(R.layout.product_list_host);
        ...
    }
}

طرح بندی موجود ( product_list ، در این مثال) به عنوان نمای اصلی قطعه ای که می خواهید ایجاد کنید استفاده می شود.

یک قطعه ایجاد کنید

یک قطعه جدید برای مدیریت رابط کاربری صفحه نمایش خود ایجاد کنید. این یک تمرین خوب است که با نام میزبان فعالیت خود سازگار باشید. قطعه زیر از ProductListFragment استفاده می کند، برای مثال:

کاتلین

class ProductListFragment : Fragment() {
    // Leave empty for now.
}

جاوا

public class ProductListFragment extends Fragment {
    // Leave empty for now.
}

منطق فعالیت را به یک قطعه منتقل کنید

با تعریف قطعه، مرحله بعدی این است که منطق رابط کاربری این صفحه را از فعالیت به این قطعه جدید منتقل کنید. اگر از یک معماری مبتنی بر فعالیت می‌آیید، احتمالاً منطق ایجاد view زیادی در تابع onCreate() فعالیت شما اتفاق می‌افتد.

در اینجا یک نمونه صفحه نمایش مبتنی بر فعالیت با منطق رابط کاربری وجود دارد که باید آن را جابجا کنیم:

کاتلین

class ProductListActivity : AppCompatActivity() {

    // Views and/or ViewDataBinding references, Adapters...
    private lateinit var productAdapter: ProductAdapter
    private lateinit var binding: ProductListActivityBinding

    ...

    // ViewModels, System Services, other Dependencies...
    private val viewModel: ProductListViewModel by viewModels()

    ...

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        // View initialization logic
        DataBindingUtil.setContentView(this, R.layout.product_list_activity)

        // Post view initialization logic
        // Connect adapters
        productAdapter = ProductAdapter(productClickCallback)
        binding.productsList.setAdapter(productAdapter)

        // Initialize view properties, set click listeners, etc.
        binding.productsSearchBtn.setOnClickListener {...}

        // Subscribe to state
        viewModel.products.observe(this, Observer { myProducts ->
            ...
        })

        // ...and so on
    }
   ...
}

جاوا

public class ProductListActivity extends AppCompatActivity {

    // Views and/or ViewDataBinding references, adapters...
    private ProductAdapter productAdapter;
    private ProductListActivityBinding binding;

    ...

    // ViewModels, system services, other dependencies...
    private ProductListViewModel viewModel;

    ...

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        // View initialization logic
        DataBindingUtil.setContentView(this, R.layout.product_list_activity);

        // Post view initialization logic
        // Connect adapters
        productAdapter = new ProductAdapter(productClickCallback);
        binding.productsList.setAdapter(productAdapter);

        // Initialize ViewModels and other dependencies
        ProductListViewModel viewModel = new ViewModelProvider(this).get(ProductListViewModel.java);

        // Initialize view properties, set click listeners, etc.
        binding.productsSearchBtn.setOnClickListener(v -> { ... });

        // Subscribe to state
        viewModel.getProducts().observe(this, myProducts ->
            ...
       );

       // ...and so on
   }

همانطور که در مثال زیر نشان داده شده است، ممکن است فعالیت شما کنترل کننده زمان و نحوه حرکت کاربر به صفحه بعدی باشد:

کاتلین

    // Provided to ProductAdapter in ProductListActivity snippet.
    private val productClickCallback = ProductClickCallback { product ->
        show(product)
    }

    fun show(product: Product) {
        val intent = Intent(this, ProductActivity::class.java)
        intent.putExtra(ProductActivity.KEY_PRODUCT_ID, product.id)
        startActivity(intent)
    }

جاوا

// Provided to ProductAdapter in ProductListActivity snippet.
private ProductClickCallback productClickCallback = this::show;

private void show(Product product) {
    Intent intent = new Intent(this, ProductActivity.class);
    intent.putExtra(ProductActivity.KEY_PRODUCT_ID, product.getId());
    startActivity(intent);
}

در داخل قطعه خود، این کار را بین onCreateView() و onViewCreated() توزیع می‌کنید و فقط منطق ناوبری در فعالیت باقی می‌ماند:

کاتلین

class ProductListFragment : Fragment() {

    private lateinit var binding: ProductListFragmentBinding
    private val viewModel: ProductListViewModel by viewModels()

     // View initialization logic
    override fun onCreateView(inflater: LayoutInflater,
            container: ViewGroup?,
            savedInstanceState: Bundle?): View? {
        binding = DataBindingUtil.inflate(
                inflater,
                R.layout.product_list,
                container,
                false
        )
        return binding.root
    }

    // Post view initialization logic
    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        // Connect adapters
        productAdapter = ProductAdapter(productClickCallback)
        binding.productsList.setAdapter(productAdapter)

        // Initialize view properties, set click listeners, etc.
        binding.productsSearchBtn.setOnClickListener {...}

        // Subscribe to state
        viewModel.products.observe(this, Observer { myProducts ->
            ...
        })

        // ...and so on
    }

    // Provided to ProductAdapter
    private val productClickCallback = ProductClickCallback { product ->
        if (lifecycle.currentState.isAtLeast(Lifecycle.State.STARTED)) {
            (requireActivity() as ProductListActivity).show(product)
        }
    }
    ...
}

جاوا

public class ProductListFragment extends Fragment {

    private ProductAdapter productAdapter;
    private ProductListFragmentBinding binding;

    // View initialization logic
    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater,
            @Nullable ViewGroup container,
            @Nullable Bundle savedInstanceState) {
        binding = DataBindingUtil.inflate(
                inflater,
                R.layout.product_list_fragment,
                container,
                false);
        return binding.getRoot();
    }

    // Post view initialization logic
    @Override
    public void onViewCreated(@NonNull View view,
            @Nullable Bundle savedInstanceState) {

        // Connect adapters
        binding.productsList.setAdapter(productAdapter);

        // Initialize ViewModels and other dependencies
        ProductListViewModel viewModel = new ViewModelProvider(this)
                .get(ProductListViewModel.class);

        // Initialize view properties, set click listeners, etc.
        binding.productsSearchBtn.setOnClickListener(...)

        // Subscribe to state
        viewModel.getProducts().observe(this, myProducts -> {
            ...
       });

       // ...and so on

    // Provided to ProductAdapter
    private ProductClickCallback productClickCallback = new ProductClickCallback() {
        @Override
        public void onClick(Product product) {
            if (getLifecycle().getCurrentState().isAtLeast(Lifecycle.State.STARTED)) {
                ((ProductListActivity) requireActivity()).show(product);
            }
        }
    };
    ...
}

در ProductListFragment ، توجه کنید که هیچ تماسی با setContentView() برای باد کردن و اتصال طرح‌بندی وجود ندارد. در یک قطعه، onCreateView() نمای ریشه را مقداردهی اولیه می کند. onCreateView() نمونه‌ای از LayoutInflater را می‌گیرد که می‌تواند برای افزایش نمای ریشه بر اساس فایل منبع طرح‌بندی استفاده شود. این مثال از طرح‌بندی product_list موجود استفاده می‌کند که توسط اکتیویتی استفاده شده است، زیرا نیازی به تغییر در خود طرح نیست.

اگر منطق UI در توابع onStart() ، onResume() ، onPause() یا onStop() وجود دارد که مربوط به ناوبری نیست، می توانید آن ها را به توابع مربوطه با همان نام در قطعه منتقل کنید.

قطعه را در فعالیت میزبان راه اندازی کنید

هنگامی که تمام منطق UI را به قطعه منتقل کردید، فقط منطق ناوبری باید در فعالیت باقی بماند.

کاتلین

class ProductListActivity : AppCompatActivity() {

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

    fun show(product: Product) {
        val intent = Intent(this, ProductActivity::class.java)
        intent.putExtra(ProductActivity.KEY_PRODUCT_ID, product.id)
        startActivity(intent)
    }
}

جاوا

public class ProductListActivity extends AppCompatActivity {

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.product_list_host);
    }

    public void show(Product product) {
        Intent intent = new Intent(this, ProductActivity.class);
        intent.putExtra(ProductActivity.KEY_PRODUCT_ID, product.getId());
        startActivity(intent);
    }
}

آخرین مرحله ایجاد یک نمونه از قطعه در onCreate() است، درست پس از تنظیم نمای محتوا:

کاتلین

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

    if (savedInstanceState == null) {
        val fragment = ProductListFragment()
        supportFragmentManager
                .beginTransaction()
                .add(R.id.main_content, fragment)
                .commit()
    }
}

جاوا

@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.product_list_host);

    if (savedInstanceState == null) {
        ProductListFragment fragment = new ProductListFragment();
        getSupportFragmentManager()
                .beginTransaction()
                .add(R.id.main_content, fragment)
                .commit();
    }
}

همانطور که در این مثال نشان داده شده است، FragmentManager به طور خودکار قطعات را با تغییرات پیکربندی ذخیره و بازیابی می کند، بنابراین فقط در صورتی که savedInstanceState null باشد باید قطعه را اضافه کنید.

موارد اضافی قصد را به قطعه ارسال کنید

اگر اکتیویتی شما Extras از طریق intent دریافت می کند، می توانید آنها را مستقیماً به عنوان آرگومان به قطعه ارسال کنید.

در این مثال، ProductDetailsFragment آرگومان‌های خود را مستقیماً از اضافی‌های هدف فعالیت دریافت می‌کند:

کاتلین

...

if (savedInstanceState == null) {
    val fragment = ProductDetailsFragment()

    // Intent extras and Fragment Args are both of type android.os.Bundle.
    fragment.arguments = intent.extras

    supportFragmentManager
            .beginTransaction()
            .add(R.id.main_content, fragment)
            .commit()
}

...

جاوا

...

if (savedInstanceState == null) {
    ProductDetailsFragment fragment = new ProductDetailsFragment();

    // Intent extras and fragment Args are both of type android.os.Bundle.
    fragment.setArguments(getIntent().getExtras());

    getSupportFragmentManager()
            .beginTransaction()
            .add(R.id.main_content, fragment)
            .commit();
}

...

در این مرحله، باید بتوانید اجرای برنامه خود را با اولین صفحه به روز شده برای استفاده از یک قطعه آزمایش کنید. به انتقال بقیه صفحه‌های مبتنی بر فعالیت خود ادامه دهید و بعد از هر بار تکرار، برای آزمایش زمان صرف کنید.

کامپوننت Navigation را یکپارچه کنید

هنگامی که از یک معماری مبتنی بر قطعه استفاده می کنید، آماده شروع یکپارچه سازی مولفه Navigation هستید.

ابتدا، با پیروی از دستورالعمل‌های یادداشت‌های انتشار کتابخانه ناوبری ، جدیدترین وابستگی‌های ناوبری را به پروژه خود اضافه کنید.

یک نمودار ناوبری ایجاد کنید

مؤلفه Navigation پیکربندی پیمایش برنامه شما را در یک فایل منبع به صورت نمودار نشان می‌دهد، دقیقاً مانند نمایش‌های برنامه شما. این به سازماندهی ناوبری برنامه شما در خارج از پایگاه کد کمک می کند و راهی را برای شما فراهم می کند تا پیمایش برنامه خود را به صورت بصری ویرایش کنید.

برای ایجاد یک نمودار ناوبری، با ایجاد یک پوشه منبع جدید به نام navigation شروع کنید. برای افزودن نمودار، روی این دایرکتوری کلیک راست کرده و New > Navigation resource file را انتخاب کنید.

مؤلفه Navigation از یک فعالیت به عنوان میزبان برای پیمایش استفاده می‌کند و تکه‌های جداگانه را در آن میزبان مبادله می‌کند، زیرا کاربران شما در برنامه شما پیمایش می‌کنند. قبل از اینکه بتوانید به صورت بصری ناوبری برنامه خود را چیدمان کنید، باید یک NavHost در داخل فعالیتی که قرار است میزبان این نمودار باشد، پیکربندی کنید. از آنجایی که ما از قطعات استفاده می کنیم، می توانیم از اجرای پیش فرض NavHost مولفه Navigation، NavHostFragment استفاده کنیم.

همانطور که در مثال زیر نشان داده شده است، یک NavHostFragment از طریق یک FragmentContainerView که در داخل یک فعالیت میزبان قرار داده شده است، پیکربندی می شود:

<androidx.fragment.app.FragmentContainerView
   android:name="androidx.navigation.fragment.NavHostFragment"
   app:navGraph="@navigation/product_list_graph"
   app:defaultNavHost="true"
   android:id="@+id/main_content"
   android:layout_width="match_parent"
   android:layout_height="match_parent" />

ویژگی app:NavGraph به نمودار ناوبری مرتبط با این میزبان ناوبری اشاره می کند. تنظیم این ویژگی، نمودار nav را افزایش می دهد و ویژگی گراف را در NavHostFragment تنظیم می کند. ویژگی app:defaultNavHost تضمین می کند که NavHostFragment شما دکمه بازگشت سیستم را قطع می کند.

اگر از پیمایش سطح بالا مانند DrawerLayout یا BottomNavigationView استفاده می کنید، این FragmentContainerView جایگزین عنصر نمای محتوای اصلی شما می شود. برای مثال به به روز رسانی اجزای رابط کاربری با NavigationUI مراجعه کنید.

برای یک چیدمان ساده، می‌توانید این عنصر FragmentContainerView را به عنوان فرزند ViewGroup ریشه وارد کنید:

<FrameLayout
   xmlns:app="http://schemas.android.com/apk/res-auto"
   xmlns:android="http://schemas.android.com/apk/res/android"
   android:layout_height="match_parent"
   android:layout_width="match_parent">

<androidx.fragment.app.FragmentContainerView
   android:id="@+id/main_content"
   android:name="androidx.navigation.fragment.NavHostFragment"
   app:navGraph="@navigation/product_list_graph"
   app:defaultNavHost="true"
   android:layout_width="match_parent"
   android:layout_height="match_parent" />

</FrameLayout>

اگر روی تب Design در پایین کلیک کنید، باید نموداری شبیه به تصویر زیر مشاهده کنید. در سمت چپ بالای نمودار، در قسمت Destinations ، می‌توانید مرجعی به فعالیت NavHost به شکل layout_name (resource_id) ببینید.

روی دکمه پلاس کلیک کنید نزدیک به بالا برای اضافه کردن قطعات خود به این نمودار.

مؤلفه ناوبری به صفحه های جداگانه به عنوان مقصد اشاره دارد. مقاصد می توانند قطعات، فعالیت ها یا مقاصد سفارشی باشند. می‌توانید هر نوع مقصدی را به نمودار خود اضافه کنید، اما توجه داشته باشید که مقصد فعالیت‌ها مقصد پایانی در نظر گرفته می‌شوند، زیرا هنگامی که به مقصد فعالیت پیمایش می‌کنید، در یک میزبان ناوبری و نمودار جداگانه فعالیت می‌کنید.

مولفه ناوبری به روشی اشاره دارد که در آن کاربران از یک مقصد به مقصد دیگر به عنوان کنش می آیند. کنش‌ها همچنین می‌توانند انیمیشن‌های انتقالی و رفتار پاپ را توصیف کنند.

تراکنش های قطعه را حذف کنید

اکنون که از مؤلفه Navigation استفاده می کنید، اگر در حال پیمایش بین صفحه های مبتنی بر قطعه تحت یک فعالیت هستید، می توانید تعاملات FragmentManager را حذف کنید.

اگر برنامه شما از چندین قطعه تحت یک فعالیت یا پیمایش سطح بالا مانند طرح بندی کشو یا پیمایش پایین استفاده می کند، احتمالاً از FragmentManager و FragmentTransactions برای افزودن یا جایگزینی قطعات در بخش محتوای اصلی رابط کاربری خود استفاده می کنید. اکنون می توان با استفاده از مولفه Navigation با ارائه اقداماتی برای پیوند دادن مقصدها در نمودار خود و سپس پیمایش با استفاده از NavController جایگزین و ساده کرد.

در اینجا چند سناریو وجود دارد که ممکن است با آنها روبرو شوید و همچنین نحوه برخورد شما با مهاجرت برای هر سناریو وجود دارد.

فعالیت منفرد که چندین قطعه را مدیریت می کند

اگر یک اکتیویتی دارید که چندین قطعه را مدیریت می کند، کد فعالیت شما ممکن است به شکل زیر باشد:

کاتلین

class MainActivity : AppCompatActivity() {

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

        // Logic to load the starting destination
        //  when the Activity is first created
        if (savedInstanceState == null) {
            val fragment = ProductListFragment()
            supportFragmentManager.beginTransaction()
                    .add(R.id.fragment_container, fragment, ProductListFragment.TAG)
                    .commit()
        }
    }

    // Logic to navigate the user to another destination.
    // This may include logic to initialize and set arguments on the destination
    // fragment or even transition animations between the fragments (not shown here).
    fun navigateToProductDetail(productId: String) {
        val fragment = new ProductDetailsFragment()
        val args = Bundle().apply {
            putInt(KEY_PRODUCT_ID, productId)
        }
        fragment.arguments = args

        supportFragmentManager.beginTransaction()
                .addToBackStack(ProductDetailsFragment.TAG)
                .replace(R.id.fragment_container, fragment, ProductDetailsFragment.TAG)
                .commit()
    }
}

جاوا

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        // Logic to load the starting destination when the activity is first created.
        if (savedInstanceState == null) {
            val fragment = ProductListFragment()
            supportFragmentManager.beginTransaction()
                    .add(R.id.fragment_container, fragment, ProductListFragment.TAG)
                    .commit();
        }
    }

    // Logic to navigate the user to another destination.
    // This may include logic to initialize and set arguments on the destination
    // fragment or even transition animations between the fragments (not shown here).
    public void navigateToProductDetail(String productId) {
        Fragment fragment = new ProductDetailsFragment();
        Bundle args = new Bundle();
        args.putInt(KEY_PRODUCT_ID, productId);
        fragment.setArguments(args);

        getSupportFragmentManager().beginTransaction()
                .addToBackStack(ProductDetailsFragment.TAG)
                .replace(R.id.fragment_container, fragment, ProductDetailsFragment.TAG)
                .commit();
    }
}

در داخل مقصد مبدا، ممکن است یک تابع ناوبری را در پاسخ به برخی رویدادها فراخوانی کنید، همانطور که در زیر نشان داده شده است:

کاتلین

class ProductListFragment : Fragment() {
    ...
    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        // In this example a callback is passed to respond to an item clicked
        //  in a RecyclerView
        productAdapter = ProductAdapter(productClickCallback)
        binding.productsList.setAdapter(productAdapter)
    }
    ...

    // The callback makes the call to the activity to make the transition.
    private val productClickCallback = ProductClickCallback { product ->
            (requireActivity() as MainActivity).navigateToProductDetail(product.id)
    }
}

جاوا

public class ProductListFragment extends Fragment  {
    ...
    @Override
    public void onViewCreated(@NonNull View view,
            @Nullable Bundle savedInstanceState) {
    // In this example a callback is passed to respond to an item clicked in a RecyclerView
        productAdapter = new ProductAdapter(productClickCallback);
        binding.productsList.setAdapter(productAdapter);
    }
    ...

    // The callback makes the call to the activity to make the transition.
    private ProductClickCallback productClickCallback = product -> (
        ((MainActivity) requireActivity()).navigateToProductDetail(product.getId())
    );
}

این را می توان با به روز رسانی نمودار ناوبری برای تنظیم مقصد شروع و اقدامات برای پیوند دادن مقصدها و تعریف آرگومان ها در صورت لزوم جایگزین کرد:

<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/product_list_graph"
    app:startDestination="@id/product_list">

    <fragment
        android:id="@+id/product_list"
        android:name="com.example.android.persistence.ui.ProductListFragment"
        android:label="Product List"
        tools:layout="@layout/product_list">
        <action
            android:id="@+id/navigate_to_product_detail"
            app:destination="@id/product_detail" />
    </fragment>
    <fragment
        android:id="@+id/product_detail"
        android:name="com.example.android.persistence.ui.ProductDetailFragment"
        android:label="Product Detail"
        tools:layout="@layout/product_detail">
        <argument
            android:name="product_id"
            app:argType="integer" />
    </fragment>
</navigation>

سپس، می توانید فعالیت خود را به روز کنید:

کاتلین

class MainActivity : AppCompatActivity() {

    // No need to load the start destination, handled automatically by the Navigation component
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
    }
}

جاوا

public class MainActivity extends AppCompatActivity {

    // No need to load the start destination, handled automatically by the Navigation component
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }
}

فعالیت دیگر نیازی به متد navigateToProductDetail() ندارد. در بخش بعدی، ما ProductListFragment به روز می کنیم تا از NavController برای رفتن به صفحه جزئیات محصول بعدی استفاده کنیم.

آرگومان ها را با خیال راحت بگذرانید

مؤلفه Navigation دارای یک پلاگین Gradle به نام Safe Args است که کلاس های شی ساده و سازنده را برای دسترسی ایمن نوع به آرگومان های مشخص شده برای مقصدها و اقدامات ایجاد می کند.

هنگامی که افزونه اعمال می شود، هر آرگومان تعریف شده در یک مقصد در نمودار ناوبری شما باعث می شود که چارچوب جزء ناوبری یک کلاس Arguments ایجاد کند که آرگومان های ایمن نوع را برای مقصد مورد نظر ارائه می دهد. تعریف یک عمل باعث می‌شود که افزونه یک کلاس پیکربندی Directions ایجاد کند که می‌تواند به NavController بگوید چگونه کاربر را به مقصد مورد نظر هدایت کند. وقتی یک عمل به مقصدی اشاره می کند که به آرگومان نیاز دارد، کلاس Directions تولید شده شامل متدهای سازنده است که به آن پارامترها نیاز دارد.

همانطور که در مثال زیر نشان داده شده است، در داخل قطعه، از NavController و کلاس Directions تولید شده برای ارائه آرگومان های ایمن نوع به مقصد مورد نظر استفاده کنید:

کاتلین

class ProductListFragment : Fragment() {

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        // In this example a callback is passed to respond to an item clicked in a RecyclerView
        productAdapter = ProductAdapter(productClickCallback)
        binding.productsList.setAdapter(productAdapter)
    }
    ...

    // The callback makes the call to the NavController to make the transition.
    private val productClickCallback = ProductClickCallback { product ->
        val directions = ProductListDirections.navigateToProductDetail(product.id)
        findNavController().navigate(directions)
    }
}

جاوا

public class ProductListFragment extends Fragment  {
    ...
    @Override
    public void onViewCreated(@NonNull View view,
            @Nullable Bundle savedInstanceState) {
        // In this example a callback is passed to respond to an item clicked in a RecyclerView
        productAdapter = new ProductAdapter(productClickCallback);
        binding.productsList.setAdapter(productAdapter);
    }
    ...

    // The callback makes the call to the activity to make the transition.
    private ProductClickCallback productClickCallback = product -> {
        ProductListDirections.ViewProductDetails directions =
                ProductListDirections.navigateToProductDetail(product.getId());
        NavHostFragment.findNavController(this).navigate(directions);
    };
}

ناوبری سطح بالا

اگر برنامه شما از DrawerLayout استفاده می کند، ممکن است منطق پیکربندی زیادی در فعالیت خود داشته باشید که باز و بسته کردن کشو و پیمایش به مقصدهای دیگر را مدیریت می کند.

فعالیت شما ممکن است چیزی شبیه به این باشد:

کاتلین

class MainActivity : AppCompatActivity(),
    NavigationView.OnNavigationItemSelectedListener {

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

        val toolbar: Toolbar = findViewById(R.id.toolbar)
        setSupportActionBar(toolbar)

        val drawerLayout: DrawerLayout = findViewById(R.id.drawer_layout)
        val navView: NavigationView = findViewById(R.id.nav_view)
        val toggle = ActionBarDrawerToggle(
                this,
                drawerLayout,
                toolbar,
                R.string.navigation_drawer_open, 
                R.string.navigation_drawer_close
        )
        drawerLayout.addDrawerListener(toggle)
        toggle.syncState()

        navView.setNavigationItemSelectedListener(this)
    }

    override fun onBackPressed() {
        val drawerLayout: DrawerLayout = findViewById(R.id.drawer_layout)
        if (drawerLayout.isDrawerOpen(GravityCompat.START)) {
            drawerLayout.closeDrawer(GravityCompat.START)
        } else {
            super.onBackPressed()
        }
    }

    override fun onNavigationItemSelected(item: MenuItem): Boolean {
        // Handle navigation view item clicks here.
        when (item.itemId) {
            R.id.home -> {
                val homeFragment = HomeFragment()
                show(homeFragment)
            }
            R.id.gallery -> {
                val galleryFragment = GalleryFragment()
                show(galleryFragment)
            }
            R.id.slide_show -> {
                val slideShowFragment = SlideShowFragment()
                show(slideShowFragment)
            }
            R.id.tools -> {
                val toolsFragment = ToolsFragment()
                show(toolsFragment)
            }
        }
        val drawerLayout: DrawerLayout = findViewById(R.id.drawer_layout)
        drawerLayout.closeDrawer(GravityCompat.START)
        return true
    }
}

private fun show(fragment: Fragment) {

    val drawerLayout = drawer_layout as DrawerLayout
    val fragmentManager = supportFragmentManager

    fragmentManager
            .beginTransaction()
            .replace(R.id.main_content, fragment)
            .commit()

    drawerLayout.closeDrawer(GravityCompat.START)
}

جاوا

public class MainActivity extends AppCompatActivity
        implements NavigationView.OnNavigationItemSelectedListener {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Toolbar toolbar = findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        DrawerLayout drawer = findViewById(R.id.drawer_layout);
        NavigationView navigationView = findViewById(R.id.nav_view);
        ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
                this,
                drawer,
                toolbar,
                R.string.navigation_drawer_open,
                R.string.navigation_drawer_close);
        drawer.addDrawerListener(toggle);
        toggle.syncState();

        navigationView.setNavigationItemSelectedListener(this);
    }

    @Override
    public void onBackPressed() {
        DrawerLayout drawer = findViewById(R.id.drawer_layout);
        if (drawer.isDrawerOpen(GravityCompat.START)) {
            drawer.closeDrawer(GravityCompat.START);
        } else {
            super.onBackPressed();
        }
    }

    @Override
    public boolean onNavigationItemSelected(MenuItem item) {
        // Handle navigation view item clicks here.
        int id = item.getItemId();

        if (id == R.id.home) {
            Fragment homeFragment = new HomeFragment();
            show(homeFragment);
        } else if (id == R.id.gallery) {
            Fragment galleryFragment = new GalleryFragment();
            show(galleryFragment);
        } else if (id == R.id.slide_show) {
            Fragment slideShowFragment = new SlideShowFragment();
            show(slideShowFragment);
        } else if (id == R.id.tools) {
            Fragment toolsFragment = new ToolsFragment();
            show(toolsFragment);
        }

        DrawerLayout drawer = findViewById(R.id.drawer_layout);
        drawer.closeDrawer(GravityCompat.START);
        return true;
    }

    private void show(Fragment fragment) {

        DrawerLayout drawerLayout = findViewById(R.id.drawer_layout);
        FragmentManager fragmentManager = getSupportFragmentManager();

        fragmentManager
                .beginTransaction()
                .replace(R.id.main_content, fragment)
                .commit();

        drawerLayout.closeDrawer(GravityCompat.START);
    }
}

پس از اینکه جزء ناوبری را به پروژه خود اضافه کردید و یک نمودار ناوبری ایجاد کردید، هر یک از مقصدهای محتوا را از نمودار خود اضافه کنید (مانند صفحه اصلی ، گالری ، نمایش اسلاید ، و ابزارها از مثال بالا). مطمئن شوید که مقادیر id آیتم های منو با مقادیر id مقصد مرتبط با آنها مطابقت دارد، همانطور که در زیر نشان داده شده است:

<!-- activity_main_drawer.xml -->
<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    tools:showIn="navigation_view">

    <group android:checkableBehavior="single">
        <item
            android:id="@+id/home"
            android:icon="@drawable/ic_menu_camera"
            android:title="@string/menu_home" />
        <item
            android:id="@+id/gallery"
            android:icon="@drawable/ic_menu_gallery"
            android:title="@string/menu_gallery" />
        <item
            android:id="@+id/slide_show"
            android:icon="@drawable/ic_menu_slideshow"
            android:title="@string/menu_slideshow" />
        <item
            android:id="@+id/tools"
            android:icon="@drawable/ic_menu_manage"
            android:title="@string/menu_tools" />
    </group>
</menu>
<!-- activity_main_graph.xml -->
<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/main_graph"
    app:startDestination="@id/home">

    <fragment
        android:id="@+id/home"
        android:name="com.example.HomeFragment"
        android:label="Home"
        tools:layout="@layout/home" />

    <fragment
        android:id="@+id/gallery"
        android:name="com.example.GalleryFragment"
        android:label="Gallery"
        tools:layout="@layout/gallery" />

    <fragment
        android:id="@+id/slide_show"
        android:name="com.example.SlideShowFragment"
        android:label="Slide Show"
        tools:layout="@layout/slide_show" />

    <fragment
        android:id="@+id/tools"
        android:name="com.example.ToolsFragment"
        android:label="Tools"
        tools:layout="@layout/tools" />

</navigation>

اگر مقادیر id منو و نمودار خود را مطابقت دهید، می‌توانید NavController برای این فعالیت سیم‌کشی کنید تا پیمایش به‌طور خودکار بر اساس آیتم منو انجام شود. NavController همچنین باز و بسته کردن DrawerLayout و رفتار مناسب دکمه‌های Up و Back را انجام می‌دهد.

سپس MainActivity شما می تواند برای اتصال NavController به Toolbar و NavigationView به روز شود.

برای نمونه به قطعه زیر مراجعه کنید:

کاتلین

class MainActivity : AppCompatActivity()  {

    val drawerLayout by lazy { findViewById<DrawerLayout>(R.id.drawer_layout) }
    val navController by lazy {
      (supportFragmentManager.findFragmentById(R.id.main_content) as NavHostFragment).navController
    }
    val navigationView by lazy { findViewById<NavigationView>(R.id.nav_view) }

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

        val toolbar = findViewById<Toolbar>(R.id.toolbar)
        setSupportActionBar(toolbar)

        // Show and Manage the Drawer and Back Icon
        setupActionBarWithNavController(navController, drawerLayout)

        // Handle Navigation item clicks
        // This works with no further action on your part if the menu and destination id’s match.
        navigationView.setupWithNavController(navController)

    }

    override fun onSupportNavigateUp(): Boolean {
        // Allows NavigationUI to support proper up navigation or the drawer layout
        // drawer menu, depending on the situation
        return navController.navigateUp(drawerLayout)
    }
}

جاوا

public class MainActivity extends AppCompatActivity {

    private DrawerLayout drawerLayout;
    private NavController navController;
    private NavigationView navigationView;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        drawerLayout = findViewById(R.id.drawer_layout);
        NavHostFragment navHostFragment = (NavHostFragment)
            getSupportFragmentManager().findFragmentById(R.id.main_content);
        navController = navHostFragment.getNavController();
        navigationView = findViewById(R.id.nav_view);

        Toolbar toolbar = findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        // Show and Manage the Drawer and Back Icon
        NavigationUI.setupActionBarWithNavController(this, navController, drawerLayout);

        // Handle Navigation item clicks
        // This works with no further action on your part if the menu and destination id’s match.
        NavigationUI.setupWithNavController(navigationView, navController);

    }

    @Override
    public boolean onSupportNavigateUp() {
        // Allows NavigationUI to support proper up navigation or the drawer layout
        // drawer menu, depending on the situation.
        return NavigationUI.navigateUp(navController, drawerLayout);

    }
}

می‌توانید از همین تکنیک هم با ناوبری مبتنی بر BottomNavigationView و هم با ناوبری مبتنی بر منو استفاده کنید. برای مثال‌های بیشتر به به‌روزرسانی اجزای رابط کاربری با NavigationUI مراجعه کنید.

مقصدهای فعالیت را اضافه کنید

هنگامی که هر صفحه در برنامه شما برای استفاده از مؤلفه Navigation سیم‌کشی می‌شود و دیگر از FragmentTransactions برای انتقال بین مقصدهای مبتنی بر قطعه استفاده نمی‌کنید، گام بعدی حذف تماس‌های startActivity است.

ابتدا، مکان‌هایی را در برنامه خود شناسایی کنید که دو نمودار ناوبری مجزا دارید و از startActivity برای انتقال بین آنها استفاده می‌کنید.

این مثال شامل دو نمودار (A و B) و یک startActivity() برای انتقال از A به B است.

کاتلین

fun navigateToProductDetails(productId: String) {
    val intent = Intent(this, ProductDetailsActivity::class.java)
    intent.putExtra(KEY_PRODUCT_ID, productId)
    startActivity(intent)
}

جاوا

private void navigateToProductDetails(String productId) {
    Intent intent = new Intent(this, ProductDetailsActivity.class);
    intent.putExtra(KEY_PRODUCT_ID, productId);
    startActivity(intent);

سپس، اینها را با یک مقصد فعالیت در نمودار A جایگزین کنید که نشان دهنده مسیریابی به فعالیت میزبان نمودار B است. اگر آرگومان هایی برای ارسال به مقصد شروع نمودار B دارید، می توانید آنها را در تعریف مقصد فعالیت مشخص کنید.

در مثال زیر، نمودار A یک مقصد فعالیت را تعریف می‌کند که آرگومان product_id را همراه با یک اقدام می‌گیرد. نمودار B هیچ تغییری ندارد.

نمایش XML نمودارهای A و B ممکن است به شکل زیر باشد:

<!-- Graph A -->
<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/product_list_graph"
    app:startDestination="@id/product_list">

    <fragment
        android:id="@+id/product_list"
        android:name="com.example.android.persistence.ui.ProductListFragment"
        android:label="Product List"
        tools:layout="@layout/product_list_fragment">
        <action
            android:id="@+id/navigate_to_product_detail"
            app:destination="@id/product_details_activity" />
    </fragment>

    <activity
        android:id="@+id/product_details_activity"
        android:name="com.example.android.persistence.ui.ProductDetailsActivity"
        android:label="Product Details"
        tools:layout="@layout/product_details_host">

        <argument
            android:name="product_id"
            app:argType="integer" />

    </activity>

</navigation>
<!-- Graph B -->
<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"
    app:startDestination="@id/product_details">

    <fragment
        android:id="@+id/product_details"
        android:name="com.example.android.persistence.ui.ProductDetailsFragment"
        android:label="Product Details"
        tools:layout="@layout/product_details_fragment">
        <argument
            android:name="product_id"
            app:argType="integer" />
    </fragment>

</navigation>

می‌توانید با استفاده از مکانیزم‌های مشابهی که برای پیمایش به مقاصد قطعه‌سازی استفاده می‌کنید، به فعالیت میزبان نمودار B بروید:

کاتلین

fun navigateToProductDetails(productId: String) {
    val directions = ProductListDirections.navigateToProductDetail(productId)
    findNavController().navigate(directions)
}

جاوا

private void navigateToProductDetails(String productId) {
    ProductListDirections.NavigateToProductDetail directions =
            ProductListDirections.navigateToProductDetail(productId);
    Navigation.findNavController(getView()).navigate(directions);

ارگهای مقصد فعالیت را به قطعه مقصد شروع منتقل کنید

اگر اکتیویتی مقصد موارد اضافی دریافت می کند، مانند مثال قبلی، می توانید آنها را مستقیماً به عنوان آرگومان به مقصد شروع ارسال کنید، اما باید نمودار ناوبری میزبان خود را به صورت دستی در متد onCreate() اکتیویتی میزبان تنظیم کنید تا بتوانید هدف را ارسال کنید. موارد اضافی به عنوان آرگومان های قطعه، همانطور که در زیر نشان داده شده است:

کاتلین

class ProductDetailsActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.product_details_host)
        val navHostFragment = supportFragmentManager.findFragmentById(R.id.main_content) as NavHostFragment
        val navController = navHostFragment.navController
        navController
                .setGraph(R.navigation.product_detail_graph, intent.extras)
    }

}

جاوا

public class ProductDetailsActivity extends AppCompatActivity {

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.product_details_host);
        NavHostFragment navHostFragment = (NavHostFragment)
            getSupportFragmentManager().findFragmentById(R.id.main_content);
        NavController navController = navHostFragment.getNavController();
        navController
                .setGraph(R.navigation.product_detail_graph, getIntent().getExtras());
    }

}

همانطور که در مثال زیر نشان داده شده است، می توان داده ها را با استفاده از کلاس args تولید شده از آرگومان های قطعه Bundle خارج کرد:

کاتلین

class ProductDetailsFragment : Fragment() {

    val args by navArgs<ProductDetailsArgs>()

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        val productId = args.productId
        ...
    }
    ...

جاوا

public class ProductDetailsFragment extends Fragment {

    ProductDetailsArgs args;

    @Override
    public void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        args = ProductDetailsArgs.fromBundle(requireArguments());
    }

    @Override
    public void onViewCreated(@NonNull View view,
            @Nullable Bundle savedInstanceState) {
       int productId = args.getProductId();
       ...
    }
    ...

فعالیت ها را ترکیب کنید

می‌توانید نمودارهای ناوبری را در مواردی که چندین فعالیت یک طرح را به اشتراک می‌گذارند، ترکیب کنید، مانند یک FrameLayout ساده که حاوی یک قطعه است. در بیشتر این موارد، شما فقط می توانید تمام عناصر را از هر نمودار ناوبری ترکیب کنید و هر عنصر مقصد فعالیت را به مقصدهای قطعه قطعه به روز کنید.

مثال زیر نمودارهای A و B را از بخش قبل ترکیب می کند:

قبل از ترکیب:

<!-- Graph A -->
<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/product_list_graph"
    app:startDestination="@id/product_list">

    <fragment
        android:id="@+id/product_list"
        android:name="com.example.android.persistence.ui.ProductListFragment"
        android:label="Product List Fragment"
        tools:layout="@layout/product_list">
        <action
            android:id="@+id/navigate_to_product_detail"
            app:destination="@id/product_details_activity" />
    </fragment>
    <activity
        android:id="@+id/product_details_activity"
        android:name="com.example.android.persistence.ui.ProductDetailsActivity"
        android:label="Product Details Host"
        tools:layout="@layout/product_details_host">
        <argument android:name="product_id"
            app:argType="integer" />
    </activity>

</navigation>
<!-- Graph B -->
<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/product_detail_graph"
    app:startDestination="@id/product_details">

    <fragment
        android:id="@+id/product_details"
        android:name="com.example.android.persistence.ui.ProductDetailsFragment"
        android:label="Product Details"
        tools:layout="@layout/product_details">
        <argument
            android:name="product_id"
            app:argType="integer" />
    </fragment>
</navigation>

پس از ترکیب:

<!-- Combined Graph A and B -->
<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/product_list_graph"
    app:startDestination="@id/product_list">

    <fragment
        android:id="@+id/product_list"
        android:name="com.example.android.persistence.ui.ProductListFragment"
        android:label="Product List Fragment"
        tools:layout="@layout/product_list">
        <action
            android:id="@+id/navigate_to_product_detail"
            app:destination="@id/product_details" />
    </fragment>

    <fragment
        android:id="@+id/product_details"
        android:name="com.example.android.persistence.ui.ProductDetailsFragment"
        android:label="Product Details"
        tools:layout="@layout/product_details">
        <argument
            android:name="product_id"
            app:argType="integer" />
    </fragment>

</navigation>

ثابت نگه داشتن نام اقدامات خود در حین ادغام می تواند این فرآیند را یکپارچه کند و نیازی به تغییر در پایگاه کد موجود شما نداشته باشد. به عنوان مثال، navigateToProductDetail در اینجا یکسان باقی می ماند. تنها تفاوت این است که این اکشن اکنون به جای یک مقصد فعالیت، هدایت به یک مقصد قطعه را در همان NavHost نشان می دهد:

کاتلین

fun navigateToProductDetails(productId: String) {
    val directions = ProductListDirections.navigateToProductDetail(productId)
    findNavController().navigate(directions)
}

جاوا

private void navigateToProductDetails(String productId) {
    ProductListDirections.NavigateToProductDetail directions =
            ProductListDirections.navigateToProductDetail(productId);
    Navigation.findNavController(getView()).navigate(directions);

منابع اضافی

برای اطلاعات بیشتر مرتبط با ناوبری، به موضوعات زیر مراجعه کنید: