使用vscode+flutter开发android程序(入门)

Flutter入门(面向Java/SpringBoot团队,快速上手)

Dart语法非常接近Java,类、泛型、函数、异常、OOP思想基本一致 ,你们团队上手会很快。

Flutter核心概念:一切都是Widget(组件),页面、按钮、文字、布局全是Widget,类似Java的组件/对象。

一、环境搭建(Windows,优先开发安卓APK)

1. 必备软件清单

  1. Git for Windows(加到PATH)
  2. Android Studio(提供Android SDK、模拟器)
  3. VS Code(写Flutter代码,推荐)
  4. Flutter SDK(官网下载压缩包,解压,把flutter\bin加入系统环境变量PATH)>

国内:https://docs.flutter.cn/get-started/install/windows

2. 校验环境

打开PowerShell执行:

复制代码
flutter doctor

它会自动检测缺失依赖,按提示补全。

  • Android部分提示 ✅ 就可以跑安卓模拟器;
  • iOS开发打包IPA必须Mac电脑,Windows只能开发安卓。

3. VS Code插件

搜索安装:Flutter(自动带Dart插件)

  • 快捷键 Ctrl+Shift+P 调出命令面板,可以直接新建Flutter项目

4. 创建项目

复制代码
# 终端执行,新建项目
flutter create bus_app
cd bus_app

# 启动(自动识别模拟器/手机)
flutter run
  • 热重载:按r,不用重启APP,页面实时刷新(开发神器)
  • flutter create --empty bus_app:生成极简空白模板,适合入门

二、项目目录重点(只看核心,其他不用管)

复制代码
bus_app/
├── lib/                # 【全部业务代码在这里】
│   └── main.dart       # 入口文件,程序main函数(类似Java main)
├── pubspec.yaml        # 依赖配置!等价 Maven pom.xml / gradle
├── android/            # 安卓原生工程,打包APK用
├── ios/                # iOS工程(Mac打包IPA)
└── build/              # 编译产物

pubspec.yaml:添加第三方包(网络、websocket、图表),flutter pub get拉取依赖,类似mvn install

三、Dart基础(Java视角快速理解)

复制代码
// main入口,程序起点
void main() {
  runApp(const MyApp()); // 启动APP,根Widget
}

// 无状态组件:页面不会动态变数据(类似静态页面)
class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: '公交运维APP',
      home: Scaffold(
        appBar: AppBar(title: const Text("车辆监控")),
        body: const Center(child: Text("Hello Flutter")),
      ),
    );
  }
}
  • class:和Java类几乎一样,支持继承、构造函数
  • final / const:类似Java final,不可变
  • 两种Widget
    1. StatelessWidget:无状态,页面渲染完不变,静态页面
    2. StatefulWidget:有状态,数据变化自动刷新UI(告警列表、实时车辆数据用这个,重点!)

基础布局(最常用,写页面必学)

  • Column:垂直排列(纵向,类似LinearLayout vertical)
  • Row:水平排列(横向,LinearLayout horizontal)
  • Container:容器,设置宽高、背景、圆角(类似View)
  • Expanded:占剩余空间(权重布局)
  • ListView:滚动列表(你的告警列表、车辆列表核心组件)

示例:垂直布局放文字+按钮

复制代码
Column(
  mainAxisAlignment: MainAxisAlignment.center,
  children: [
    Text("车辆编号:沪B12345"),
    SizedBox(height:20), // 空白间距
    ElevatedButton(
      onPressed: (){
        // 按钮点击事件,类似Java onClick
      },
      child: Text("查看告警"),
    )
  ],
)

四、对接你的SpringBoot后端(重点)

1. 引入http包(GET/POST请求,调用SpringBoot接口)

修改 pubspec.yaml

复制代码
dependencies:
  flutter:
    sdk: flutter
  http: ^1.2.1

终端拉包:

复制代码
flutter pub get

2. 最小Demo:请求SpringBoot接口,获取车辆数据

复制代码
import 'package:http/http.dart' as http;
import 'dart:convert';

// 请求SpringBoot后端接口
Future<List> fetchBusList() async {
  // SpringBoot接口地址
  final res = await http.get(Uri.parse("[http://127.0.0.1:8080/api/bus/list](http://127.0.0.1:8080/api/bus/list)"));
  if(res.statusCode == 200){
    // json解析,和Jackson解析DTO思路一致
    return jsonDecode(res.body);
  }else{
    throw Exception("请求失败");
  }
}

async / await:Dart异步,类似Java CompletableFuture,非常适合网络请求。

3. WebSocket(接收实时车辆告警!你们业务核心)

用包 web_socket_channel,订阅SpringBoot的WebSocket,实时推送告警。

五、打包(Windows)

复制代码
# 打包安卓APK,输出在 build/app/outputs/apk/release/
flutter build apk

iOS IPA打包:只能Mac电脑执行 flutter build ipa

