Women's clothing mall in the actual combat of fluent project ----- navigation bar addition, status management and screen adaptation

Navigation bar add:

Continue with the last time Women's clothing mall in the actual combat of fluent project ------ project overview, project creation, directory structure, portal programming - cexo - blog Park I wrote the actual operation of the project. I didn't write anything last time. It's a small foundation. Next, let's build the navigation bar at the bottom:

Effect demonstration:

Specific implementation:  

The processing of the navigation bar is also relatively simple, that is, it is processed with the bottomnavigator bar control. The foundation can be referred to Start the basic journey of Fluter < 2 > ----- further discussion on future, common components and Material Design style components - cexo - blog Park However, provide will be introduced here for state management, which is a new knowledge. Therefore, although it is simple, it is still of great significance for learning. Let's implement it below.

Add navigation item:

1. First, create a new page for the home page:

2. Next, prepare the TAB data:

Other Tab items follow suit:

Empty page add:

Next, you need to prepare the corresponding page when you click TAB, similar to Fragment in Android, which occupies one bit first:

Each page is very simple and posted directly:

import 'package:flutter/material.dart';

class HomePage extends StatefulWidget {
  @override
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
  @override
  Widget build(BuildContext context) {
    return Center(
      child: Text('home page'),
    );
  }
}
import 'package:flutter/material.dart';

class CategoryPage extends StatefulWidget {
  @override
  _CategoryPageState createState() => _CategoryPageState();
}

class _CategoryPageState extends State<CategoryPage> {
  @override
  Widget build(BuildContext context) {
    return Center(
      child: Text('classification'),
    );
  }
}
import 'package:flutter/material.dart';

class CartPage extends StatefulWidget {
  @override
  _CartPageState createState() => _CartPageState();
}

class _CartPageState extends State<CartPage> {
  @override
  Widget build(BuildContext context) {
    return Center(
      child: Text('Shopping Cart'),
    );
  }
}
import 'package:flutter/material.dart';

class MemberPage extends StatefulWidget {
  @override
  _MemberPageState createState() => _MemberPageState();
}

class _MemberPageState extends State<MemberPage> {
  @override
  Widget build(BuildContext context) {
    return Center(
      child: Text('Member Center'),
    );
  }
}

Page rendering:

Next, the data we defined will form the display of the bottom navigation bar. At this time, we need to use the scaffold widget. The code is as follows:

import 'package:flutter/material.dart';
import 'package:fluttershop/config/index.dart';

import 'cart_page.dart';
import 'category_page.dart';
import 'home_page.dart';
import 'member_page.dart';

class IndexPage extends StatelessWidget {
  int _currentIndex = 0;

  final List<BottomNavigationBarItem> bottomTabs = [
    BottomNavigationBarItem(
      icon: Icon(Icons.home),
      title: Text(KString.homeTitle), //home page
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.category),
      title: Text(KString.categoryTitle), //classification
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.shopping_cart),
      title: Text(KString.shoppingCartTitle), //Shopping Cart
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.person),
      title: Text(KString.memberTitle), //Member Center
    ),
  ];

  final List<Widget> tabBodies = [
    HomePage(),
    CategoryPage(),
    CartPage(),
    MemberPage()
  ];

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Color.fromRGBO(244, 245, 245, 1.0),
      body: IndexedStack(
        index: _currentIndex,
        children: tabBodies,
      ),
      bottomNavigationBar: BottomNavigationBar(
        type: BottomNavigationBarType.fixed,
        currentIndex: _currentIndex,
        items: bottomTabs,
      ),
    );
  }
}

Then hang it on main.dart:

Now run to see:

At this time, we have to deal with the attack event to realize the face switching. Because the StatelessWidget is currently used, and if you want to click it, it will become a StatefulWidget, so let's modify it first:

import 'package:flutter/material.dart';
import 'package:fluttershop/config/index.dart';

import 'cart_page.dart';
import 'category_page.dart';
import 'home_page.dart';
import 'member_page.dart';

class IndexPage extends StatefulWidget {
  @override
  _IndexPageState createState() => _IndexPageState();
}

class _IndexPageState extends State<IndexPage> {
  int _currentIndex = 0;

