Android程序员的Flutter学习笔记 (2)

Flutter同样支持, CustomPaint作为一个 Widgets就支持传入一个实现CustomPainter抽象类的参数, 而CustomPainter的抽象方法也类似于Android View的onDraw.

void paint(Canvas canvas, Size size) bool shouldRepaint(CustomPainter oldDelegate) 如何自定义View

不用继承, 而使用类似Android ViewGroup的办法, 通过组合(composing)与封装的方法来实现, 通过小Widgets组合成需要的新Widgets.

页面跳转怎么办, 四大组件之一的Intent跑哪里去了

貌似在讲类似于Activity的MaterialApp的时候剧透了...

就是使用Navigator与Routes来实现界面跳转, 实际上是整个Widgets的替换.

routes: <String, WidgetBuilder> { '/a': (BuildContext context) => MyPage(title: 'page A'), '/b': (BuildContext context) => MyPage(title: 'page B'), '/c': (BuildContext context) => MyPage(title: 'page C'), } Navigator.of(context).pushNamed('/b'); 如何处理外部的Intent

实际上还是需要在Flutter App的Android壳子中注册这个filter, 然后在FlutterActivity中拿到存下来,

FlutterView初始化后再通过Bridge, 官方叫MethodChannel从Java里获取,进行下一步逻辑.

可以看个简单的例子.

new MethodChannel(getFlutterView(), "app.channel.shared.data").setMethodCallHandler( new MethodCallHandler() { @Override public void onMethodCall(MethodCall call, MethodChannel.Result result) { if (call.method.contentEquals("getSharedText")) { result.success(sharedText); sharedText = null; } } }); getSharedText() async { var sharedData = await platform.invokeMethod("getSharedText"); if (sharedData != null) { setState(() { dataShared = sharedData; }); } } 常用的startActivityForResult怎么办.

这个Flutter有完全对应的办法, 而且用起来很方便, 结合之前说的页面跳转:

Map xxx = await Navigator.of(context).pushNamed('/xxx'); Navigator.of(context).pop({xxx}); 异步怎么办, runOnUiThread()哪里去了

Flutter有点像JS, 是一个单线程模式, 所以只是通过模拟来构建简单的异步, 关键字就是类似于kotlin coroutines一样, 通过await+async来处理.

如:

loadData() async { response = await http.get(xxx); setState(() {xxx}); }

但是由于它的单线程, 所以无法做很长的阻塞操作, 像http请求的延迟正常情况可能都是毫秒级的, 但是数据的处理等, 可能就得秒级了.

这也是RN在线程方面的做android程序的一个痛点, Flutter采用了比较容易想到的曲线救国的办法, 提供了一个叫Isolate的对象, 它实际是一个基于socket的数据通道, 相当于把数据放在一个独立的进程进行处理, 然后再通过socket发送回程序进程, 还记得进程间通信办法之一的管道吗...

具体API可以参考文档1...,2....

Flutter 替代OkHttp的网络库

自带了http库, 直接http.get(url), 在线程部分的代码实例里也有涉及.

通过类似gradle的文件pubspec.yaml引入.

dependencies: ... http: ^0.12

^表示不升大版本, 并取最新版本, 比gradle的+要范围更小.

常见的LCE(Loading Content Error)里面的Loading怎么show

Flutter有一个widget叫做ProgressIndicator, 比如我们期望有一个转圈圈的Loading界面在数据加载出来之前.

我们就可以通过StatefulWidgets, 根据数据, 或者List Widgets的个数 (如果是显示一个List的话)来判断是否显示Loading, 使用子类CircularProgressIndicator, 来替换页面的Widgets.

当然也是通过setState(() {...})来触发界面刷新的, 可以在initState()内触发加载数据的异步操作.

不同分辨率的图片资源怎么放

这个有点像iOS了, 即有1x,2x,3x:

images/my_icon.png // Base: 1.0x image images/2.0x/my_icon.png // 2.0x image images/3.0x/my_icon.png // 3.0x image

不一样的一点还需要添加到类似gradle的文件pubspec.yaml里.

assets: - images/my_icon.jpeg 字符串怎么存储

Flutter没有像Android的string.xml的东西, 目前来说最好的就就是存成静态字符串.

class Strings { static String welcomeMessage = "Welcome To Flutter"; } Text(Strings.welcomeMessage) Gradle变成什么了

前面说网络库, 图片资源的时候提到过, 提供了一个叫pubspec.yaml的文件, 具体支持的规则可以查看这个文档.

Fragment与Activity呢?

之前做过类比, 如MaterialApp有点类似于Activity, 而Scaffold都点类似Fragment, 实际上他们两个都是Flutter的Widgets, 也就是说其实只有View的概念了.

还有生命周期吗?

Flutter有一个叫做WidgetsBinding的可以提供类似生命周期的回调.

四种状态inactive (iOS专用), paused(相当于onPause, 退后台), resumed(相当于onPostResume, 到前台), suspending(android专用, 相当于onStop).

一般在StatefulWidgets的State中注册与反注册.

@override void initState() { super.initState(); WidgetsBinding.instance.addObserver(this); } @override void dispose() { WidgetsBinding.instance.removeObserver(this); super.dispose(); } ScrollView vs ListView

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wpgywx.html