Riverpod 导航
使用 riverpod 管理 Flutter 导航。
用法
Bootstrap
将您的根 ProviderScope 替换为 RiverpodNavigation widget,并提供您的路由层次结构,然后将提供的 delegate 和 parser 提供给您的 MaterialApp.router 工厂。
final routes = RouteDefinition(
template: UriTemplate.parse('/'),
builder: (context, entry) => MaterialPage(
child: HomeLayout(),
),
next: [
RouteDefinition(
template: UriTemplate.parse('/articles/:id'),
builder: (context, entry) => MaterialPage(
child: ArticleLayout(
id: entry.parameters['id']!,
),
),
),
],
);
return RiverpodNavigation( // Replaces your root ProviderScope
routes: routes,
builder: (context, delegate, parser) => MaterialApp.router(
title: 'Flutter Demo',
routerDelegate: delegate,
routeInformationParser: parser,
),
);
导航
从 Provider
提供了一个 navigationProvider,可用于读取当前的导航状态。
要访问允许各种操作的底层 Notifier,请使用 navigationProvider.notifier provider。
final myProvider = Provider<MyState>((ref) {
final navigation = ref.watch(navigationProvider.notifier);
return MyState(
navigateToArticles: () {
navigation.navigate(Uri.parse('/articles'))
},
pop: () {
navigation.pop();
}
);
},
);
从 BuildContext
可以使用 BuildContext 的 navigation 扩展方法访问 Notifier。
@override
Widget build(BuildContext context) {
return TextButton(
child: Text('Articles'),
onPressed: () {
context.navigation.navigate(Uri.parse('/articles'))
}
);
}
Pop 行为
要自定义导航返回时的 pop 行为,可以将 PopBehavior 回调提供给 RiverpodNavigation 实例。结果指示当前 pop 操作是应该更新、取消还是自动(默认行为,仅用父级路由替换当前路由)。
RiverpodNavigation(
popBehaviour: (notifier, stack) {
if (stack.lastRoute?.key == Key('share-article')) {
return PopResult.update(Uri.parse('/'));
}
return PopResult.auto();
},
// ...
)
URI 重写
在 URI 被路由处理之前,可以使用 uriRewriter 属性修改 URI。这对于重定向或规范化 URI 非常有用。
RiverpodNavigation(
uriRewriter: (notifier, uri) {
if (uri == Uri.parse('/home')) {
return Uri.parse('/');
}
const publicPrefix = 'https://example.com';
final stringUri = uri.toString();
if (stringUri.startsWith(publicPrefix)) {
return Uri.parse(stringUri.substring(publicPrefix.length);
}
return uri;
},
// ...
);