初识Flutter

453 阅读8分钟

Flutter 整体简单介绍

Flutter 是由 Google 开发的开源 UI 软件开发工具包,用于构建跨平台的高性能程序。它允许开发者使用单一代码库创建适用于 iOS、Android、Web 和桌面平台的应用


目录

  1. Flutter 简介
  2. 开发环境搭建
  3. 创建你的第一个 Flutter 项目
  4. 项目结构解析
  5. 基础 Widgets
  6. 布局与设计
  7. 用户输入处理
  8. 导航与路由
  9. 状态管理
  10. 网络请求与数据处理
  11. 持久化存储
  12. 使用插件与包
  13. 构建与部署应用
  14. 调试与测试
  15. 性能优化
  16. 附加资源

1. Flutter 简介

Flutter 是一个由 Google 推出的开源 UI 软件开发工具包,旨在帮助开发者以高效的方式构建跨平台应用。它使用 Dart 编程语言,并提供丰富的预制 Widgets,使开发者能够轻松创建漂亮且高性能的用户界面。

主要特点:

  • 跨平台支持:同一代码库可部署到 iOS、Android、Web、Windows、macOS 和 Linux。
  • 高性能:直接编译为原生代码,性能接近原生应用。
  • 丰富的 Widgets:内置丰富的 Material Design 和 Cupertino(iOS 风格) Widgets。
  • 热重载:快速查看代码更改的效果,大大提高开发效率。

2. 开发环境搭建

2.1 安装 Flutter SDK

  1. 下载 Flutter SDK

    前往 Flutter 官方网站 下载适用于你操作系统的 Flutter SDK 压缩包。

  2. 解压并配置路径

    将下载的压缩包解压到你选择的目录,并将 Flutter 的 bin 目录添加到系统的环境变量中。

    示例(macOS/Linux):

    export PATH="$PATH:`pwd`/flutter/bin"
    

    示例(Windows):

    flutter\bin 路径添加到系统环境变量的 PATH 中。

  3. 验证安装

    打开终端或命令提示符,运行以下命令检查 Flutter 是否安装成功:

    flutter doctor
    

    这个命令会检查你的开发环境,并列出需要配置的部分。

2.2 安装 Android Studio

  1. 下载并安装 Android Studio

    前往 Android Studio 官方网站 下载并安装最新版本的 Android Studio。

  2. 配置 Android Studio

    • 安装 Flutter 和 Dart 插件
      1. 打开 Android Studio。

      2. 点击 File > Settings(Windows)或 Android Studio > Preferences(macOS)。

      3. 在左侧菜单中选择 Plugins

      4. 搜索 Flutter,点击 Install。安装 Flutter 插件时,Dart 插件会自动安装。

      5. 安装完成后,重启 Android Studio。

2.3 设置 Android 模拟器

  1. 启动 AVD Manager

    在 Android Studio 中,点击工具栏的 AVD Manager 图标,或通过 Tools > AVD Manager 访问。

  2. 创建新的虚拟设备

    点击 Create Virtual Device,选择设备型号(如 Pixel 4),点击 Next

  3. 选择系统映像

    选择一个 Android 系统映像(建议使用最新稳定版),点击 Download(如果尚未下载),然后点击 Next

  4. 完成设置

    点击 Finish 创建虚拟设备。

  5. 启动模拟器

    在 AVD Manager 中,点击刚创建的虚拟设备旁边的 播放 按钮启动模拟器。


3. 创建你的第一个 Flutter 项目

3.1 使用 Android Studio 创建项目

  1. 启动 Android Studio

    打开 Android Studio,如果是首次启动,可能需要一些时间进行初始化。

  2. 新建 Flutter 项目

    点击 Start a new Flutter project

  3. 选择项目类型

    选择 Flutter Application,点击 Next

  4. 配置项目

    填写以下信息:

    • Project name:输入项目名称(例如 my_first_flutter_app)。
    • Flutter SDK path:确认 Flutter SDK 路径(应自动填充)。
    • Project location:选择项目存储位置。
    • Description:可选,输入项目描述。
  5. 选择平台语言

    • Android language:选择 KotlinJava
    • iOS language:选择 SwiftObjective-C

    通常选择默认的 KotlinSwift

  6. 完成创建

    点击 Finish,Android Studio 将自动创建并打开项目。

