在不离开父屏幕的情况下导航到新屏幕

Posted

技术标签:

【中文标题】在不离开父屏幕的情况下导航到新屏幕【英文标题】:Navigate to a new screen without leaving parent screen 【发布时间】:2020-12-18 05:06:56 【问题描述】:

我是 Flutter 的新手,我有这个使用 bottomSheet 的屏幕,当我点击一个项目时,我想转到一个新屏幕,同时留在这个包含 bottomSheet 的父屏幕中。这是父屏幕和其中的项目屏幕的源代码。

父主菜单屏幕

import 'package:flutter/material.dart';
import 'projects.dart';
import 'app-bar.dart';

class MainMenu extends StatefulWidget 
  @override
  _MainMenuState createState() => _MainMenuState();


class _MainMenuState extends State<MainMenu> 
  final GlobalKey<ScaffoldState> _scaffoldKey = new GlobalKey<ScaffoldState>();
  int _selectedIndex = 0;
  static List<TabItem> _widgetOptions = <TabItem>[
    TabItem(
      text: new Text('Projects'),
      className: Projects(),
    ),
    TabItem(
      text: new Text('Organization'),
      className: null,
    ),
    TabItem(
      text: new Text('Profile'),
      className: null,
    ),
  ];

  void _onItemTapped(int index) 
    setState(() 
      _selectedIndex = index;
    );
  

  @override
  Widget build(BuildContext context) 
    return new MaterialApp(
      home: SafeArea(
        child: new DefaultTabController(
          length: 3,
          child: new Scaffold(
            key: _scaffoldKey,
            appBar: appBar(_widgetOptions.elementAt(_selectedIndex).text),
            body: _widgetOptions.elementAt(_selectedIndex).className,
            bottomNavigationBar: BottomNavigationBar(
              items: <BottomNavigationBarItem>[
                BottomNavigationBarItem(
                  icon: Icon(Icons.view_column),
                  label: 'Projects'
                ),
                BottomNavigationBarItem(
                  icon: Icon(Icons.people),
                  label: 'Organization'
                ),
                BottomNavigationBarItem(
                  icon: Icon(Icons.person),
                  label: 'Profile'
                )
              ],
              currentIndex: _selectedIndex,
              onTap: _onItemTapped,
            ),
          ),
        )
      ),
    );
  


class TabItem 
  Widget text;
  dynamic className;

  TabItem( @required this.text, @required this.className );

项目

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:pmtool/project-page.dart';
import './interfaces/iprojects.dart';
import './constants/route-names.dart';


class Projects extends StatefulWidget 
  @override
  _ProjectsState createState() => _ProjectsState();


