当前位置: 首页 > Web前端 > HTML

flutter系列:flutter中可索引的栈布局IndexedStack

时间:2023-03-28 14:10:35 HTML

简介之前我们介绍了一个flutter的栈结构的布局组件,叫做Stack。通过Stack,我们可以将一些widget堆叠在其他widget之上,这样我们就可以实现图片组合功能,这也是日常生活中最常用的组件。今天要介绍的这个组件是Stack的近亲,叫做IndexedStack。它有什么功能?一起来看看吧。IndexedStack简介从名字就可以看出,IndexedStack是一个给Stack添加索引的函数。是这样吗?我们先看一下IndexedStack的定义:classIndexedStackextendsStack可以看到IndexedStack继承自Stack,Stack其实是Stack的子类,所以IndexedStack具有前面介绍的Stack的所有功能,IndexedStack是Stack的功能增强。我们看一下它的构造函数:IndexedStack({Key?key,AlignmentGeometryalignment=AlignmentDirectional.topStart,TextDirection?textDirection,StackFitsizing=StackFit.loose,this.index=0,Listchildren=const[],}):super(key:key,alignment:alignment,textDirection:textDirection,fit:sizing,children:children);可以看到和Stack相比,IndexedStack多了一个index参数,但是这个参数没有传到super的构造函数中,index用在哪里呢?不用担心,IndexedStack还重写了以下两个方法,createRenderObject和updateRenderObject:returnRenderIndexedStack(index:index,alignment:alignment,textDirection:textDirection??Directionality.maybeOf(context),);}@overridevoidupdateRenderObject(BuildContextcontext,RenderIndexedStackrenderObject){assert(_debugCheckHasDirectionality(context));渲染对象..index=index..alignment=alignment..textDirection=textDirection??Directionality.maybeOf(上下文);}与Stack相比,IndexedStack在这两个方法中使用的是RenderIndexedStack,而Stack使用的是RenderStack,所以IndexedStack虽然继承自Stack,但是两者在性能上有着本质的区别。对于Stack,一个widget放置在另一个widget之上,但可以同时显示多个widget。对于IndexedStack,它只会显示索引对应的widget。RenderIndexedStack也是继承自RenderStack:classRenderIndexedStackextendsRenderStack我们看一下它的paintStack方法:@overridevoidpaintStack(PaintingContextcontext,Offsetoffset){if(firstChild==null||index==null)return;finalRenderBoxchild=_childAtIndex();最终StackParentDatachildParentData=child.parentData!作为StackParentData;context.paintChild(child,childParentData.offset+offset);可以看到在paintStack方法中,只绘制了索引对应的组件_childAtIndex,所以如果索引不匹配,则不会显示。IndexedStack的行为有点像我们常用的选项卡。IndexedStack的使用从上面IndexedStack的构造函数我们知道IndexedStack需要传入一个index属性和对应的children。在这个例子中,我们向IndexedStack传递了一个变量index属性,以及4个children:IndexedStack(index:_counter,children:[widgetOne(),widgetTwo(),widgetThree(),widgetFour(),],)_counter是定义的变量在StatefulWidget中。可以通过调用setState方法修改index,达到动态切换children的目的。这里的子部件非常简单。我们使用不同大小的SizedBoxes,并在SizedBoxes中设置不同的颜色,方便观察切换效果:WidgetwidgetOne(){returnSizedBox(width:100,height:100,child:Container(color:Colors.yellow,),);最后调用Scaffold的floatingActionButton中的_changeIndex方法改变索引。最终代码如下:classMyHomePageextendsStatefulWidget{constMyHomePage({Key?key,requiredthis.title}):super(key:key);最终字符串标题;@overrideStatecreateState()=>_MyHomePageState();}class_MyHomePageStateextendsState{int_counter=0;void_changeIndex(){setState((){_counter=(_counter+1)%4;print(_counter);});}@overrideWidgetbuild(BuildContextcontext){returnScaffold(appBar:AppBar(title:Text(widget.title),),body:Center(child:IndexedStack(index:_counter,children:[widgetOne(),widgetTwo()},瓦idgetThree(),widgetFour(),],),),floatingActionButton:FloatingActionButton(onPressed:_changeIndex,tooltip:'改变索引',child:constIcon(Icons.arrow_back),),);程序运行后的效果如下:点击右下角的按钮,我们可以得到不同widgets的汇总。IndexWidget类似于tab,需要的时候可以用。本文示例:https://github.com/ddean2009/learn-flutter.git更多内容请参考www.flydean.com最通俗的解读,最深刻的干货,最简洁的教程,以及很多你不知道的小技巧等着你去发现!欢迎关注我的公众号:《程序那些事儿》,懂技术,更懂你!

最新推荐
猜你喜欢