Route — adalah kelas abstrak di Flutter yang mewakili layar atau halaman terpisah dalam riwayat navigasi Navigator. Implementasi konkret Route — MaterialPageRoute, CupertinoPageRoute dan PlatformRoute — menentukan bagaimana layar ditampilkan dan animasi apa yang digunakan saat transisi. Berbeda dengan widget biasa, Route memiliki siklus hidup sendiri dengan metode didPush, didPop, didReplace dan didChangeNext. Menurut Flutter API Reference (2026), setiap Route mengelola ModalBarrier, mempertimbangkan fitur platform (geser kembali di iOS) dan memastikan isolasi status antar layar.
Poin utama
Route — adalah dasar dari sistem navigasi Flutter. Setiap layar yang dilihat pengguna di aplikasi diwakili oleh objek Route yang berada di tumpukan Navigator. Route mengabstraksi layar dari kode manajemen: Navigator menambah dan menghapus Route, dan di dalam Route terdapat antarmuka yang dilihat pengguna. Arsitektur ini memisahkan tanggung jawab antara navigasi dan tampilan.
Berbeda dengan penggantian widget sederhana, Route menyediakan layanan yang tidak tersedia untuk widget biasa: ModalBarrier (menggelapkan latar belakang saat dialog terbuka), manajemen animasi masuk dan keluar, pemrosesan tombol keras “Kembali” di Android dan integrasi dengan animasi Hero untuk transisi mulus antar layar.
Menurut Flutter Cookbook (2026), Route adalah elemen kunci untuk animasi Hero: widget Hero di satu Route secara otomatis menganimasikan transisi ke widget Hero di Route berikutnya, menciptakan efek elemen “terbang”. Ini dimungkinkan karena Route menyimpan kedua layar di Overlay selama animasi.
Route adalah dasar untuk aplikasi mobile sederhana (melalui Navigator 1.0) maupun skenario kompleks dengan tautan dalam (Navigator 2.0). Di Navigator 2.0, Route mewakili Page yang dikonversi RouterDelegate dari konfigurasi rute. Memahami Route sangat penting untuk bekerja dengan sistem navigasi Flutter apa pun — terlepas dari pendekatan atau paket yang dipilih.
Flutter menyediakan beberapa implementasi bawaan Route, masing-masing menyesuaikan perilaku untuk platform tertentu. Pemilihan jenis Route yang tepat memengaruhi pengalaman pengguna: animasi Material di Android dan animasi Cupertino di iOS menciptakan rasa aplikasi “native”.
| Jenis Route | Animasi | Platform | Fitur |
|---|---|---|---|
| MaterialPageRoute | Geser dari bawah ke atas | Android, desktop | bayangan saat transisi, pemrosesan SafeArea otomatis |
| CupertinoPageRoute | Geser dari kanan ke kiri | iOS, iPadOS | gesture geser kembali, latar belakang transparan saat transisi |
| PlatformRoute | Pemilihan otomatis | Semua platform | memilih jenis berdasarkan TargetPlatform |
| PageRouteBuilder | Kustom | Semua platform | kontrol penuh atas animasi melalui AnimationController |
MaterialPageRoute — implementasi Route yang paling sering digunakan. Ini menganimasikan masuknya layar baru dari bawah ke atas dengan kemunculan bertahap. Saat keluar, layar dianimasikan dari atas ke bawah, kembali ke posisi awal. Bilah alat (AppBar) dan badan layar dianimasikan secara terpisah, menciptakan efek hierarki.
CupertinoPageRoute meniru UINavigationController dari iOS. Layar baru masuk dari kanan, menutupi yang sebelumnya. Fitur utama — dukungan untuk gesture interaktif geser kembali, diimplementasikan melalui CupertinoBackGestureDetector. Gesture ini diproses bahkan di tengah animasi, memberikan perilaku alami yang dikenal pengguna iPhone.
Route memiliki siklus hidup sendiri yang berbeda dari siklus hidup StatefulWidget biasa. Memahami siklus ini penting untuk inisialisasi data yang benar, berlangganan stream, dan membebaskan sumber daya saat layar ditutup.
Siklus hidup Route terdiri dari empat tahap utama. Transition — Route dibuat dan dianimasikan saat masuk (didPush dipanggil). Active — Route ditampilkan sepenuhnya dan berinteraksi dengan pengguna. Inactive — Route lain menutupi yang sekarang (dialog, layar bawah), tetapi Route tetap di tumpukan. Disposed — Route dihapus dari tumpukan dan dihancurkan, didPop dan dispose dipanggil.
Metode siklus hidup Route dapat ditimpa dalam implementasi kustom. Misalnya, didPop dipanggil saat Route dihapus dari tumpukan — di sini dapat menyimpan draf data. didChangeNext dipanggil saat Route berikutnya di tumpukan berubah — berguna untuk memperbarui UI saat riwayat navigasi berubah.
Menurut Flutter API Route.didPop (2026), penting untuk tidak membingungkan siklus hidup Route dengan siklus hidup State di dalam Route. StatefulWidget di dalam Route memiliki initState dan dispose sendiri yang dipanggil masing-masing di tahap Transition dan Disposed. Route hidup lebih lama dari State internalnya — Route tetap di Overlay bahkan ketika widgetnya disembunyikan sementara oleh Route lain.
Route menyediakan mekanisme untuk mentransfer data baik saat masuk (saat pembuatan) maupun saat keluar (saat penyelesaian). Transfer data yang benar melalui Route menghilangkan kebutuhan akan variabel global dan InheritedWidget, membuat navigasi aman tipe dan dapat diprediksi.
Untuk mentransfer data ke layar baru, digunakan konstruktor widget penerima atau argumen arguments di Navigator.pushNamed. Di dalam Route, data dapat diakses melalui RouteSettings.arguments yang disimpan dalam objek Route. Pendekatan ini berfungsi untuk semua jenis Route — MaterialPageRoute, CupertinoPageRoute dan implementasi kustom.
Untuk mengembalikan data, digunakan argumen kedua Navigator.pop(context, result). Navigator.push mengembalikan Future
Saat pemanggilan langsung Navigator.push dengan MaterialPageRoute, data ditransfer melalui konstruktor layar tujuan. MethodChannel tidak digunakan — ini adalah interaksi Dart murni. Pendekatan ini lebih disukai untuk transfer objek kompleks yang aman tipe.
Mari kita lihat contoh pembuatan Route kustom dengan animasi sendiri dan transfer data. PageRouteBuilder memungkinkan mendefinisikan animasi masuk dan keluar dengan kontrol penuh atas kurva animasi dan durasi.
// Route kustom dengan animasi geser
Navigator.push(context, PageRouteBuilder(
pageBuilder: (context, animation, secondaryAnimation) {
return DetailPage(productId: '42');
},
transitionsBuilder: (context, animation, secondaryAnimation, child) {
const begin = Offset(0.0, 0.3);
const end = Offset.zero;
final tween = Tween(begin: begin, end: end);
final offsetAnimation = animation.drive(tween);
return SlideTransition(position: offsetAnimation, child: child);
},
transitionDuration: const Duration(milliseconds: 400),
));
// Kembalikan data dari layar
ElevatedButton(
onPressed: () => Navigator.of(context).pop({'selected': true, 'id': '42'}),
child: const Text('Pilih'),
);
// Dapatkan hasil di layar pemanggil
final result = await Navigator.push(context, MaterialPageRoute(
builder: (context) => const SelectionPage(),
));
if (result != null) {
print('Dipilih: ${result['selected']}');
}
Dalam contoh, PageRouteBuilder mendefinisikan animasi kustom geser dari bawah dengan transparansi. transitionDuration mengatur kecepatan animasi. Kode juga mendemonstrasikan pengiriman hasil: layar detail mengembalikan Map dengan pilihan pengguna, dan layar pemanggil menerima data ini melalui Future dari push. Route memastikan isolasi penuh: draf di layar detail tidak memengaruhi status daftar.
Pertanyaan yang sering diajukan
Route — adalah objek yang mengelola layar di tingkat navigasi: menyimpan animasi, ModalBarrier dan siklus hidup. Widget — adalah deskripsi bagian antarmuka. Route berisi Widget di dalamnya, tetapi juga menyediakan layanan (lapisan Overlay, animasi Hero) yang tidak tersedia untuk widget biasa. Satu Route dapat berisi hierarki widget kompleks dengan kedalaman berapa pun.
Gunakan PageRouteBuilder dengan parameter pageBuilder (membangun layar) dan transitionsBuilder (mendefinisikan animasi). Di transitionsBuilder tersedia animation (0.0–1.0) dan secondaryAnimation untuk animasi paralel. Untuk kontrol penuh, buat subkelas Route dan timpa buildPage, createAnimationController dan buildTransitions, yang akan memberikan akses ke AnimationController tingkat rendah.
Untuk mentransfer objek kompleks, gunakan konstruktor layar tujuan saat Navigator.push langsung atau argumen arguments saat pushNamed. Pastikan objek dapat diserialisasi (Map, JSON atau kelas kustom). Untuk transfer aman tipe di Flutter, digunakan model freezed atau json_serializable yang menjamin deserialisasi yang benar saat transfer melalui RouteSettings.
Route.dispose tidak dipanggil jika Route tetap di tumpukan Navigator. Misalnya, saat membuka Route baru, Route lama masuk ke status tidak aktif (Inactive), tetapi tidak dihancurkan — tetap di tumpukan untuk kembali cepat. Dispose hanya dipanggil saat Route dihapus dari tumpukan melalui pop, pushReplacement atau pushAndRemoveUntil. Untuk membebaskan sumber daya, gunakan dispose State di dalam Route, bukan dispose Route itu sendiri.
Gunakan ModalRoute.of(context) untuk mendapatkan Route saat ini dari BuildContext. Properti ModalRoute.isActive menunjukkan apakah Route adalah layar yang terlihat saat ini. ModalRoute.isCurrent — true jika Route berada di puncak tumpukan. Untuk mengamati perubahan tumpukan, berlanggananlah ke pengamat Navigator melalui RouteAware dan RouteObserver, yang memberi tahu tentang perubahan Route aktif.
Ringkasan
Kami akan mengembangkan aplikasi seluler turnkey
IT Sectr membuat aplikasi iOS dan Android untuk startup dan bisnis sejak 2017. Kami akan memberi saran dan mengusulkan solusi terbaik.
Baca juga