Octopus: A Revolutionary Declarative Router for Flutter
Published on by Flutter News Hub
Octopus, an innovative routing solution for Flutter, empowers developers with a declarative approach to navigation. Unlike traditional routers that rely on templates and imperative commands, Octopus introduces a truly declarative paradigm where developers simply define the desired outcome and let Octopus handle the rest.
Key Advantages of Octopus:
- Declarative Navigation: Change state through simple mutations, eliminating the need for push and pop commands.
- Nested Navigation: Navigate through complex state trees with ease, both through out-of-the-box solutions and custom implementations.
- State Machine: Build a robust router that responds predictably to state changes, enabling efficient handling of breadcrumbs and other complex navigation scenarios.
- History Preservation: Keep track of navigation states, allowing users to revisit previous pages and restore state effortlessly.
- Guards: Implement fine-grained control over navigation by defining custom guards to enforce authorization, change states, or perform any desired actions.
- Dialog Support: Show dialogs using declarative navigation, streamlining the user experience and reducing complexity.
- URL Representation: Preserve the entire navigation tree in URLs, providing transparency and deep linking capabilities.
- Concurrency Support: Out-of-the-box support for concurrent navigation tasks, ensuring smooth and responsive app behavior.
Getting Started with Octopus:
1. Installation:
dependencies:
octopus:
2. Define Routes:
enum Routes with OctopusRoute {
home('home'),
gallery('gallery'),
picture('picture'),
settings('settings');
const Routes(this.name);
final String name;
@override
Widget builder(BuildContext context, OctopusState state, OctopusNode node) {
switch (this) {
case Routes.home:
return const HomeScreen();
case Routes.gallery:
return const GalleryScreen();
case Routes.picture:
return PictureScreen(id: node.arguments['id']);
case Routes.settingsDialog:
return const SettingsDialog();
}
}
}
3. Create Octopus Router Instance:
router = Octopus(
routes: Routes.values,
defaultRoute: Routes.home,
);
4. Add Router Configuration:
MaterialApp.router(
routerConfig: router.config,
)
How to Navigate:
Use context.octopus.setState
to navigate declaratively:
context.octopus.setState((state) =>
state
..findByName('catalog-tab')?
.add(Routes.category.node(arguments: {'id': category.id}));
Guards:
Enforce navigation rules and perform custom actions with guards:
class AuthenticationGuard extends OctopusGuard {
@override
bool check(OctopusState state, OctopusNode node) {
// Implement authentication check
return true; // Navigate if authenticated
}
}
Glossary:
- State: Mutable or immutable representation of the current navigation state.
- Node: Building blocks of the state tree, each with a unique name and arguments.
- Route: Defines how to construct a page for the navigator, matched with nodes by name.
State Structure:
State is represented as a hierarchical tree structure, allowing for complex navigation scenarios:
final state = OctopusState(
children: [
OctopusNode(
name: 'home',
children: [],
),
OctopusNode(
name: 'shop',
children: [
OctopusNode(
name: 'catalog-tab',
children: [
OctopusNode(
name: 'catalog',
children: [],
),
OctopusNode(
name: 'category',
arguments: {'id': 'electronics'},
children: [],
),
// ...
],
),
OctopusNode(
name: 'basket-tab',
children: [
OctopusNode(
name: 'basket',
children: [],
),
OctopusNode(
name: 'checkout',
children: [],
),
],
),
],
),
],
);
Conclusion:
Octopus revolutionizes navigation in Flutter, empowering developers with a highly flexible, predictable, and declarative approach. Its robust features and ease of use make it an ideal choice for building complex and interactive Flutter applications.