Flutter Go Code Development Specification Version 1.0

What is Flutter?

On June 21, 2018, Google released the first release preview of Flutter, as a brand new responsive, cross-platform, high-performance mobile development framework that Google vigorously launched. Flutter is a cross-platform mobile UI framework designed to help developers use a set of codes to develop high-performance, high-fidelity Android and iOS applications.

The advantages of flutter mainly include:

  • Cross-platform
  • Open source
  • Hot Reload, responsive framework, and its rich controls and development tools
  • Flexible interface design and control combination
  • With the help of portable GPU accelerated rendering engine and high-performance ARM code runtime, high-quality user experience has been achieved

Flutter Go origin

  • Flutter has too few learning materials, which is relatively difficult for students with poor English
  • The official website document examples are not sound enough and not intuitive enough
  • The usage of each widget is different, and the attributes are numerous. To run a widget demo, you often need to browse various materials everywhere
  • Alibaba auction front-end team dedication
  • Flutter_go code development specification is alibaba's good practice in the Flutter_go project on github.

Advantages of Flutter Go

  • Detailed common widget up to 140 + a
  • Supporting Demo to explain the general usage of widget
  • Centralized integration of widget cases, one APP handles the usage of all common widgets
  • Continue to iterate the official version of'chasing the new'

 

Project address: https://github.com/alibaba/flutter-go

The Flutter-Go Roadmap (Roadmap) for 2019

Basic environment

The project environment is continuously updated. Please update each dependent package regularly.

  • dart(version: 2.0.0)
  • flutter(version: v1.0.0)

 

Code style

Three types of identifiers

Big hump

Classes, enums, typedefs, and type parameters

  class SliderMenu { ... }
  
  class HttpRequest { ... }
  
  typedef Predicate = bool Function<T>(T value);

Include classes for metadata annotation

  class Foo {
    const Foo([arg]);
  }
  
  @Foo(anArg)
  class A { ... }
  
  @Foo()
  class B { ... }

Use lowercase and underscore to name libraries and source files

  library peg_parser.source_scanner;
  
  import 'file_system.dart';
  import 'slider_menu.dart';

The following is not recommended:

  library pegparser.SourceScanner;
  
  import 'file-system.dart';
  import 'SliderMenu.dart';

Use lowercase and underscore to name the import prefix

  import 'dart:math' as math;
  import 'package:angular_components/angular_components'
      as angular_components;
  import 'package:js/js.dart' as js;

The following is not recommended:

  import 'dart:math' as Math;
  import 'package:angular_components/angular_components'
      as angularComponents;
  import 'package:js/js.dart' as JS;

Use little camel case to name other identifiers

  var item;
  
  HttpRequest httpRequest;
  
  void align(bool clearItems) {
    // ...
  }

Prefer to use the little camel case as constant naming

  const pi = 3.14;
  const defaultTimeout = 1000;
  final urlScheme = RegExp('^([a-z]+):');
  
  class Dice {
    static final numberGenerator = Random();
  }

The following is not recommended:

  const PI = 3.14;
  const DefaultTimeout = 1000;
  final URL_SCHEME = RegExp('^([a-z]+):');
  
  class Dice {
    static final NUMBER_GENERATOR = Random();
  }

Do not use prefix letters

Because Dart can tell you the declared type, scope, variability, and other properties, there is no reason to encode these properties as identifier names.

  defaultTimeout

The following is not recommended:

  kDefaultTimeout

Sort

In order to keep your document foreword tidy, we have prescribed orders in which instructions should appear. Each "part" should be separated by a blank line.

Introduce the required dart library before other introductions

  import 'dart:async';
  import 'dart:html';
  
  import 'package:bar/bar.dart';
  import 'package:foo/foo.dart';

Introduce the library in the package before the relative introduction

  import 'package:bar/bar.dart';
  import 'package:foo/foo.dart';
  
  import 'util.dart';

Import of third-party packages precedes other packages

  import 'package:bar/bar.dart';
  import 'package:foo/foo.dart';
  
  import 'package:my_package/util.dart';

After all imports, specify the export in a separate section

  import 'src/error.dart';
  import 'src/foo_bar.dart';
  
  export 'src/error.dart';

The following is not recommended:

  import 'src/error.dart';
  export 'src/error.dart';
  import 'src/foo_bar.dart';

For all flow control structures, please use braces

This can avoid the suspended else problem

  if (isWeekDay) {
    print('Bike to work!');
  } else {
    print('Go dancing or read a book!');
  }

exception

An if statement has no else clause, and the entire if statement and then body fit on one line. In this case, you can remove the braces if you like

  if (arg == null) return defaultValue;