  final List<BottomNavigationBarItem> bottomTabs = [
    BottomNavigationBarItem(
      icon: Icon(Icons.home),
      title: Text(KString.homeTitle), //home page
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.category),
      title: Text(KString.categoryTitle), //classification
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.shopping_cart),
      title: Text(KString.shoppingCartTitle), //Shopping Cart
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.person),
      title: Text(KString.memberTitle), //Member Center
    ),
  ];

  final List<Widget> tabBodies = [
    HomePage(),
    CategoryPage(),
    CartPage(),
    MemberPage()
  ];

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Color.fromRGBO(244, 245, 245, 1.0),
      body: IndexedStack(
        index: _currentIndex,
        children: tabBodies,
      ),
      bottomNavigationBar: BottomNavigationBar(
        type: BottomNavigationBarType.fixed,
        currentIndex: _currentIndex,
        items: bottomTabs,
        onTap: (index) {
          setState(() {
            _currentIndex = index;
          });
        },
      ),
    );
  }
}

Run to see:

Status management:

The goal to learn this time has been achieved, but!!! The focus here is to learn the state management mechanism of a provider, which is very useful for future project development.

State management basis:

Why state management?

Let's look at two scenarios first:

This page is very simple. In fact, it is the page logic generated by the official default. When you click the Floating Action Icon, the Text text in the page will be continuously digitally updated. It is very easy to update this simple page, but!! Let's take another look at the complex page:

Seeing so many lines, I felt dizzy.. If you want to:

For example, when you like an article and exit to the external thumbnail display, the number of likes also needs to be displayed externally. At this time, you need to synchronize these two states. At this time, we urgently need an architecture to help us clarify these relationships, and the state management framework came into being.

List of status management schemes:

  • Scoped Model:
    Its github is: scoped_model | Flutter Package , we'll find out later.
  • Redux:
    Its github is: flutter_redux | Flutter Package , I found an introduction to it on the Internet Flutter | exploration of state management -- Redux (II) - brief book , paste:

    Because wood has been used, wood has the right to speak. It's OK to feel weak. It feels that there are still many steps to use, which is more complex.

  • Bloc:
    Its github is: flutter_bloc | Flutter Package
  • State:
    This is the status notification method we currently use:

    It is OK to use it in small projects, but if the project is too large, the coupling of this use method is too strong and confusing.

  • Provide: [key learning]
    Its github address: GitHub - google/flutter-provide: A simple framework for state management in Flutter. , it's actually related to scoped_ Like the model, Provide also uses the InheritWidget (a very important widget through which state management is basically realized) to put the shared state on the top-level MaterialApp, that is:

    The underlying component obtains the state through the Provier and notifies the components that depend on the state to refresh through the hybrid ChangeNotifier. Let's learn about it from the official website:


    Let's see how it is used:


    The focus here is on its use, and the underlying principles will be studied later.

Current index status processing:

Next, use Provide to transform our program, that is, use it to handle the switching state of the Tab at the bottom, because sometimes the switching state is not necessarily generated by the user's click, or a detail sub page may need to switch the Tab of the home page to a page, so it will become very easy if Provide is integrated to manage the state, Let's start to modify our program to replace the previous way we used setState().

1. Add a dependency for Provide:

2. Define a Provide:

In fact, the definition is as shown in the official:

Save them in the provide directory:

3. Modify main() to initialize Provide:

Let's take a look at the main code of our main():

In fact, the next thing to do is as the above theory says:

The corresponding official codes are as follows:

Transformation according to the gourd and gourd:

Then wrap MyApp with Container:

4. Read the status value of Provide:

At this point, we can go back to the logic of Tab switching and read the location information to be switched from Provide, so that we can use Provide to change the state later and get the effect of switching the state in time. Let's take a look at the current code first:

How to rewrite it? Look at the following, basically write the routine once and learn it:

Then the naming structure in it is as follows:

Therefore, it can be constructed as follows:

Then the scaffold we wrote before can be written in it, as follows:

OK, here are the key steps. At this time, we have to remove the state code we use setState to process and use Provide instead, as follows:

At this time_ The value of currentIndex can be read through Provide. How to read it? See the following:

In fact, it is to read the value defined by us:

5. Click Tab to use provide instead:

Next, we'll deal with the Tab click. Now let's see how to use Provide to update the index status:

In this way, the state management has been transformed into. Of course, its effect is the same as that of setState(). The whole process will be called when we press TAB to switch:

You will return to this monitoring location:

One advantage of using Provide to manage status is that you can use statements like this to change the status of the Tab on any of our pages:

And it is completely decoupled from the business, which is a very important technique for commercial complex projects.

Add code for screen adaptation:

Finally, a screen adaptation tool library is introduced here, as follows:

Its use is also relatively simple:

You can see the blogger's thoughts Flutter screen adaptation scheme_ Screenutil - toeii's personal blog , post the core idea:

Therefore, it's time to integrate and add library dependencies:

Then add a sentence to the home page:

Pay attention to personal public account and get real-time push

 

Tags: iOS Android Flutter

Posted on Wed, 22 Sep 2021 03:47:09 -0400 by rg_22uk