3.2 运行项目

  1. 选择设备

    在 Android Studio 中,确保你已启动模拟器或连接了真实设备。点击工具栏上的设备选择器,选择目标设备。

  2. 运行应用

    点击工具栏上的绿色运行按钮(▶️),应用将被编译并部署到选定的设备上。

  3. 查看效果

    应用启动后,你将看到一个简单的计数器应用,点击按钮可以增加计数。


4. 项目结构解析

Flutter 项目包含多个文件和文件夹,以下是主要部分的介绍:

my_first_flutter_app/
├── android/
├── build/
├── ios/
├── lib/
│   └── main.dart
├── test/
├── pubspec.yaml
└── README.md

4.1 关键目录与文件

  • android/:包含 Android 平台相关的配置文件和源代码。
  • ios/:包含 iOS 平台相关的配置文件和源代码。
  • lib/:存放 Dart 代码,是应用的主要代码库。
    • main.dart:应用的入口文件,定义了应用的启动逻辑和根 Widget。
  • test/:存放测试代码。
  • pubspec.yaml:项目配置文件,定义了应用的依赖、资源等。
  • README.md:项目说明文件。

5. 基础 Widgets

Widgets 是 Flutter 的核心构建块,几乎所有东西都是 Widget。理解 Widgets 的使用是开发 Flutter 应用的基础。

5.1 Stateless Widget vs Stateful Widget

Stateless Widget
  • 定义:不可变的 Widget,一旦构建后不会改变其状态。
  • 适用场景:显示静态内容,如图标、文本等。

示例:

import 'package:flutter/material.dart';

class MyStatelessWidget extends StatelessWidget {
  final String title;

  MyStatelessWidget({required this.title});

  @override
  Widget build(BuildContext context) {
    return Text(title);
  }
}
Stateful Widget
  • 定义:可变的 Widget,具有内部状态,可以在生命周期中改变。
  • 适用场景:需要动态更新内容的 Widget,如表单、动画等。

示例:

import 'package:flutter/material.dart';

class MyStatefulWidget extends StatefulWidget {
  final String title;

  MyStatefulWidget({required this.title});

  @override
  _MyStatefulWidgetState createState() => _MyStatefulWidgetState();
}

class _MyStatefulWidgetState extends State<MyStatefulWidget> {
  int counter = 0;

  void _incrementCounter() {
    setState(() {
      counter++;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        Text(widget.title),
        Text('Counter: $counter'),
        ElevatedButton(
          onPressed: _incrementCounter,
          child: Text('Increment'),
        ),
      ],
    );
  }
}

6. 布局与设计

布局是 Flutter 应用设计的关键部分,掌握布局 Widgets 可以帮助你创建灵活且美观的界面。

6.1 常用布局 Widgets

  • Container:基本的布局 Widget,可以设置边距、填充、背景颜色等。
  • RowColumn:水平和垂直布局容器,用于排列子 Widgets。
  • Stack:叠加布局,允许子 Widgets 层叠显示。
  • ExpandedFlexible:用于在 Row 和 Column 中调整子 Widgets 的占用空间。
  • PaddingMargin:设置内边距和外边距。

示例:使用 Row 和 Column 创建布局

import 'package:flutter/material.dart';

class MyLayoutWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        Row(
          children: [
            Text('Hello'),
            SizedBox(width: 10),
            Text('World'),
          ],
        ),
        Container(
          padding: EdgeInsets.all(16),
          color: Colors.blue,
          child: Text('This is a container'),
        ),
      ],
    );
  }
}

6.2 响应式设计

Flutter 支持响应式设计,通过使用布局 Widgets 和 MediaQuery 可以适应不同屏幕尺寸和方向。

示例:根据屏幕宽度调整布局

import 'package:flutter/material.dart';

class ResponsiveLayout extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    // 获取屏幕宽度
    double screenWidth = MediaQuery.of(context).size.width;

    return Scaffold(
      appBar: AppBar(title: Text('Responsive Layout')),
      body: screenWidth > 600
          ? Row(
              children: [
                Expanded(child: Text('Sidebar')),
                Expanded(child: Text('Content')),
              ],
            )
          : Column(
              children: [
                Text('Content'),
                Text('Sidebar'),
              ],
            ),
    );
  }
}

