![](https://img-blog.csdnimg.cn/5b24b7dde5f54643b08ecef0f7ed326d.png?x-oss-process=image/resize,m_fixed,h_224,w_224)
Flutter
文章平均质量分 75
Flutter是谷歌的移动UI框架,可以快速在iOS和Android上构建高质量的原生用户界面。 Flutter可以与现有的代码一起工作。在全世界,Flutter正在被越来越多的开发者和组织使用,并且Flutter是完全免费、开源的。
风雨「83」
木秀于林,风必崔之。出外言行,慎之慎之!
展开
-
62、Flutter插件通信iOS,Android实现过程<二>
前言61、Flutter插件通信原理<一>_风雨「83」的博客-CSDN博客Flutter与原生通讯 - Flutter Plugin - 知乎前言Flutter优势主要体现在UI上--高性能且跨平台表现一致。但是针对平台(Android、IOS)的实现,如:获取电量、判断WiFi使用、调起WebView加载网页等,得调用特定平台的API包。Flutter Plugin就是为调用平台API而生。下文中所提及到的"平台"指的是Android、IOS两端。介绍Flutter Plugin包含针对Androi原创 2022-04-19 17:22:04 · 4477 阅读 · 0 评论 -
61、Flutter插件通信原理<一>
Flutter与原生通讯 - Flutter Plugin - 知乎前言Flutter优势主要体现在UI上--高性能且跨平台表现一致。但是针对平台(Android、IOS)的实现,如:获取电量、判断WiFi使用、调起WebView加载网页等,得调用特定平台的API包。Flutter Plugin就是为调用平台API而生。下文中所提及到的"平台"指的是Android、IOS两端。介绍Flutter Plugin包含针对Android(Java或Kotlin代码)或iOS(Objecti原创 2022-04-12 08:19:16 · 3776 阅读 · 0 评论 -
60、Flutter核心原理--绘制Compositing
本节我们来介绍一下 flushCompositingBits()。现在,我们再来回顾一下Flutter的渲染管线:void drawFrame(){ pipelineOwner.flushLayout(); pipelineOwner.flushCompositingBits(); pipelineOwner.flushPaint(); renderView.compositeFrame() ...//省略 } 其中只有 flushCompositingBits() 还没原创 2022-02-24 08:55:53 · 11241 阅读 · 0 评论 -
59、Flutter核心原理--组件树绘制流程
绘制相关实现在渲染对象 RenderObject 中,RenderObject 中和绘制相关的主要属性有:layer isRepaintBoundary(类型bool) needsCompositing (类型bool)RepaintBoundaryFlutter 自带了一个 RepaintBoundary 组件,它的功能其实就是向组件树中插入一个绘制边界节点。组件树绘制流程我们先讲一下Flutter绘制组件树的一般流程,注意,并非完整流程,因为我们暂时会忽略子树中需要“层合成”(原创 2022-02-21 17:19:48 · 11282 阅读 · 0 评论 -
58、Flutter核心原理--绘制原理及Layer
Flutter 绘制原理Flutter中和绘制相关的对象有三个,分别是Canvas、Layer 和 Scene:Canvas:封装了Flutter Skia各种绘制指令,比如画线、画圆、画矩形等指令。 Layer:分为容器类和绘制类两种;暂时可以理解为是绘制产物的载体,比如调用 Canvas 的绘制 API 后,相应的绘制产物被保存在 PictureLayer.picture 对象中。 Scene:屏幕上将要要显示的元素。在上屏前,我们需要将Layer中保存的绘制产物关联到 Scene 上。F原创 2022-02-18 16:37:52 · 10303 阅读 · 0 评论 -
57、Flutter核心原理--布局Layout过程
布局(Layout)过程Layout(布局)过程主要是确定每一个组件的布局信息(大小和位置),Flutter 的布局过程如下:父节点向子节点传递约束(constraints)信息,限制子节点的最大和最小宽高。 子节点根据约束信息确定自己的大小(size)。 父节点根据特定布局规则(不同布局组件会有不同的布局算法)确定每一个子节点在父节点布局空间中的位置,用偏移 offset 表示。 递归整个过程,确定出每一个节点的位置的大小和位置。可以看到,组件的大小是由自身决定的,而组件的位置是由父组件决原创 2022-02-16 11:29:43 · 10920 阅读 · 0 评论 -
56、Flutter核心原理--Flutter启动流程和渲染管线
启动Flutter的入口在"lib/main.dart"的main()函数中,它是Dart应用程序的起点。在Flutter应用中,main()函数最简单的实现如下:void main() => runApp(MyApp());可以看main()函数只调用了一个runApp()方法,我们看看runApp()方法中都做了什么:void runApp(Widget app) { WidgetsFlutterBinding.ensureInitialized() ..attac原创 2022-02-15 11:20:19 · 10452 阅读 · 0 评论 -
55、Flutter核心原理--Element、BuildContext和RenderObject
Element我们知道最终的UI树其实是由一个个独立的Element节点构成。组件最终的Layout、渲染都是通过RenderObject来完成的,从创建到渲染的大体流程是:根据Widget生成Element,然后创建相应的RenderObject并关联到Element.renderObject属性上,最后再通过RenderObject来完成布局排列和绘制。Element就是Widget在UI树具体位置的一个实例化对象,大多数Element只有唯一的renderObject,但还有一些Element原创 2022-02-14 09:12:04 · 10348 阅读 · 0 评论 -
54、Flutter核心原理--Flutter UI 框架(Framework)
Flutter 从上到下分为框架层、引擎层和嵌入层三层。开发者基本上都是与框架层打交道。术语UI框架(UI Framework)特指:基于一个平台,在此平台上实现一个能快速开发GUI(图形用户接口)的框架,这里的平台特指操作系统,如Android、iOS或者Windows、macOS。通常来讲平台提供的都是图形 API 都非常的基础,通常就是一个和 Canvas 差不多基础的绘制接口,如果没有UI 框架的封装,可以想象一下,如果没有UI框架的封装,直接用 Canvas 来构建用户界面将会是怎样的一个体验原创 2022-02-10 21:25:24 · 12244 阅读 · 0 评论 -
53、Flutter之通知 Notification
通知(Notification)是Flutter中一个重要的机制,在widget树中,每一个节点都可以分发通知,通知会沿着当前节点向上传递,所有父节点都可以通过NotificationListener来监听通知。Flutter中将这种由子向父的传递通知的机制称为通知冒泡(Notification Bubbling)。通知冒泡和用户触摸事件冒泡是相似的,但有一点不同:通知冒泡可以中止,但用户触摸事件不行。Flutter中很多地方使用了通知,如前面介绍的 Scrollable 组件,它在滑动时就会分发滚动通原创 2022-02-10 08:35:07 · 14461 阅读 · 0 评论 -
52、Flutter之事件总线
在 App 中,我们经常会需要一个广播机制,用以跨页面事件通知,比如一个需要登录的 App 中,页面会关注用户登录或注销事件,来进行一些状态更新。这时候,一个事件总线便会非常有用,事件总线通常实现了订阅者模式,订阅者模式包含发布者和订阅者两种角色,可以通过事件总线来触发事件和监听事件,本节我们实现一个简单的全局事件总线,我们使用单例模式,代码如下://订阅者回调签名typedef void EventCallback(arg);class EventBus { //私有构造函数 Even原创 2022-01-29 09:12:35 · 10815 阅读 · 0 评论 -
51、Flutter之Widgets跨组件状态共享(Provider)
在 Flutter 开发中,状态管理是一个永恒的话题。一般的原则是:如果状态是组件私有的,则应该由组件自己管理;如果状态要跨组件共享,则该状态应该由各个组件共同的父元素来管理。对于组件私有的状态管理很好理解,但对于跨组件共享的状态,管理的方式就比较多了,如使用全局事件总线EventBus,它是一个观察者模式的实现,通过它就可以实现跨组件状态同步:状态持有方(发布者)负责更新、发布状态,状态使用方(观察者)监听状态改变事件来执行一些操作。下面我们看一个登录状态同步的简单示例:定义事件:enum Ev原创 2022-01-28 08:35:13 · 10756 阅读 · 0 评论 -
50、Flutter之Widget 数据共享(InheritedWidget)
InheritedWidget是 Flutter 中非常重要的一个功能型组件,它提供了一种在 widget 树中从上到下共享数据的方式,比如我们在应用的根 widget 中通过InheritedWidget共享了一个数据,那么我们便可以在任意子widget 中来获取该共享的数据!这个特性在一些需要在整个 widget 树中共享数据的场景中非常方便!如Flutter SDK中正是通过 InheritedWidget 来共享应用主题(Theme)和 Locale (当前语言环境)信息的。Inherited原创 2022-01-26 09:54:56 · 12703 阅读 · 0 评论 -
49、Flutter之容器组件 变换(Transform)
Transform可以在其子组件绘制时对其应用一些矩阵变换来实现一些特效。Matrix4是一个4D矩阵,通过它我们可以实现各种矩阵操作,下面是一个例子:Container( margin: EdgeInsets.only(top: 200,left: 20), color: Colors.black, child: Transform( alignment: Alignment.topRight, transform: Matrix4原创 2022-01-25 22:06:28 · 13413 阅读 · 0 评论 -
48、Flutter之widgets LayoutBuilder组件
LayoutBuilder通过 LayoutBuilder,我们可以在布局过程中拿到父组件传递的约束信息,然后我们可以根据约束信息动态的构建不同的布局。比如我们实现一个响应式的 Column 组件 ResponsiveColumn,它的功能是当当前可用的宽度小于 200 时,将子组件显示为一列,否则显示为两列。简单来实现一下:class ResponsiveColumn extends StatelessWidget { const ResponsiveColumn({Key? key,原创 2022-01-25 09:41:37 · 13429 阅读 · 0 评论 -
47、Flutter之widgets 组件布局对齐与相对定位(Align)
我们讲过通过Stack和Positioned,我们可以指定一个或多个子元素相对于父元素各个边的精确偏移,并且可以重叠。但如果我们只想简单的调整一个子元素在父元素中的位置的话,使用Align组件会更简单一些。AlignAlign 组件可以调整子组件的位置,定义如下:Align({ Key key, this.alignment = Alignment.center, this.widthFactor, this.heightFactor, Widget child,})原创 2022-01-24 08:58:14 · 13134 阅读 · 0 评论 -
46、Flutter之 布局组件 流式布局Wrap,Flow
Row 和 Colum 如果子 widget 超出屏幕范围,则会报溢出错误,如:Row( children: <Widget>[ Text("xxx"*100) ],);运行效果所示:可以看到,右边溢出部分报错。这是因为Row默认只有一行,如果超出屏幕不会折行。我们把超出屏幕显示范围会自动折行的布局称为流式布局。Flutter中通过Wrap和Flow来支持流式布局,将上例中的 Row 换成Wrap后溢出部分则会自动折行,下面我们分别介绍Wrap和Flow原创 2022-01-23 16:22:39 · 11397 阅读 · 0 评论 -
45、Flutter之布局组件 弹性布局Flex
弹性布局允许子组件按照一定比例来分配父容器空间。弹性布局的概念在其它UI系统中也都存在,如 H5 中的弹性盒子布局,Android中 的FlexboxLayout等。Flutter 中的弹性布局主要通过Flex和Expanded来配合实现。FlexFlex组件可以沿着水平或垂直方向排列子组件,如果你知道主轴方向,使用Row或Column会方便一些,**因为Row和Column都继承自Flex,**参数基本相同,所以能使用Flex的地方基本上都可以使用Row或Column。Flex本身功能是很强大的,原创 2022-01-23 10:18:53 · 10611 阅读 · 0 评论 -
44、Flutter之组件布局原理与约束(constraints)
尺寸限制类容器用于限制容器大小,Flutter中提供了多种这样的容器,如ConstrainedBox、SizedBox、UnconstrainedBox、AspectRatio 等,本节将介绍一些常用的。Flutter 中有两种布局模型:基于 RenderBox 的盒模型布局。 基于 Sliver ( RenderSliver ) 按需加载列表布局。两种布局方式在细节上略有差异,但大体流程相同,布局流程如下:上层组件向下层组件传递约束(constraints)条件。 下层组件确定自己的大小原创 2022-01-22 17:35:41 · 11460 阅读 · 0 评论 -
43、Flutter之布局类组件-布局类组件简介
简介布局类组件都会包含一个或多个子组件,不同的布局类组件对子组件排列(layout)方式不同。Widget 说明 用途 LeafRenderObjectWidget 非容器类组件基类 Widget树的叶子节点,用于没有子节点的widget,通常基础组件都属于这一类,如Image。 SingleChildRenderObjectWidget 单子组件基类 包含一个子Widget,如:ConstrainedBox、DecoratedBox等 MultiCh原创 2022-01-22 08:54:31 · 10728 阅读 · 0 评论 -
42、Flutter之GridView组件详解
GridViewGridView可以构建一个二维网格列表,其默认构造函数定义如下: GridView({ Key? key, Axis scrollDirection = Axis.vertical, bool reverse = false, ScrollController? controller, bool? primary, ScrollPhysics? physics, bool shrinkWrap = false, E原创 2022-01-21 09:49:44 · 10551 阅读 · 0 评论 -
41、Flutter之AnimatedList详解
AnimatedListAnimatedList 和 ListView 的功能大体相似,不同的是, AnimatedList 可以在列表中插入或删除节点时执行一个动画,在需要添加或删除列表项的场景中会提高用户体验。AnimatedList 是一个 StatefulWidget,它对应的 State 类型为 AnimatedListState,添加和删除元素的方法位于 AnimatedListState 中:void insertItem(int index, { Duration durati原创 2022-01-20 09:15:58 · 5739 阅读 · 0 评论 -
40、Flutter之滚动监听及控制
ScrollControllerScrollController构造函数如下:ScrollController({ double initialScrollOffset = 0.0, //初始滚动位置 this.keepScrollOffset = true,//是否保存滚动位置 ...})我们介绍一下ScrollController常用的属性和方法:offset:可滚动组件当前的滚动位置。 jumpTo(double offset)、animateTo(double o原创 2022-01-19 23:37:50 · 7406 阅读 · 0 评论 -
39、Flutter之 ListView组件详解
ListViewListView是最常用的可滚动组件之一,它可以沿一个方向线性排布所有子组件,并且它也支持列表项懒加载(在需要时才会创建)。我们看看ListView的默认构造函数定义:ListView({ ... //可滚动widget公共参数 Axis scrollDirection = Axis.vertical, bool reverse = false, ScrollController? controller, bool? primary, ScrollP原创 2022-01-19 10:35:11 · 12856 阅读 · 0 评论 -
38、Flutter之 可滚动组件简介
Flutter 中有两种布局模型:基于 RenderBox 的盒模型布局。 基于 Sliver ( RenderSliver ) 按需加载列表布局。通常可滚动组件的子组件可能会非常多、占用的总高度也会非常大;如果要一次性将子组件全部构建出将会非常昂贵!为此,Flutter中提出一个Sliver(中文为“薄片”的意思)概念,Sliver 可以包含一个或多个子组件。Sliver 的主要作用是配合:加载子组件并确定每一个子组件的布局和绘制信息,如果 Sliver 可以包含多个子组件时,通常会实现按需加载模原创 2022-01-18 22:04:41 · 5915 阅读 · 0 评论 -
37、Flutter之TabBarView组件
TabBarView 是 Material 组件库中提供了 Tab 布局组件,通常和 TabBar 配合使用。TabBarViewTabBarView 封装了 PageView,它的构造方法很简单 TabBarView({ Key? key, required this.children, // tab 页 this.controller, // TabController this.physics, this.dragStartBehavior = DragStartBe原创 2022-01-18 09:46:39 · 7779 阅读 · 2 评论 -
36、Flutter之可滚动组件子项缓存 KeepAlive
首先回想一下,在介绍 ListView 时,有一个addAutomaticKeepAlives 属性我们并没有介绍,如果addAutomaticKeepAlives 为 true,则 ListView 会为每一个列表项添加一个 AutomaticKeepAlive 父组件。虽然 PageView 的默认构造函数和 PageView.builder 构造函数中没有该参数,但它们最终都会生成一个 SliverChildDelegate 来负责列表项的按需加载,而在 SliverChildDelegate 中每当原创 2022-01-18 08:59:28 · 5938 阅读 · 0 评论 -
35、Flutter之PageView与页面缓存
PageView如果要实现页面切换和 Tab 布局,我们可以使用 PageView 组件。需要注意,PageView 是一个非常重要的组件,因为在移动端开发中很常用,比如大多数 App 都包含 Tab 换页效果、图片轮动以及抖音上下滑页切换视频功能等等,这些都可以通过 PageView 轻松实现。PageView({ Key? key, this.scrollDirection = Axis.horizontal, // 滑动方向 this.reverse = false, Pag原创 2022-01-17 22:28:33 · 5307 阅读 · 0 评论 -
34、Flutter之组件过度动画
Widget属性发生变化时会执行过渡动画的组件统称为”动画过渡组件“,而动画过渡组件最明显的一个特征就是它会在内部自管理AnimationController。我们知道,为了方便使用者可以自定义动画的曲线、执行时长、方向等,在前面介绍过的动画封装方法中,通常都需要使用者自己提供一个AnimationController对象来自定义这些属性值。但是,如此一来,使用者就必须得手动管理AnimationController,这又会增加使用的复杂性。因此,如果也能将AnimationController进行封装,则原创 2022-01-17 08:42:27 · 4280 阅读 · 0 评论 -
33、Flutter之动画切换组件(AnimatedSwitcher)
实际开发中,我们经常会遇到切换UI元素的场景,比如Tab切换、路由切换。为了增强用户体验,通常在切换时都会指定一个动画,以使切换过程显得平滑。Flutter SDK组件库中已经提供了一些常用的切换组件,如PageView、TabView等,但是,这些组件并不能覆盖全部的需求场景,为此,Flutter SDK中提供了一个AnimatedSwitcher组件,它定义了一种通用的UI切换抽象。AnimatedSwitcherAnimatedSwitcher 可以同时对其新、旧子元素添加显示、隐藏动画。也就原创 2022-01-13 22:17:53 · 6409 阅读 · 0 评论 -
32、Flutter之自定义路由切换动画
Material组件库中提供了一个MaterialPageRoute组件,它可以使用和平台风格一致的路由切换动画,如在iOS上会左右滑动切换,而在Android上会上下滑动切换。现在,我们如果在Android上也想使用左右切换风格,该怎么做?一个简单的作法是可以直接使用CupertinoPageRoute,如: Navigator.push(context, CupertinoPageRoute( builder: (context)=>PageB(), ));Cupertino原创 2022-01-13 09:01:13 · 5614 阅读 · 0 评论 -
31、Flutter之Hero动画
Flutter Hero动画Hero指的是可以在路由(页面)之间“飞行”的widget。 使用Flutter的Hero widget创建hero动画。 将 hero从一个路由飞到另一个路由。 将 hero 的形状从圆形转换为矩形,同时将其从一个路由飞到另一个路由的过程中进行动画处理。 Flutter中的Hero widget实现了通常称为 共享元素转换 或 共享元素动画的动画风格。你可能多次看过 hero 动画。例如,路由显示代表待售物品的缩略图列表。选择一个条目会将其跳转到一个新路由,原创 2022-01-12 22:15:17 · 5949 阅读 · 0 评论 -
30、Flutter之AnimatedWidget相关动画
基本的动画概念和类 Animation<double> CurvedAnimation AnimationController Tween Tween.animate 动画通知 动画示例 渲染动画 用AnimatedWidget简化 监视动画的过程 用AnimatedBuilder重构 并行动画 基本的动画概念和类重点是什么?Animation对象是Flutter动画库中的一个核心类,它生成指导动画的值。 Animation对象知原创 2022-01-11 22:22:32 · 5150 阅读 · 0 评论 -
29、Flutter之CustomPaint 绘画
简介在flutter里面有着万物皆是widget这句话,CustomPaint是Flutter中用于自由绘制的一个widget。它与android原生的绘制规则基本一致,以当前Canves(画布)的左上角为原点进行绘制。构造方法:class CustomPaint extends SingleChildRenderObjectWidget { /// Creates a widget that delegates its painting. const CustomPaint({原创 2022-01-11 15:03:59 · 4708 阅读 · 0 评论 -
28、Flutter之Navigator进行局部跳转页面
NavigatorNavigator 是管理路由的控件,通常情况下直接使用Navigator.of(context)的方法来跳转页面,之所以可以直接使用Navigator.of(context)是因为在WidgetsApp中使用了此控件,应用程序的根控件通常是MaterialApp,MaterialApp包含WidgetsApp,所以可以直接使用Navigator的相关属性。基本用法:class MyNavigator extends StatefulWidget { const MyNa原创 2022-01-10 22:38:45 · 5196 阅读 · 0 评论 -
27、Flutter之 dart空安全适配
自定义Widget的空安全适配分两种情况:Widget的空安全适配 State的空安全适配Widget的空安全适配对于自定的Widget无论是页面的某控件还是整个页面,通常都会为Widget定义一些属性。在进行空安全适配时要对属性进行一下分类:可空的属性:通过?进行修饰 不可空的属性:在构造函数中设置默认值或者通过required进行修饰class WebView extends StatefulWidget { String? url; final String? sta原创 2022-01-10 14:58:19 · 5985 阅读 · 0 评论 -
26、Flutter之 dart空安全问题
从Flutter 2开始,Flutter便在配置中默认启用了空安全,通过将空检查合并到类型系统中,可以在开发过程中捕获这些错误,从而防止再生产环境导致的崩溃。什么是空安全时至今日,空安全已经是一个屡见不鲜的话题,目前像主流的编程语言Kotlin、Swift、Rust 等都对空安全有自己的支持。Dart从2.12版本开始支持了空安全,通过空安全开发人员可以有效避免null错误崩溃。空安全性可以说是Dart语言的重要补充,它通过区分可空类型和非可空类型进一步增强了类型系统。引入空安全的好处原创 2022-01-10 14:50:49 · 6143 阅读 · 0 评论 -
25、 Flutter Widgets 之 WillPopScope
为了避免用户误触返回按钮而导致 App 退出,在很多 App 中都拦截了用户点击返回键的按钮,然后进行一些防误触判断,比如当用户在某一个时间段内点击两次时,才会认为用户是要退出(而非误触)。Flutter中可以通过WillPopScope来实现返回按钮拦截,我们看看WillPopScope的默认构造函数:const WillPopScope({ ... required WillPopCallback onWillPop, required Widget child})onWill原创 2022-01-09 22:45:10 · 4148 阅读 · 0 评论 -
24、 Flutter Widgets 之 标签类控件大全Chip
RawChipMaterial风格标签控件,此控件是其他标签控件的基类,通常情况下,不会直接创建此控件,而是使用如下控件: Chip InputChip ChoiceChip FilterChip ActionChip 如果你想自定义标签类控件,通常使用此控件。RawChip可以通过设置onSelected被选中,设置onDeleted被删除,也可以通过设置onPressed而像一个按钮,它有一个label属性,有一个前置(avatar)和后置图标(原创 2022-01-08 22:57:44 · 5180 阅读 · 0 评论 -
23、 Flutter Widgets 之 Flutter日期类组件
showDatePicker、showTimePicker 是 flutter 提供的日期选择器弹框。CalendarDatePicker 是替代 YearPicker、MonthPicker、DayPicker 的新的日期选择控件。CupertinoDatePicker、CupertinoTimerPicker 是 iOS 风格的 DatePickerView 和 TimePickerView 的日期时间选择器。属性介绍showDatePicker属性 介绍 context @原创 2022-01-08 21:13:27 · 5201 阅读 · 0 评论