If the process body exceeds one line and needs to be divided, please use braces:

  if (overflowChars != other.overflowChars) {
    return overflowChars < other.overflowChars;
  }

The following is not recommended:

  if (overflowChars != other.overflowChars)
    return overflowChars < other.overflowChars;

Comment

Format like a sentence

Unless it is a case-sensitive identifier, the first word must be capitalized. End with a period (or "!" or "?"). This is true for all comments: doc comments, inline content, and even TODOs. Even a sentence fragment.

  greet(name) {
    // Assume we have a valid name.
    print('Hi, $name!');
  }

The following is not recommended:

  greet(name) {
    /* Assume we have a valid name. */
    print('Hi, $name!');
  }

You can use block comments (/.../) to temporarily comment out a piece of code, but all other comments should use //

Doc comment

Use ///document comments to record members and types.

Using doc comments instead of regular comments allows dartdoc to find and generate documentation.

  /// The number of characters in this chunk when unsplit.
  int get length => ...

For historical reasons, Dartmouth College supports the two syntaxes of Doug's comments: ///("C# style") and /**...*/("JavaDoc style"). We prefer /// because it is more compact. /* and / add two lines with no content in a multi-line document comment. In some cases, the /// syntax is also easier to read, such as document comments containing bulleted lists marked with *.

Consider writing documentation comments for private APIs

Doc comments are not just for external users of the library's public API. They also help to understand private members called from other parts of the library

Start doc comment with one sentence summary

Start your documentation comments with a short, user-centric description, and end with a period.

/// Deletes the file at [path] from the file system.
void delete(String path) {
  ...
}

The following is not recommended:

  /// Depending on the state of the file system and the user's permissions,
  /// certain operations may or may not be possible. If there is no file at
  /// [path] or it can't be accessed, this function throws either [IOError]
  /// or [PermissionError], respectively. Otherwise, this deletes the file.
  void delete(String path) {
    ...
  }

Separate the first sentence of "doc comment" into its own paragraph

Add a blank line after the first sentence and divide it into its own paragraphs

  /// Deletes the file at [path].
  ///
  /// Throws an [IOError] if the file could not be found. Throws a
  /// [PermissionError] if the file is present but could not be deleted.
  void delete(String path) {
    ...
  }

Flutter_Go use reference

Library reference

In flutter go, import the file library under lib and specify the package name uniformly to avoid excessive../../

package:flutter_go/

Use of strings

Concatenate string literals with adjacent strings

If there are two string literals (not values, but actually quoted literals), you don't need to use + to connect them. Just like in C and C++, it can be done simply by putting them together. This is a great way to create a long string, but not for a single line.

raiseAlarm(
    'ERROR: Parts of the spaceship are on fire. Other '
    'parts are overrun by martians. Unclear which are which.');

The following is not recommended:

raiseAlarm('ERROR: Parts of the spaceship are on fire. Other ' +
    'parts are overrun by martians. Unclear which are which.');

Prefer template strings

'Hello, $name! You are ${year - birth} years old.';

Avoid using curly braces when they are not needed

  'Hi, $name!'
  "Wear your wildest $decade's outfit."

The following is not recommended:

  'Hello, ' + name + '! You are ' + (year - birth).toString() + ' y...';

The following is not recommended:

  'Hi, ${name}!'
  "Wear your wildest ${decade}'s outfit."

set

Use collective literals whenever possible

If you want to create a non-growth list, or some other custom collection type, then anyway, you must use the constructor.

  var points = [];
  var addresses = {};
  var lines = <Lines>[];

The following is not recommended:

  var points = List();
  var addresses = Map();

Don't use .length to see if the collection is empty

if (lunchBox.isEmpty) return 'so hungry...';
if (words.isNotEmpty) return words.join(' ');

The following is not recommended:

  if (lunchBox.length == 0) return 'so hungry...';
  if (!words.isEmpty) return words.join(' ');

Consider using higher-order methods to convert the sequence

If you have a collection and you want to generate a new modified collection from it, then using .map(), .where() and other convenient methods on Iterable are usually shorter and more declarative

  var aquaticNames = animals
      .where((animal) => animal.isAquatic)
      .map((animal) => animal.name);

Avoid using Iterable.forEach() with function literals

In Dart, if you want to traverse a sequence, the idiomatic way is to use loops.

for (var person in people) {
  ...
}

The following is not recommended:

  people.forEach((person) {
    ...
  });

Do not use List.from() unless you plan to change the type of the result

Given an iteration, there are two obvious ways to generate a new list containing the same elements