7. 用户输入处理

用户输入是应用互动的重要部分,Flutter 提供了多种控件来处理用户输入。

7.1 表单与输入控件

  • TextField:用于单行文本输入。
  • TextFormField:集成了表单验证功能的文本输入。
  • CheckboxRadioSwitch:用于选择性输入。
  • DropdownButton:下拉选择菜单。

示例:简单表单

import 'package:flutter/material.dart';

class MyForm extends StatefulWidget {
  @override
  _MyFormState createState() => _MyFormState();
}

class _MyFormState extends State<MyForm> {
  final _formKey = GlobalKey<FormState>();
  String _name = '';

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('My Form')),
      body: Padding(
        padding: EdgeInsets.all(16),
        child: Form(
          key: _formKey,
          child: Column(
            children: [
              TextFormField(
                decoration: InputDecoration(labelText: 'Name'),
                onSaved: (value) {
                  _name = value ?? '';
                },
                validator: (value) {
                  if (value == null || value.isEmpty) {
                    return 'Please enter your name';
                  }
                  return null;
                },
              ),
              SizedBox(height: 20),
              ElevatedButton(
                onPressed: () {
                  if (_formKey.currentState!.validate()) {
                    _formKey.currentState!.save();
                    // 处理数据
                    print('Name: $_name');
                  }
                },
                child: Text('Submit'),
              ),
            ],
          ),
        ),
      ),
    );
  }
}

8. 导航与路由

导航是 Flutter 应用中管理页面切换的机制。Flutter 提供了多种方式来实现页面导航。

8.1 使用 Navigator 进行导航

示例:基本导航

import 'package:flutter/material.dart';

class FirstPage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('First Page'),
      ),
      body: Center(
        child: ElevatedButton(
          child: Text('Go to Second Page'),
          onPressed: () {
            Navigator.push(
              context,
              MaterialPageRoute(builder: (context) => SecondPage()),
            );
          },
        ),
      ),
    );
  }
}

class SecondPage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Second Page'),
      ),
      body: Center(
        child: ElevatedButton(
          child: Text('Go Back'),
          onPressed: () {
            Navigator.pop(context);
          },
        ),
      ),
    );
  }
}

8.2 命名路由

示例:使用命名路由

  1. 定义路由

    void main() {
      runApp(MaterialApp(
        initialRoute: '/',
        routes: {
          '/': (context) => FirstPage(),
          '/second': (context) => SecondPage(),
        },
      ));
    }
    
  2. 导航到命名路由

    ElevatedButton(
      child: Text('Go to Second Page'),
      onPressed: () {
        Navigator.pushNamed(context, '/second');
      },
    );
    

9. 状态管理

状态管理是 Flutter 开发中一个重要的主题,特别是在构建复杂应用时。Flutter 提供了多种状态管理解决方案,下面介绍最常用的两种:setStateProvider

9.1 setState

setState 是 Flutter 中最基本的状态管理方法,适用于管理局部状态。

示例:使用 setState 管理状态

import 'package:flutter/material.dart';

class CounterPage extends StatefulWidget {
  @override
  _CounterPageState createState() => _CounterPageState();
}

class _CounterPageState extends State<CounterPage> {
  int _counter = 0;

  void _incrementCounter() {
    setState(() {  // 通知 Flutter 更新 UI
      _counter++;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        appBar: AppBar(title: Text('Counter')),
        body: Center(child: Text('Counter: $_counter')),
        floatingActionButton: FloatingActionButton(
          onPressed: _incrementCounter,
          child: Icon(Icons.add),
        ));
  }
}

9.2 Provider

Provider 是一个更为强大且灵活的状态管理解决方案,适用于跨多个 Widget 管理共享状态。

步骤:

  1. 添加依赖

    pubspec.yaml 中添加 provider 依赖:

    dependencies:
      flutter:
        sdk: flutter
      provider: ^6.0.0
    

    然后运行 flutter pub get 安装依赖。

  2. 创建状态类

    import 'package:flutter/foundation.dart';
    
