美文网首页
Flutter 之路由

Flutter 之路由

作者: Abner_XuanYuan | 来源:发表于2023-10-15 11:31 被阅读0次

    1、路由介绍

    Flutter 中的路由通俗的讲就是页面跳转。在 Flutter 中通过 Navigator 组件管理路由导航。并提供了管理堆栈的方法。如:Navigator.push 和 Navigator.pop。
    Flutter 中给我们提供了两种配置路由跳转的方式:1、基本路由 2、命名路由。

    2、普通路由

    例:从 HomePage 组件跳转到 SearchPage 组件。
    1、需要在 HomPage 中引入 SearchPage.dart

    import './testLib/SearchPage.dart';
    

    2、在 HomePage 中跳转

    class HomePage extends StatelessWidget {
      const HomePage({super.key});
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: const Text("页面跳转"),
          ),
          backgroundColor: Colors.grey,
          body: Center(
            child: ElevatedButton(
                onPressed: () {
                  //通过以下方法实现跳转
                  Navigator.of(context).push(MaterialPageRoute(builder: (context) {
                    return const SearchPage();
                  }));
                },
                child: const Text("页面跳转按钮")),
          ),
        );
      }
    }
    

    传值
    1、SearchPage 页面

    import 'package:flutter/material.dart';
    
    class SearchPage extends StatelessWidget {
      final String title;
    
      const SearchPage({super.key, this.title = "Search"});
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          backgroundColor: Colors.orange,
          appBar: AppBar(
            title: Text(title),
            centerTitle: true,
          ),
          body: Center(
            child: Container(
              color: Colors.green,
              child: const Text("搜索页面视图"),
            ),
          ),
        );
      }
    }
    

    2、HomePage 页面

    // 以下为传值时的代码
    class HomePage extends StatelessWidget {
      const HomePage({super.key});
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: const Text("页面跳转"),
          ),
          backgroundColor: Colors.grey,
          body: Center(
            child: ElevatedButton(
                onPressed: () {
                  //通过以下方法实现跳转
                  Navigator.of(context).push(MaterialPageRoute(builder: (context) {
                    // return const SearchPage();
                    return const SearchPage(title: "搜索vvvvv",);  //传值
                  }));
                },
                child: const Text("页面跳转按钮")),
          ),
        );
      }
    }
    

    3、命名路由

    1、无参跳转

    配置 routes

    import 'package:flutter/material.dart'; 
    import './pages/tabs.dart'; 
    import './pages/search.dart'; 
    import './pages/form.dart';
    
    void main(List<String> args) {
      runApp(const MyApp());
    }
    
    class MyApp extends StatelessWidget {
      const MyApp({super.key});
    
      @override
      Widget build(BuildContext context) {
        return const MaterialApp(
          // home: HomePage(),
         initialRoute: '/',    //初始化路由
          routes: {     //跳转路由(更改建议:调整为路由表)
            '/':(contxt)=>const Tabs(), 
            '/search':(contxt) => const SearchPage(), 
            '/form': (context) => const FormPage(), },
        );
      }
    }
    

    跳转

    ElevatedButton(
                onPressed: () {
                  Navigator.pushNamed(context, '/form');
                },
                child: const Text("跳转到form页面")),
    
    2、有参跳转

    配置 onGenerateRoute

    import 'package:flutter/material.dart'; 
    import './pages/tabs.dart'; 
    import './pages/search.dart'; 
    import './pages/form.dart'; 
    
    
    void main() { 
      runApp(const MyApp()); 
      }
      
      class MyApp extends StatelessWidget {
         //1、定义Map类型的routes 
         Map routes = { 
          '/': (contxt) => const Tabs(), 
          '/search': (contxt) => const SearchPage(),      //注意:命名路由无需传值方式
          '/form': (context, {arguments}) => FormPage(arguments: arguments),     //注意:命名路由需要传值方式
          };
          MyApp({Key? key}) : super(key: key); 
          @override Widget build(BuildContext context) { 
            return MaterialApp( 
              debugShowCheckedModeBanner: false, 
              title: 'Flutter Demo', 
              theme: ThemeData( 
                primarySwatch: Colors.blue, 
                ),
                initialRoute: '/',     //初始化路由
                //2、配置 onGenerateRoute
                onGenerateRoute: (RouteSettings settings) { 
                  // 统一处理 
                  final String? name = settings.name;     //路由名称,如:/form
                  final Function? pageContentBuilder = routes[name];     // Function,如:(contxt) => const SearchPage()
                  if (pageContentBuilder != null) { 
                    if (settings.arguments != null) {    //是否有传参
                      final Route route = MaterialPageRoute( 
                        builder: (context) => 
                            pageContentBuilder(context, arguments: settings.arguments)); 
                      return route;
                    } else { 
                      final Route route = MaterialPageRoute( 
                        builder: (context) => pageContentBuilder(context)); 
                          return route; 
                    } 
                  }
                  return null; 
                }, 
            );
          } 
    }
    

    定义页面接收 arguments 参数

    import 'package:flutter/material.dart'; 
    class FormPage extends StatefulWidget { 
      final Map arguments;     //接收参数
      const FormPage({super.key,required this.arguments}); 
      
      @override 
      State<FormPage> createState() => _FormPageState(); 
    }
    
    class _FormPageState extends State<FormPage> { 
      @override 
      void initState() {
         print(widget.arguments); 
      }
      
      @override 
      Widget build(BuildContext context) { 
        return Scaffold( 
          appBar: AppBar( 
            title: const Text("我是一个Form表单演示页面"), 
          ), 
        ); 
      } 
    }
    

    跳转

    ElevatedButton(
      onPressed: () { 
        Navigator.pushNamed(context, '/form',arguments: {     //传参
          "title": "搜索页面", 
        }); 
      },
       child: const Text("form") 
    )
    
    3、命名路由方法封装

    在路由文件中配置公共路由和 onGenerateRoute

    //1、导入头文件
    import 'package:flutter/material.dart';
    import '../pages/tabs.dart';
    import '../pages/search.dart';
    import '../pages/news.dart';
    import '../pages/form.dart';
    import '../pages/shop.dart';
    
    //2、配置路由(路由中字符串(key)可以进一步进行宏定义封装)
    Map routes = {
      "/": (contxt) => const Tabs(),
      "/news": (contxt) => const NewsPage(),
      "/search": (contxt) => const SearchPage(),
      "/form": (contxt, {arguments}) => FormPage(arguments: arguments),
      "/shop": (contxt, {arguments}) => ShopPage(arguments: arguments),
    };
    
    //3、配置 onGenerateRoute (固定写法,这个方法也相当于一个中间件,这里可以做权限判断)
    var onGenerateRoute = (RouteSettings settings) { 
      final String? name = settings.name; 
      final Function? pageContentBuilder = routes[name]; 
    
      if (pageContentBuilder != null) {
        if (settings.arguments != null) {
          final Route route = MaterialPageRoute(
              builder: (context) =>
                  pageContentBuilder(context, arguments: settings.arguments));
          return route;
        } else {
          final Route route =
              MaterialPageRoute(builder: (context) => pageContentBuilder(context));
          return route;
        }
      }
      return null;
    };
    

    路由跳转配置

    import 'package:flutter/material.dart';
    import './routers/routers.dart';  //导入路由文件
    
    void main() {
      runApp(const MyApp());
    }
    
    class MyApp extends StatelessWidget {
      const MyApp({Key? key}) : super(key: key);
    
      // This widget is the root of your application.
      @override
      Widget build(BuildContext context) {
        return MaterialApp(
          title: 'Flutter Demo',
          theme: ThemeData(
            primarySwatch: Colors.blue,
          ),
          //路由跳转
          initialRoute: "/",    //初始化路由
          onGenerateRoute: onGenerateRoute,   //路由跳转
        );
      }
    }
    

    使用

    //无参
    ElevatedButton(
                  onPressed: () {
                    Navigator.pushNamed(context, "/news");
                  },
                  child: const Text("命名路由跳转news")),
    //有参
    ElevatedButton(
                  onPressed: () {
                    Navigator.pushNamed(context, "/shop",
                        arguments: {"title": "shop传值", "aid": 21});
                  },
                  child: const Text("命名路由传值Shop")),
    

    4、路由相关方法

    返回上一级路由

    Navigator.of(context).pop();
    

    路由替换:跳转到指定页面

    Navigator.of(context).pushReplacementNamed('/registerSecond');
    

    返回到根路由

    Navigator.of(context).pushAndRemoveUntil( 
      MaterialPageRoute(builder: (BuildContext context) { 
        return const Tabs(); 
      }), (route) => false);
    

    路由跳转风格
    Material 组件库中提供了一个 MaterialPageRoute 组件,它可以使用和平台风格一致的路由切换动画,如在 iOS 平台上会左右滑动切换,而在 Android 上会上下滑动切换 。CupertinoPageRoute 是 Cupertino 组件库提供的 iOS 风格的路由切换组件如果在 Android 上也想使用左右切换风格,可以使用 CupertinoPageRoute。
    使用方法
    1、引入 cupertino.dart

    import 'package:flutter/cupertino.dart';
    

    2、MaterialPageRoute 改为 CupertinoPageRoute

    ///测试示例
    import 'package:flutter/cupertino.dart';     //注意:引入头文件
    import '../pages/tabs.dart'; 
    import '../pages/shop.dart'; 
    import '../pages/user/login.dart'; 
    import '../pages/user/registerFirst.dart'; 
    import '../pages/user/registerSecond.dart'; 
    import '../pages/user/registerThird.dart'; 
    
    //1、配置路由 
    Map routes = { 
      "/": (contxt) => const Tabs(), 
      "/login": (contxt) => const LoginPage(),
      "/registerFirst": (contxt) => const RegisterFirstPage(), 
      "/registerSecond": (contxt) => const RegisterSecondPage(), 
      "/registerThird": (contxt) => const RegisterThirdPage(), 
      "/shop": (contxt, {arguments}) => ShopPage(arguments: arguments), 
      };
      
    //2、配置onGenerateRoute 固定写法 这个方法也相当于一个中间件,这里可以做权限判断 
    var onGenerateRoute = (RouteSettings settings) { 
      final String? name = settings.name; // /news 或者 /search 
      final Function? pageContentBuilder = routes[name]; 
    Function = (contxt) { return const NewsPage()} 
    
      if (pageContentBuilder != null) { 
        if (settings.arguments != null) { 
          final Route route = CupertinoPageRoute(     //MaterialPageRoute 改为 CupertinoPageRoute
            builder: (context) => 
                pageContentBuilder(context, arguments: settings.arguments)); 
          return route; 
        } else { 
          final Route route = 
            CupertinoPageRoute(builder: (context) => pageContentBuilder(context));     //MaterialPageRoute 改为 CupertinoPageRoute
          return route; 
        } 
      }
      return null; 
    };
    

    相关文章

      网友评论

          本文标题:Flutter 之路由

          本文链接:https://www.haomeiwen.com/subject/jhmcpdtx.html