var copy1 = iterable.toList();
var copy2 = List.from(iterable);

The obvious difference is that the first one is shorter. The important difference is that the first one retains the type parameter of the original object

// Creates a List<int>:
var iterable = [1, 2, 3];

// Prints "List<int>":
print(iterable.toList().runtimeType);
// Creates a List<int>:
var iterable = [1, 2, 3];

// Prints "List<dynamic>":
print(List.from(iterable).runtimeType);

Use of parameters

Use = to separate named parameters from their default values

Due to legacy reasons, Dart allows ":" and "=" as the default value separators for specified parameters. In order to be consistent with the optional positional parameters, use "=".

  void insert(Object item, {int at = 0}) { ... }

The following is not recommended:

  void insert(Object item, {int at: 0}) { ... }

Do not use the explicit default value of null

If the parameter is optional, but no default value is given to it, the language implicitly uses null as the default value, so there is no need to write it

void error([String message]) {
  stderr.write(message ?? '\n');
}

The following is not recommended:

void error([String message = null]) {
  stderr.write(message ?? '\n');
}

variable

Don't explicitly initialize variables to empty

In Dart, variables or fields that are not explicitly initialized are automatically initialized to null. Don't assign null redundantly

  int _nextId;
  
  class LazyId {
    int _id;
  
    int get id {
      if (_nextId == null) _nextId = 0;
      if (_id == null) _id = _nextId++;
  
      return _id;
    }
  }

The following is not recommended:

  int _nextId = null;
  
  class LazyId {
    int _id = null;
  
    int get id {
      if (_nextId == null) _nextId = 0;
      if (_id == null) _id = _nextId++;
  
      return _id;
    }
  }

Avoid storing things you can calculate

When designing a class, you usually want to expose multiple views to the same underlying state. Usually you will see the code that calculates all views in the constructor and then store them:

Wording that should be avoided:

  class Circle {
    num radius;
    num area;
    num circumference;
  
    Circle(num radius)
        : radius = radius,
          area = pi * radius * radius,
          circumference = pi * 2.0 * radius;
  }

The above code problem:

  • Waste of memory
  • The problem with caching is invalidation-how do you know when the cache expires and needs to be recalculated?

The recommended writing is as follows:

  class Circle {
    num radius;
  
    Circle(this.radius);
  
    num get area => pi * radius * radius;
    num get circumference => pi * 2.0 * radius;
  }

Class member

Don't unnecessarily wrap fields in getters and setters

The following is not recommended:

  class Box {
    var _contents;
    get contents => _contents;
    set contents(value) {
      _contents = value;
    }
  }

Prefer final fields to create read-only attributes

Especially for StatelessWidget

Don't use this when you don't need it

The following is not recommended:

  class Box {
    var value;
    
    void clear() {
      this.update(null);
    }
    
    void update(value) {
      this.value = value;
    }
  }

The following is recommended:

  class Box {
    var value;
  
    void clear() {
      update(null);
    }
  
    void update(value) {
      this.value = value;
    }
  }

Constructor

Use the form of initialization whenever possible

The following is not recommended:

  class Point {
    num x, y;
    Point(num x, num y) {
      this.x = x;
      this.y = y;
    }
  }

The following is recommended:

class Point {
  num x, y;
  Point(this.x, this.y);
}

Don't use new

Dart2 makes the new keyword optional

Recommended writing:

  Widget build(BuildContext context) {
    return Row(
      children: [
        RaisedButton(
          child: Text('Increment'),
        ),
        Text('Click!'),
      ],
    );
  }

The following is not recommended:

  Widget build(BuildContext context) {
    return new Row(
      children: [
        new RaisedButton(
          child: new Text('Increment'),
        ),
        new Text('Click!'),
      ],
    );
  }

asynchronous

Prefer async/await instead of original futures

The async/await syntax improves readability and allows you to use all Dart control flow structures in asynchronous code.

  Future<int> countActivePlayers(String teamName) async {
    try {
      var team = await downloadTeam(teamName);
      if (team == null) return 0;
  
      var players = await team.roster;
      return players.where((player) => player.isActive).length;
    } catch (e) {
      log.error(e);
      return 0;
    }
  }

Don't use it when asynchrony is of no use

If you can omit asynchrony without changing the behavior of the function, then do so. ,

  Future afterTwoThings(Future first, Future second) {
    return Future.wait([first, second]);
  }

Not recommended to write:

  Future afterTwoThings(Future first, Future second) async {
    return Future.wait([first, second]);
  }

 

 

 

 

Guess you like

Origin blog.csdn.net/MYBOYER/article/details/89447998