    class Counter with ChangeNotifier {
      int _count = 0;
    
      int get count => _count;
    
      void increment() {
        _count++;
        notifyListeners();  // 通知监听器更新
      }
    }
    
  3. 提供状态

    在应用的根 Widget 中提供状态:

    import 'package:flutter/material.dart';
    import 'package:provider/provider.dart';
    import 'counter.dart';  // 导入 Counter 类
    
    void main() {
      runApp(
        ChangeNotifierProvider(
          create: (context) => Counter(),
          child: MyApp(),
        ),
      );
    }
    
    class MyApp extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return MaterialApp(
          home: CounterPage(),
        );
      }
    }
    
  4. 消费状态

    在需要的地方使用 ConsumerProvider.of 来访问和修改状态。

    import 'package:flutter/material.dart';
    import 'package:provider/provider.dart';
    import 'counter.dart';  // 导入 Counter 类
    
    class CounterPage extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(title: Text('Provider Counter')),
          body: Center(
            child: Consumer<Counter>(
              builder: (context, counter, child) {
                return Text('Counter: ${counter.count}');
              },
            ),
          ),
          floatingActionButton: FloatingActionButton(
            onPressed: () {
              Provider.of<Counter>(context, listen: false).increment();
            },
            child: Icon(Icons.add),
          ),
        );
      }
    }
    

10. 网络请求与数据处理

在现代应用中,网络请求和数据处理是必不可少的。Flutter 提供了强大的网络功能,可以轻松实现这些需求。

10.1 HTTP 请求

使用 http 包可以轻松发送 HTTP 请求。

步骤:

  1. 添加依赖

    pubspec.yaml 中添加 http 依赖:

    dependencies:
      flutter:
        sdk: flutter
      http: ^0.13.4
    

    然后运行 flutter pub get 安装依赖。

  2. 发送请求

    import 'package:flutter/material.dart';
    import 'package:http/http.dart' as http;
    import 'dart:convert';
    
    class FetchDataPage extends StatefulWidget {
      @override
      _FetchDataPageState createState() => _FetchDataPageState();
    }
    
    class _FetchDataPageState extends State<FetchDataPage> {
      String data = 'Fetching data...';
    
      @override
      void initState() {
        super.initState();
        fetchData();
      }
    
      Future<void> fetchData() async {
        final response = await http.get(Uri.parse('https://jsonplaceholder.typicode.com/posts/1'));
        if (response.statusCode == 200) {
          setState(() {
            data = json.decode(response.body)['title'];
          });
        } else {
          setState(() {
            data = 'Failed to fetch data';
          });
        }
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(title: Text('Fetch Data')),
          body: Center(child: Text(data)),
        );
      }
    }
    

10.2 JSON 解析

解析 JSON 数据是处理网络请求返回数据的重要部分。Flutter 使用 Dart 的 dart:convert 库进行 JSON 解析。

示例:解析复杂 JSON

import 'dart:convert';

class Post {
  final int userId;
  final int id;
  final String title;
  final String body;

  Post({required this.userId, required this.id, required this.title, required this.body});

  factory Post.fromJson(Map<String, dynamic> json) {
    return Post(
      userId: json['userId'],
      id: json['id'],
      title: json['title'],
      body: json['body'],
    );
  }
}

Future<Post> fetchPost() async {
  final response = await http.get(Uri.parse('https://jsonplaceholder.typicode.com/posts/1'));

  if (response.statusCode == 200) {
    return Post.fromJson(json.decode(response.body));
  } else {
    throw Exception('Failed to load post');
  }
}

11. 持久化存储

应用通常需要保存用户数据或应用状态,Flutter 提供了多种持久化存储方案。

11.1 Shared Preferences

适用于存储简单的键值对,如用户设置、登录状态等。

