五个你所不知道的Flutter开发细节

1、利用IDE高效组合Widget

在Flutter中,UI的构建是经过Widget的层层嵌套实现的,开发过程当中不可避免地须要频繁修改Widget树,从中插入或者移除一些Widget。git

除了手动写代码和剪切粘贴去修改Widget树以外,在Android Studio和Visual Studio Code中,你还有更高效的方法可使用:github

  • 在Android Studio中

Android Studio

  • 在Visual Studio Code中

Visual Studio Code

2、理解下划线开头命名的含义

Flutter所使用的Dart语言,没有相似Java的publice protect private,以_开头的变量、函数和类,意味着它仅在库中是可视的bash

Libraries not only provide APIs, but are a unit of privacy: identifiers that start with an underscore (_) are visible only inside the library.出处ide

观察如下几个例子,加深理解:函数

  • 变量

name变量以_开头后,虽然都是继承于Fruit,可是因为Apple不在同一库中,所以它没法访问父类的name属性。

  • 函数

getName方法以_开头后,虽然都是继承于Fruit,可是因为Apple不在同一库中,所以它没法访问父类的getName方法,也无须实现它。

Banana类能够访问在同一个库中的_Fruit类,可是因为Apple不在同一库中,所以它没法访问_Fruit类。

3、区别final与const

在Dart中,当你不须要去改变一个变量的时候,应该使用final或者const,而不是使用var去声明一个变量。布局

一个final变量只容许被赋值一次,必须在定义时或者构造函数参数表中将其初始化。ui

const所修饰的是编译时常量,咱们在编译时就已经知道了它的值,它的值是不可改变的。spa

它们的区别就在于,const比final更加严格,看如下几个例子:3d

final List<String> list = [];
list.add('1'); // 正确

const List<String> list = [];
list.add('1'); // 错误,运行时报错:Cannot add to an unmodifiable list
复制代码
final timestamp = new DateTime.now().millisecondsSinceEpoch; // 正确

const timestamp = new DateTime.now().millisecondsSinceEpoch; 
// 错误,编译前报错:Const variables must be initialized with a constant value
复制代码

官方文档调试

4、使用Debug Painting调试界面

Flutter提供的Debug Painting能够很方便地协助咱们观察界面的布局,调试界面的开发

在Android Studio和Visual Studio Code中都有提供开关去显示或隐藏Debug Painting( 前提是App处于调试运行状态):

  • 在Android Studio中

Android Studio

  • 在Visual Studio Code中

Visual Studio Code

5、使用FocusScope转移焦点,隐藏输入法

咱们在开发App的时候,会常常遇到当点击空白区域时将输入法隐藏的需求。一想到输入法,你们可能都会想经过Method Channle,让原生实现隐藏输入法的办法来解决。其实咱们能够经过FocusScope来转移焦点,一样可以达到隐藏输入法的目的。

Container(
        height: 500.0,
        child: new GestureDetector(
          onTap: () {
            // 经过GestureDetector捕获点击事件,再经过FocusScope将焦点转移至空焦点——new FocusNode()
            FocusScope.of(context).requestFocus(FocusNode());
          },
          child: Container(
              margin: EdgeInsets.all(30.0),
              child: ListView(children: <Widget>[
                TextField(
                  decoration: InputDecoration(labelText: 'Username'),
                ),
                TextField(
                  decoration: InputDecoration(labelText: 'Password'),
                )
              ])),
        ),
      ),
复制代码

开发过程当中还发现了Flutter一个bug,这里传递给FocusScope的context不能在MaterialApp下面,即你须要将这部分代码放到独立的一个Widget里面。 具体参考这个issue最后一个评论。

相关文章
相关标签/搜索