likes
comments
collection
share

【Flutter开发】搬砖技巧扩展操作符“...” Dart 在 2.3 引入了 扩展操作符(...)和 空感知扩展操作

作者站长头像
站长
· 阅读数 20

在线编程

DartPad

dartpad.cn/?null_safet…

配置相关

开启 Linter 规则

在 flutter 工程的根路径下添加名为 analysis_options.yaml 的文件,即可配置静态分析的相关规则

具体配置可参考:github.com/jonataslaw/…

详情见:dart.cn/guides/lang…

编码相关

避空运算符

Dart 提供了一系列方便的运算符用于处理可能会为空值的变量。其中一个是 ??= 赋值运算符,仅当该变量为空值时才为其赋值:

int? a; // = null
a ??= 3;
print(a); // <-- Prints 3.

a ??= 5;
print(a); // <-- Still prints 3.

另外一个避空运算符是 ??,如果该运算符左边的表达式返回的是空值,则会计算并返回右边的表达式。

print(1 ?? 3); // <-- Prints 1.
print(null ?? 12); // <-- Prints 12.

初始化列表

有时,当你在实现构造函数时,您需要在构造函数体执行之前进行一些初始化。例如,final 修饰的字段必须在构造函数体执行之前赋值。在初始化列表中执行此操作,该列表位于构造函数的签名与其函数体之间:

Point.fromJson(Map<String, num> json)
    : x = json['x'],
      y = json['y'] {
  print('In Point.fromJson(): ($x, $y)');
}

初始化列表也是放置断言的便利位置,它仅会在开发期间运行:

NonNegativePoint(this.x, this.y)
    : assert(x >= 0),
      assert(y >= 0) {
  print('I just made a NonNegativePoint: ($x, $y)');
}

扩展操作符“...”

Dart 在 2.3 引入了 扩展操作符...)和 空感知扩展操作符...?),它们提供了一种将多个元素插入集合的简洁方法。

例如,你可以使用扩展操作符(...)将一个 List 中的所有元素插入到另一个 List 中:

var list = [1, 2, 3];
var list2 = [0, ...list];
assert(list2.length == 4);

如果扩展操作符右边可能为 null ,你可以使用 null-aware 扩展操作符(...?)来避免产生异常:

var list;
var list2 = [0, ...?list];
assert(list2.length == 1);

可以查阅扩展操作符建议获取更多关于如何使用扩展操作符的信息。

集合中的 if

Dart 还同时引入了 集合中的 if集合中的 for 操作,在构建集合时,可以使用条件判断 (if) 和循环 (for)。

下面示例是使用 集合中的 if 来创建一个 List 的示例,它可能包含 3 个或 4 个元素:

var nav = [
  'Home',
  'Furniture',
  'Plants',
  if (promoActive) 'Outlet'
];

懒加载

In the following example, if the temperature variable is never used, then the expensive _readThermometer() function is never called:

 // This is the program's only call to _readThermometer().
 late String temperature = _readThermometer(); // Lazily initialized.

格式化json字符串

String prettyJsonString(dynamic json) {
  JsonEncoder encoder = new JsonEncoder.withIndent('  ');
  String jsonString = encoder.convert(json);

  return jsonString;
}

dynamic 转字符串

static Object toEncodableFallback(dynamic object) {
  return object.toString();
}

static String stringifyMessage(dynamic message) {
  final finalMessage = message is Function ? message() : message;
  if (finalMessage is Map || finalMessage is Iterable) {
    var encoder = JsonEncoder.withIndent('  ', toEncodableFallback);
    return encoder.convert(finalMessage);
  } else {
    return finalMessage.toString();
  }
}

删除集合中的空对象

import 'dart:core';

Map<String, dynamic> removeNullsFromMap(Map<String, dynamic> json) => json
  ..removeWhere((String key, dynamic value) => value == null)
  ..map<String, dynamic>((key, value) => MapEntry(key, removeNulls(value)));

List removeNullsFromList(List list) => list
  ..removeWhere((value) => value == null)
  ..map(removeNulls).toList();

dynamic removeNulls(dynamic e) => (e is List)
    ? removeNullsFromList(e)
    : (e is Map ? removeNullsFromMap(e as Map<String, dynamic>) : e);

extension ListExtension on List {
  List removeNulls() => removeNullsFromList(this);
}

extension MapExtension on Map {
  Map removeNulls() => removeNullsFromMap(this as Map<String, dynamic>);
}

疑难杂症

GestureDetector 的交互范围

因为在开发中,都是高度自定义的UI组件,类似按钮,基本上都是通过包裹 GestureDetector 来实现

但问题是,包裹后的组件总是很难点击到(触发 onTap 等事件),特别是“文字按钮”

在实践中发现,可以通过【设置背景色】来解决

—— 如果不需要有色背景,用透明背景Colors.transparent也是有效的

GestureDetector(
  child: Container(
    width: 67,
    height: 40,
    alignment: Alignment.center,
    color: Colors.transparent, // <= 可以体验下 有或没有这行代码的效果
    child: Text('取消'),
  ),
  onTap: () => print('onTap'),
)

TextField 中文字过多时 内容会被裁切

  • 内容不多时 可以正常显示【Flutter开发】搬砖技巧扩展操作符“...” Dart 在 2.3 引入了 扩展操作符(...)和 空感知扩展操作

  • 内容过多时 文字底部会被裁切【Flutter开发】搬砖技巧扩展操作符“...” Dart 在 2.3 引入了 扩展操作符(...)和 空感知扩展操作

解决方法:

修改 TextField.decoration.contentPadding 属性,完整示例如下:

Widget buildSearchBarTextField() {
  return TextField(
    autofocus: false,
    minLines: 1,
    textInputAction: TextInputAction.search,
    controller: textEditingController,
    focusNode: focusNode,
    textAlignVertical: TextAlignVertical.top, // 新加代码
    style: TextStyle(color: Color(0xFF1F1F1F), fontWeight: FontWeight.w400, fontSize: 15),  
    decoration: InputDecoration(
      hintText: '输入字词、成语、诗词',
      hintStyle: TextStyle(color: Color(0xFF8E8F85)),
      hintMaxLines: 1,
      border: InputBorder.none,
      isCollapsed: false,
      contentPadding: const EdgeInsets.only(bottom: 10), // 新加代码
    ),
    onChanged: onChangedTextField,
    onSubmitted: onSubmittedTextField,
  ).bhk_expanded();
}

效果如下:

【Flutter开发】搬砖技巧扩展操作符“...” Dart 在 2.3 引入了 扩展操作符(...)和 空感知扩展操作

参考文档

转载自:https://juejin.cn/post/6995880893113958408
评论
请登录