步骤:

  1. 添加依赖

    pubspec.yaml 中添加 shared_preferences 依赖:

    dependencies:
      flutter:
        sdk: flutter
      shared_preferences: ^2.0.11
    

    然后运行 flutter pub get 安装依赖。

  2. 使用 Shared Preferences

    import 'package:flutter/material.dart';
    import 'package:shared_preferences/shared_preferences.dart';
    
    class SharedPreferencesPage extends StatefulWidget {
      @override
      _SharedPreferencesPageState createState() => _SharedPreferencesPageState();
    }
    
    class _SharedPreferencesPageState extends State<SharedPreferencesPage> {
      String _value = 'No data';
    
      @override
      void initState() {
        super.initState();
        _loadData();
      }
    
      Future<void> _loadData() async {
        final prefs = await SharedPreferences.getInstance();
        setState(() {
          _value = prefs.getString('my_key') ?? 'No data';
        });
      }
    
      Future<void> _saveData() async {
        final prefs = await SharedPreferences.getInstance();
        await prefs.setString('my_key', 'Hello, SharedPreferences!');
        _loadData();
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(title: Text('Shared Preferences')),
          body: Center(child: Text(_value)),
          floatingActionButton: FloatingActionButton(
            onPressed: _saveData,
            child: Icon(Icons.save),
          ),
        );
      }
    }
    

11.2 SQLite

适用于需要存储结构化数据的场景,如本地数据库。

步骤:

  1. 添加依赖

    pubspec.yaml 中添加 sqflitepath 依赖:

    dependencies:
      flutter:
        sdk: flutter
      sqflite: ^2.0.0+4
      path: ^1.8.0
    

    然后运行 flutter pub get 安装依赖。

  2. 使用 SQLite

    import 'package:flutter/material.dart';
    import 'package:sqflite/sqflite.dart';
    import 'package:path/path.dart';
    
    class SQFLitePage extends StatefulWidget {
      @override
      _SQFLitePageState createState() => _SQFLitePageState();
    }
    
    class _SQFLitePageState extends State<SQFLitePage> {
      Database? _database;
      List<Map<String, dynamic>> _items = [];
    
      @override
      void initState() {
        super.initState();
        _initDatabase();
      }
    
      Future<void> _initDatabase() async {
        String path = join(await getDatabasesPath(), 'my_database.db');
        _database = await openDatabase(
          path,
          onCreate: (db, version) {
            return db.execute(
              "CREATE TABLE items(id INTEGER PRIMARY KEY, name TEXT)",
            );
          },
          version: 1,
        );
        _loadItems();
      }
    
      Future<void> _loadItems() async {
        final List<Map<String, dynamic>> maps = await _database!.query('items');
        setState(() {
          _items = maps;
        });
      }
    
      Future<void> _addItem(String name) async {
        await _database!.insert(
          'items',
          {'name': name},
          conflictAlgorithm: ConflictAlgorithm.replace,
        );
        _loadItems();
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(title: Text('SQLite')),
          body: ListView.builder(
            itemCount: _items.length,
            itemBuilder: (context, index) {
              return ListTile(
                title: Text(_items[index]['name']),
              );
            },
          ),
          floatingActionButton: FloatingActionButton(
            onPressed: () => _addItem('Item ${_items.length + 1}'),
            child: Icon(Icons.add),
          ),
        );
      }
    }
    

12. 使用插件与包

Flutter 拥有丰富的插件和包,可以扩展应用的功能。以下介绍如何使用和创建插件。

12.1 使用插件

步骤:

  1. 搜索插件

    pub.dev 搜索所需的插件。

  2. 添加依赖

    pubspec.yaml 中添加插件依赖。例如,添加 url_launcher 插件:

    dependencies:
      flutter:
        sdk: flutter
      url_launcher: ^6.0.9
    
  3. 安装依赖

    运行 flutter pub get 安装依赖。

  4. 使用插件

    import 'package:flutter/material.dart';
    import 'package:url_launcher/url_launcher.dart';
    
    class URLLauncherPage extends StatelessWidget {
      _launchURL() async {
        const url = 'https://flutter.dev';
        if (await canLaunch(url)) {
          await launch(url);
        } else {
          throw 'Could not launch $url';
        }
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(title: Text('URL Launcher')),
          body: Center(
            child: ElevatedButton(
              onPressed: _launchURL,
              child: Text('Open Flutter Website'),
            ),
          ),
        );
      }
    }
    

12.2 创建自定义插件

如果现有插件无法满足需求,可以创建自定义插件。

