Android集成flutter使用热重载功能

1、在Android原生项目中集成flutter,使用flutter的东西还是很不错的,这里我介绍一下如何使用,以一个demo的形式从开始一步一步介绍,

首先在电脑的某一个盘新建一个文件夹,这里我找到一个本地磁盘,新建一个android_flutter文件夹(这么做的目的是为了让android原生项目和flutter项目在同一级文件夹中,属于同级关系,这个应该都理解吧,为了在android项目中引入flutter时更方便):

Android集成flutter使用热重载功能_第1张图片

好了,这里就开始打开androidstudio,新建一个Android原生项目,这个简单,不多说,主要注意一下,新建的这个项目存储的位置要放在上面新建的文件夹下,

这里截一个图,给大家看一下,

Android集成flutter使用热重载功能_第2张图片

创建完一个android原生项目了,这里在看一下刚创建的项目目录:

Android集成flutter使用热重载功能_第3张图片

下面开始新建一个flutter项目,项目也存储在android_flutter 文件夹下:

注意:这里使用命令创建,打开android项目,在点击Terminal,在控制台中使用 cd命令回到当前android项目的上一级目录(仔细看下图):

Android集成flutter使用热重载功能_第4张图片

可以看到命令之后,当前路径就到了上级目录下,这里使用命令的方式创建一个flutter项目:flutter create -t module flutter_app

Android集成flutter使用热重载功能_第5张图片

然后回车开始创建flutter项目,运行完之后,在回到磁盘文件下就看到了已创建好的两个项目:

Android集成flutter使用热重载功能_第6张图片

说明一下,这里我为什么使用命令创建:因为我开始是使用手动通过 File --> new flutter peoject方法创建,创建好之后,项目中的一些文件夹有问题,比如flutter文件夹下有一个  .android  文件夹,但是通过new 方式创建,就没有,只有一个  android 文件夹 ,前面不带点,具体为什么,不懂,就这么做吧!

好了,这里两个空的项目就建好了,开始下一步操作,

2、编译Flutter工程

此时打开的还是android原生项目,还在命令窗口下,通过cd命令到

cd到Flutter工程目录下的.android目录,执行gradlew脚本
>* 注意:点后面是反斜杠

Android集成flutter使用热重载功能_第7张图片

 

3、在Android工程中加入Flutter Module的依赖

修改Android项目根目录下的setting.gradle:

//加入下面配置
setBinding(new Binding([gradle: this]))
evaluate(new File(
        settingsDir.parentFile,
        'flutter_app/.android/include_flutter.groovy'  //这里是一个路径,注意不要写错
))

Android集成flutter使用热重载功能_第8张图片

 

然后,修改app下的build.gradle:

minSdkVersion 16//至少16

//添加下面配置
    compileOptions {
        sourceCompatibility 1.8
        targetCompatibility 1.8
    }

dependencies {
    ...
    //加入下面配置
    implementation project(':flutter')
}

Android集成flutter使用热重载功能_第9张图片

4、在Android工程中创建Flutter的View

打开MainActivity.class,加入如下代码,

View flutterView = Flutter.createView(
                MainActivity.this, getLifecycle(), "r1");
        FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(
                ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
        addContentView(flutterView, layoutParams);

注意:在activity中创建flutter布局时,用Flutter.createView,然后addContentView到布局中

5、在Flutter工程中创建Widget

这里需要打开flutter项目,所以目前就是同时打开android项目和flutter,

在flutter中的main.dart文件中,删除自动生成的代码,修改为一下代码进行测试:

import 'dart:ui';

import 'package:flutter/material.dart';

void main() => runApp(selectWidget(window.defaultRouteName));

Widget selectWidget(String routeName) {
  switch (routeName) {
    case 'r1':
      return MyFlutterView();//这个是测试activity中添加flutter时用,
    case 'r2':
      return MyFlutterFragment();//这个是测试Fragment中添加flutter时用,
    default:
      return MaterialApp(
        debugShowCheckedModeBanner: false,
        home: Scaffold(
          body: Center(
            child: Text(
              '路由不存在!',
              style: TextStyle(color: Color(0xffff0000)),
            ),
          ),
        ),
      );
  }
}


class MyFlutterView extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      home: Scaffold(
        body: Center(
          child: Card(
            color: Color(0xffff0000),
            shape: RoundedRectangleBorder(
              borderRadius: BorderRadius.all(
                Radius.circular(15.0),
              ),
            ),
            child: Center(
              child: Text(
                'My Flutter View',
                style: TextStyle(
                  color: Color(0xffffffff),
                ),
              ),
            ),
          ),
        ),
      ),
    );
  }
}


class MyFlutterFragment extends StatefulWidget {
  @override
  _MyFlutterFragmentState createState() => _MyFlutterFragmentState();
}

class _MyFlutterFragmentState extends State {
  var _count = 0;

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      home: Scaffold(
        body: Center(
          child: Card(
            color: Color(0xff0000ff),
            shape: RoundedRectangleBorder(
              borderRadius: BorderRadius.all(
                Radius.circular(15.0),
              ),
            ),
            child: Center(
              child: Text(
                'My Flutter Fragment: $_count',
                style: TextStyle(
                  color: Color(0xffffffff),
                  fontSize: 20.0,
                ),
              ),
            ),
          ),
        ),
        floatingActionButton: FloatingActionButton(onPressed: () {
          setState(() {
            _count++;
          });
        },
          child: Icon(Icons.add),),
      ),
    );
  }
}

好了,上面这部分代码既有activity中添加flutter布局方法,也有Fragment中添加flutter的部分,下面会用到,下面就不在单独在flutter中写Fragment,就先放在这里了,

6、让Flutter模块支持热加载

首先在Flutter 项目工程目录下在命令行中执行flutter attach,开始监听flutter。

Android集成flutter使用热重载功能_第10张图片

执行完,它会一直在等待(注意当前我的手机是已经连接电脑的,)

然后,在Android工程中运行程序,运行成功之后,手机会显示flutter中的布局,此时在看flutter项目中Terminal,看到命令已经有所变化,但是当前命令处于等待状态,

Android集成flutter使用热重载功能_第11张图片

这里说明一下,这表示,如果我们要进行布局flutter中的布局,也就是布局要变化,写完之后,直接在flutter项目的这里直接输入 小写r热加载,大写R热重启。

到这里基本就结束在activity中添加flutter了。下面在多说一下在Fragment中添加布局,

首先在android项目中写一个activity,在activity中添加Fragment,然后Fragment布局引入flutter布局

这是activity布局,就一个子控件,

Android集成flutter使用热重载功能_第12张图片

在activity中这样写:

Android集成flutter使用热重载功能_第13张图片

这里android原生项目中的内容就写完了,flutter中的内容在前面已经写完了,也有说明,自己去看,

这里一看看出来在activity添加布局和Fragment中是不一样的,这里是createFragment  

这里因为修改了android原生代码,所以必须重新运行android项目才行,然在修改flutter代码,这个时候如果要使用热重载,还是一样,需要先在flutter项目执行 flutter attach  ,然后通过 大写 R和小写 r 进行热重载,和热重启。

好了,今年就到这里了,在此记录一下,希望对你也有所帮助。

 

你可能感兴趣的:(Android开发,flutter)