Flutter_学习记录_导航和其他

Flutter 的导航页面跳转,是通过组件Navigator 和 组件MaterialPageRoute来实现的,Navigator提供了很多个方法,但是目前,我只记录我学习过程中接触到的方法:

  1. Navigator.push(), 跳转下一个页面
  2. Navigator.pop(), 返回上一个页面

1. 不带参数的页面跳转案例

代码如下:

dart 复制代码
import 'package:flutter/material.dart';

void main() {
  runApp(MaterialApp(
    title: "导航演示",
    home: FirstScreen(),
  ));
}


class FirstScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text("导航页面"),
      ),
      body: Center(
        child: ElevatedButton(
          style: ElevatedButton.styleFrom(
            backgroundColor: Colors.blueAccent,
            foregroundColor: Colors.white
          ),
          onPressed: (){
            Navigator.push(context, MaterialPageRoute(
                builder: (context) => SecondScreen()
              ));
          }, 
          child: Text("查看商品详情页"))
      ),
    );
  }
}

class SecondScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text("商品详情页")),
      body: Center(
        child: ElevatedButton(
          onPressed: (){
            Navigator.pop(context);
          }, 
          child: Text("点击返回")),
      ),
    );
  }
}

效果图:

2. 导航常数的传递和接收

代码如下:

dart 复制代码
import 'package:flutter/material.dart';

void main() {
  runApp(MaterialApp(
    title: "导航演示",
    home: ProductList(products: List.generate(20, (i) => Product("商品$i", "这是一个商品详情页,编号为:$i")))
  ));
}

class ProductList extends StatelessWidget {
  // 定义一个参数
  final List<Product> products;
  // 接收参数
  const ProductList({super.key, required this.products});

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar( title: Text("商品列表")),
      body: ListView.builder(
        itemCount: products.length,
        itemBuilder: (context, index) {
          return ListTile(
            title: Text(products[index].title),
            onTap: (){
              Navigator.push(context, MaterialPageRoute(
                builder: (context) => ProductDetail(product:products[index])
              ));
            },
          );
        })
    );
  }
}

// 商品详情页
class ProductDetail extends StatelessWidget {
   // 定义一个参数
  final Product product;
  const ProductDetail({super.key, required this.product});

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text(product.title)),
      body: Center(
        child: Text(product.description),
      ),
    );
  }
}

// 定义一个商品的对象
class Product {
  final String title; // 商品标题
  final String description; // 商品描述

  Product(this.title, this.description);
}

效果图如下:

3. 子页面给父级页面返回数据

代码如下:

dart 复制代码
import 'package:flutter/material.dart';

void main() {
  runApp(MaterialApp(
    title: "导航演示",
    home: FirstPage()
  ));
}

 class FirstPage extends StatelessWidget {
  const FirstPage({super.key});

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text("子页面将数据回传给父视图")),
      body: Center(
        child: RouteButton(),
      ),
    );
  }
}

class RouteButton extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return ElevatedButton(
      onPressed: (){
        _navigateDataToChildView(context);
      }, 
      child: Text("传递数据"));
  }

  _navigateDataToChildView(BuildContext context) async {
  	// 等待子视图返回时,回传的数据
    final result = await Navigator.push(
      context, 
      MaterialPageRoute(builder: (context) => ChildView())
    );
    // 屏幕底部的小弹窗
    ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(result)));
  }
}

// 子视图
class ChildView extends StatelessWidget {
  const ChildView({super.key});

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text("子视图")),
      body: Center(
        child: Column(
          children: [
            ElevatedButton(
              onPressed: (){
                Navigator.pop(context, "回传:这是第一个数据回传");
              }, 
              style: ElevatedButton.styleFrom(
                backgroundColor: Colors.blueAccent,
                foregroundColor: Colors.white
              ),
              child: Text("第一个数据回传")
            ),
            ElevatedButton(
              onPressed: (){
                Navigator.pop(context, "回传:这是第二个数据回传");
              },
              style: ElevatedButton.styleFrom(
                backgroundColor: Colors.orangeAccent,
                foregroundColor: Colors.white
              ), 
              child: Text("第二个数据回传")
            )
          ],
        ),
      ),
    );
  }
}

效果图如下:

Flutter_学习记录_数据回传

4. 设置导航栏的主题色

MaterialApp组件里面有个 theme属性,设置theme属性就可以设置导航栏的主题色,代码如下:

dart 复制代码
import 'package:flutter/material.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return  MaterialApp(
      debugShowCheckedModeBanner: true,
      home: Contrainer(),
      // 设置导航栏的主题色
      theme: ThemeData(
       appBarTheme: AppBarTheme(
         backgroundColor: Colors.yellow, // 设置导航栏颜色为蓝色
        ),
      ),
    );
  }
}

5. 导航栏的左右两侧添加操作按钮

AppBar组件中的leading是可以添加左边一个按钮,actions是可以添加右边的一组按钮,代码实例如下:

dart 复制代码
import 'package:flutter/material.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return  MaterialApp(
      debugShowCheckedModeBanner: true,
      home: Home(),
      theme: ThemeData(
       appBarTheme: AppBarTheme(
         backgroundColor: Colors.yellow, // 设置导航栏颜色为蓝色
        ),
      ),
    );
  }
}

class Home extends StatelessWidget {
  const Home({super.key});

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        // 添加左边的操作按钮
        leading: IconButton(
          onPressed: () => debugPrint("navigation button is pressed."), 
          icon: Icon(Icons.menu),
          tooltip: "Navigation",
        ),
        // 添加右边的操作按钮
        actions: [
          IconButton(
            onPressed: () => debugPrint("navigation button is pressed."), 
            icon: Icon(Icons.search),
            tooltip: "search",
          )
        ],
        title: Text("App Demo"),
        elevation: 0.0),
      body: Center(
        child: Text("添加导航栏的事件"),
      ),
    );
  }
}

效果图如下:

相关推荐
珊瑚里的鱼6 分钟前
【单链表算法实战】解锁数据结构核心谜题——环形链表
数据结构·学习·程序人生·算法·leetcode·链表·visual studio
林涧泣7 分钟前
图的矩阵表示
学习·线性代数·矩阵
chimchim6614 分钟前
【starrocks学习】之catalog
学习
yqcoder19 分钟前
Commander 一款命令行自定义命令依赖
前端·javascript·arcgis·node.js
前端Hardy35 分钟前
HTML&CSS :下雪了
前端·javascript·css·html·交互
愿天深海40 分钟前
Flutter TextPainter 计算文本高度和行数
flutter
梦云澜1 小时前
论文阅读(二):理解概率图模型的两个要点:关于推理和学习的知识
论文阅读·深度学习·学习
LuiChun1 小时前
webview_flutter_android 4.3.0使用
android·flutter
码上飞扬2 小时前
Vue 3 30天精进之旅:Day 05 - 事件处理
前端·javascript·vue.js
Ronin-Lotus2 小时前
上位机知识篇---CMake
c语言·c++·笔记·学习·跨平台·编译·cmake