六、推荐学习路线(Java团队按这个顺序学)

  1. Dart基础语法(1天,因为和Java很像)
  2. Widget基础:Text/Button/Container/Row/Column/ListView(2天)
  3. StatefulWidget状态管理(核心,动态告警页面)
  4. Http请求、Json序列化对接SpringBoot(1天)
  5. WebSocket实时数据流(公交告警推送)
  6. 项目架构分层(推荐:数据层repository / 业务逻辑 / UI层,和Spring分层思想对齐)
  7. 进阶:原生插件(需要蓝牙、串口、流媒体时,写Android Java插件)

状态管理入门优先:Provider,简单够用,适合企业运维APP;复杂后可换Bloc。

七、踩坑提前说(你们团队重点注意)

  1. Android模拟器需要开启CPU虚拟化(BIOS打开VT-x),否则跑不起来;
  2. 本地调试访问SpringBoot,不要写127.0.0.1,模拟器要写电脑局域网IP;
  3. 安卓网络权限:AndroidManifest.xml 添加 INTERNET;
  4. Dart空安全:? 可空类型,类似Java的可空判断,新手最容易报错。

八、 flutter build apk一直卡着

执行如下命令

flutter build apk --releasd --verbose

能看到console out的过程,知道错误的原因

一般有如下2个地方要改。

(1)改仓库地址

android/settings.gradle.kts

kts 复制代码
pluginManagement {
    val flutterSdkPath =
        run {
            val properties = java.util.Properties()
            file("local.properties").inputStream().use { properties.load(it) }
            val flutterSdkPath = properties.getProperty("flutter.sdk")
            require(flutterSdkPath != null) { "flutter.sdk not set in local.properties" }
            flutterSdkPath
        }

    includeBuild("$flutterSdkPath/packages/flutter_tools/gradle")

    repositories {
  		 //加这些内容////////////////////////////////==================================
        maven("https://maven.aliyun.com/repository/google")
        maven("https://maven.aliyun.com/repository/central")
        maven("https://maven.aliyun.com/repository/public")
        maven("https://maven.aliyun.com/repository/gradle-plugin")
        /////////////////////////////==========================================
        google()
        mavenCentral()
        gradlePluginPortal()
    }
}

plugins {
    id("dev.flutter.flutter-plugin-loader") version "1.0.0"
    id("com.android.application") version "9.1.0" apply false
    id("org.jetbrains.kotlin.android") version "2.4.0" apply false
}

include(":app")

(2) 改build,不打包模拟器

android/app/build.gradle.kts

kts 复制代码
plugins {
    id("com.android.application")
    // The Flutter Gradle Plugin must be applied after the Android and Kotlin Gradle plugins.
    id("dev.flutter.flutter-gradle-plugin")
}

android {
    namespace = "com.example.flutter_application_1"
    compileSdk = flutter.compileSdkVersion
    ndkVersion = flutter.ndkVersion

    compileOptions {
        sourceCompatibility = JavaVersion.VERSION_17
        targetCompatibility = JavaVersion.VERSION_17
    }

    defaultConfig {
        // TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
        applicationId = "com.example.flutter_application_1"
        // You can update the following values to match your application needs.
        // For more information, see: https://flutter.dev/to/review-gradle-config.
        minSdk = flutter.minSdkVersion
        targetSdk = flutter.targetSdkVersion
        // Uses the version code from pubspec.yaml. When using split APKs, 1000 * ABI_VERSION
        // is added automatically by Flutter. (https://developer.android.com/studio/build/configure-apk-splits#configure-APK-versions)
        // You can force using the value of versionCode by specifying the `-P force-version-code-ignoring-abi=true`
        // flag during build.
        versionCode = flutter.versionCode
        versionName = flutter.versionName
        // ==========新增这一行,只打包arm64-v8a(绝大多数安卓手机)=======================================================
        ndk {
            abiFilters += listOf("arm64-v8a")
        }
        //===============================================================
    }

    buildTypes {
        release {
            // TODO: Add your own signing config for the release build.
            // Signing with the debug keys for now, so `flutter run --release` works.
            signingConfig = signingConfigs.getByName("debug")
        }
    }
}

kotlin {
    compilerOptions {
        jvmTarget = org.jetbrains.kotlin.gradle.dsl.JvmTarget.JVM_17
    }
}

flutter {
    source = "../.."
}
相关推荐
事圆则缓1 小时前
Kotlin学习导航:从知识树走到项目与面试
android·开发语言·kotlin
jason.zeng@15022072 小时前
Flutter 项目标准分层目录(repository/dto/page,对齐后端思想)
flutter
天空之城--2 小时前
近一周Android开发动态:AI编码、Compose与自适应实践
android
mmsx2 小时前
Android 混淆挡不住二次打包:一条完整的攻击链与突破口
android·混淆
聚美智数11 小时前
智能结构化识别-图片结构解析-图像结构化解析-照片结构化解析
android·java·数据库
mmsx16 小时前
Android 插件化架构:40 个 Gradle 模块的拆分、通信与共存
android·kotlin
mmsx16 小时前
Android 不改一行源码:用 AspectJ 做三类拦截
android·kotlin
TST-魚爷16 小时前
易视讯会议摄像头 + 全向麦克风实操讲解稿
android·电脑·钉钉·腾讯会议·zoom会议