步骤:

  1. 创建插件项目

    在终端中运行以下命令创建插件模板:

    flutter create --template=plugin my_custom_plugin
    
  2. 实现原生代码

    android/ios/ 目录下实现原生功能。

  3. 导出 Dart 接口

    lib/my_custom_plugin.dart 中定义 Dart 接口,调用原生代码。

  4. 发布插件

    将插件发布到 pub.dev 或私有仓库,供其他项目使用。


13. 构建与部署应用

完成应用开发后,需要进行构建和部署,以便发布给用户使用。

13.1 构建 APK(Android)

  1. 配置签名

    android/app 目录下创建 key.properties 文件,配置签名密钥。

  2. 修改 build.gradle

    配置签名信息。

  3. 构建 APK

    在终端中运行:

    flutter build apk --release
    

    构建完成后,APK 文件位于 build/app/outputs/flutter-apk/app-release.apk

13.2 构建 iOS 应用

  1. 配置签名

    在 Xcode 中配置应用的签名和证书。

  2. 构建应用

    在终端中运行:

    flutter build ios --release
    

    或者在 Xcode 中选择 Product > Archive 进行构建和发布。

13.3 部署到 App Store 和 Google Play

  • Google Play

    1. 创建 Google Play 开发者账户。
    2. 上传 APK 文件,并填写应用信息。
    3. 提交审核。
  • App Store

    1. 创建 Apple Developer 账户。
    2. 使用 Xcode 上传应用。
    3. 在 App Store Connect 中填写应用信息。
    4. 提交审核。

14. 调试与测试

确保应用的质量和稳定性,调试与测试是必不可少的步骤。

14.1 调试

  • 使用 Flutter DevTools

    提供性能分析、Widget 检查、内存监控等功能。

  • 断点调试

    在 Android Studio 中设置断点,逐步执行代码。

14.2 测试

单元测试

用于测试单个函数或类的逻辑。

示例:

import 'package:flutter_test/flutter_test.dart';
import 'package:my_app/counter.dart';

void main() {
  test('Counter value should start at 0', () {
    final counter = Counter();
    expect(counter.value, 0);
  });

  test('Counter value should increment', () {
    final counter = Counter();
    counter.increment();
    expect(counter.value, 1);
  });
}
Widget 测试

用于测试单个 Widget 的 UI 及其交互。

示例:

import 'package:flutter/material.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:my_app/counter_page.dart';

void main() {
  testWidgets('Counter increments smoke test', (WidgetTester tester) async {
    await tester.pumpWidget(MaterialApp(home: CounterPage()));

    expect(find.text('Counter: 0'), findsOneWidget);
    expect(find.text('Counter: 1'), findsNothing);

    await tester.tap(find.byIcon(Icons.add));
    await tester.pump();

    expect(find.text('Counter: 0'), findsNothing);
    expect(find.text('Counter: 1'), findsOneWidget);
  });
}
集成测试

用于测试整个应用的交互和功能。

步骤:

  1. 添加依赖

    pubspec.yaml 中添加 integration_test 依赖。

  2. 编写测试

    创建 integration_test/app_test.dart 并编写测试代码。

  3. 运行测试

    使用命令行或 Android Studio 运行集成测试。


15. 性能优化

优化 Flutter 应用的性能,确保流畅的用户体验。

15.1 使用 const 构造函数

尽可能使用 const 声明不可变的 Widgets,减少不必要的重建。

示例:

const Text('Hello, Flutter!'),

15.2 减少 Widget 重绘

  • 避免在不必要的地方调用 setState
  • 使用 const Widgets
  • 分离大型 Widget,将其拆分为更小的部分。

15.3 使用懒加载技术

对于长列表,使用 ListView.builderGridView.builder,按需构建 Widgets。

示例:

ListView.builder(
  itemCount: items.length,
  itemBuilder: (context, index) {
    return ListTile(title: Text(items[index]));
  },
);

15.4 使用缓存

  • 图片缓存:使用 CachedNetworkImage 插件缓存网络图片。
  • 数据缓存:缓存常用数据,减少重复的网络请求。

16. 附加资源

官方文档

在线教程与课程

社区与支持

插件库

  • pub.dev:Flutter 和 Dart 的官方包管理网站。