class _ProjectsState extends State<Projects> 
  final GlobalKey<ScaffoldState> _scaffoldState = new GlobalKey<ScaffoldState>();
  static const List<Text> sortOptions = [
    Text('Project Name'),
    Text('Project Number'),
    Text('Client Name'),
    Text('Percent Completed'),
    Text('Date Added'),
    Text('Project Type'),
  ];
  static const List<String> sortOrder = [
    'Descending',
    'Ascending',
  ];
  static const List<String> filters = [
    'Ongoing',
    'All',
    'Completed',
  ];
  List<bool> isSelected = [
    true, false, false, false, false, false,
  ];
  String selectedSort = 'Descending';
  static List<ProjectsMock> projects = [
    ProjectsMock(projectId: '1', projectNumber: '1', projectName: 'Project 1', clientName: 'asd', projectStatus: 'Ongoing'),
    ProjectsMock(projectId: '2', projectNumber: '2', projectName: 'Project 2', clientName: 'qwe', projectStatus: 'Completed'),
  ];
  String selectedFilter = 'Ongoing';

  void selectItem(int index) 
    setState(() 
      for (int i = 0; i < isSelected.length; i++) 
        if (i != index) 
          isSelected[i] = false;
          return;
        
        isSelected[i] = true;
      
    );
  

  void navigateToProject(BuildContext context, ProjectsMock project) 
    Navigator.push(
      context,
      MaterialPageRoute(
        builder: (context) => ProjectPage(),
        settings: RouteSettings(
          arguments: project,
        )
      )
    );
  

  void setBottomSheet(context) 
    showModalBottomSheet(
      context: context,
      builder: (BuildContext buildContext) 
        return Padding(
          padding: const EdgeInsets.all(10.0),
          child: Column(
            crossAxisAlignment: CrossAxisAlignment.start,
            children: <Widget>[
              new Text('Filters', style: TextStyle(fontWeight: FontWeight.bold),),
              new Wrap(
                spacing: 5.0,
                children: List.generate(filters.length, (index) 
                  if (selectedFilter == filters.elementAt(index)) 
                    return new ActionChip(
                      label: new Text(filters.elementAt(index)),
                      backgroundColor: Colors.blue,
                      labelStyle: TextStyle(color: Colors.white),
                      onPressed: () 
                        return;
                      ,
                    );
                  
                  return new ActionChip(
                    label: new Text(filters.elementAt(index)),
                    backgroundColor: Colors.white,
                    labelStyle: TextStyle(color: Colors.blue),
                    onPressed: () 
                      return;
                    ,
                  );
                ),
              ),
              new Text('Sort by', style: TextStyle(fontWeight: FontWeight.bold),),
              new Wrap(
                spacing: 5.0,
                children: List.generate(sortOptions.length, (index) 
                  if (isSelected[index]) 
                    return new ActionChip(
                      label: sortOptions.elementAt(index),
                      backgroundColor: Colors.blue,
                      labelStyle: TextStyle(color: Colors.white),
                      onPressed: () 
                        return;
                      ,
                    );
                  
                  return new ActionChip(
                    label: sortOptions.elementAt(index),
                    backgroundColor: Colors.white,
                    labelStyle: TextStyle(color: Colors.blue),
                    onPressed: () 
                      return;
                    ,
                  );
                ),
              ),
              new Container(
                margin: const EdgeInsets.only(top: 10.0),
                child: new Text('Sort Order', style: TextStyle(fontWeight: FontWeight.bold),),
              ),
              new Wrap(
                spacing: 5.0,
                children: List.generate(sortOrder.length, (index) 
                  if (selectedSort == sortOrder[index]) 
                    return new ActionChip(
                      label: Text(sortOrder.elementAt(index)),
                      backgroundColor: Colors.blue,
                      labelStyle: TextStyle(color: Colors.white),
                      onPressed: () 
                        return;
                      ,
                    );
                  
                  return new ActionChip(
                    label: Text(sortOrder.elementAt(index)),
                    backgroundColor: Colors.white,
                    labelStyle: TextStyle(color: Colors.blue),
                    onPressed: () 
                      return;
                    ,
                  );
                ),
              ),
            ],
          ),
        );
      
    );
  

  @override
  Widget build(BuildContext context) 
    return new Scaffold(
      floatingActionButton: new FloatingActionButton(child: new Icon(Icons.filter_alt), onPressed: () => setBottomSheet(context), mini: true),
      key: _scaffoldState,
      body: new Column(
        children: <Widget>[
          new Expanded(
            child: new Column(
              children: <Widget>[
                // Search header
                new Container(
                  padding: const EdgeInsets.all(10.0),
                  child: new Column(
                    crossAxisAlignment: CrossAxisAlignment.start,
                    children: <Widget>[
                      new Row(
                        mainAxisAlignment: MainAxisAlignment.center,
                        children: <Widget>[
                          new Expanded(
                            child: new TextField(
                              decoration: new InputDecoration(
                                hintText: 'Search',
                                labelText: 'Search',
                                suffixIcon: new IconButton(icon: Icon(Icons.search), onPressed: () 
                                  return;
                                ),
                                contentPadding: const EdgeInsets.only(left: 5.0, right: 5.0)
                              ),
                            )
                          ),
                        ],
                      ),
                    ],
                  ),
                ),
                new Padding(
                  padding: const EdgeInsets.only(left: 10.0, right: 10.0),
                  child: new Column(
                    children: List.generate(projects.length, (index) 
                      return new Container(
                        margin: const EdgeInsets.only(bottom: 10.0),
                        child: new RaisedButton(
                          onPressed: () => navigateToProject(context, projects.elementAt(index)),
                          color: Colors.white,
                          textColor: Colors.black,
                          child: new Padding(
                            padding: const EdgeInsets.all(10.0),
                            child: new Row(
                              mainAxisAlignment: MainAxisAlignment.spaceBetween,
                              children: <Widget>[
                                new Expanded(
                                  child: new Column(
                                    children: <Widget>[
                                      new Text(projects.elementAt(index)?.projectName, style: TextStyle(fontWeight: FontWeight.bold)),
                                      new Text(projects.elementAt(index)?.projectNumber),
                                    ]
                                  ),
                                ),
                                new Expanded(
                                  child: new Column(
                                    children: <Widget>[
                                      new Text(projects.elementAt(index)?.clientName, style: TextStyle(fontWeight: FontWeight.bold)),
                                      new Text(projects.elementAt(index)?.projectStatus),
                                    ]
                                  ),
                                )
                              ],
                            ),
                          ),
                        ),
                      );
                    ),
                  ),
                )
              ],
            ),
          )
        ],
      ),
    );
  

这是页面的快照。

我该怎么做?我尝试使用Navigator,但它进入了一个全新的屏幕。如果您需要更多信息,请告诉我。

【问题讨论】:

请让您的问题尽可能简短。当您转储所有代码时,很难调试正在发生的事情。下面的答案将解决您的问题。我建议从 Flutter 教程和在线播放列表中学习 Flutter。他们肯定帮了很多忙。最好不要跳过任何基础知识。祝你好运。 【参考方案1】:

您在 main.dart 文件中创建另一个并使用 Navigator 移动到该屏幕而不实际移动到另一个屏幕而不是替换当前屏幕

代码是这样的

Navigator.push(

              context,
              MaterialPageRoute(
                builder: (context) => DisplayPictureScreen(string1: string),//passing a parameter
              ),

            );

这是上课的方式

class DisplayPictureScreen extends StatelessWidget 
  final String string1;
  
  const DisplayPictureScreen(Key key, this.string1) : super(key: key);


  @override

  Widget build(BuildContext context) 
    return Scaffold(
      appBar: AppBar(title: Text(value[0]["label"],style: TextStyle(color: Colors.black,fontSize: 20),
      )),
      
    
      body: Column(
        children: [
          Text("lsfnklsnlvfdngvlirs")

        ],
      ),

    );
  

【讨论】:

以上是关于在不离开父屏幕的情况下导航到新屏幕的主要内容,如果未能解决你的问题,请参考以下文章

如何让 UICollectionView 在不离开屏幕的情况下使用自动布局填充其包含滚动视图的宽度?

在按钮单击 SwiftUI 时导航到新屏幕

切换到新屏幕时白色闪烁且背景为深色?

单击可扩展表视图中的子菜单时,我们可以导航到新视图吗?

使用 swiftUI 中的按钮导航到新屏幕

Flutter - 导航到新屏幕并返回