gpt4 book ai didi

flutter - 具有动态容器高度的 TabBarView

转载 作者:IT王子 更新时间:2023-10-29 06:36:25 63 4
gpt4 key购买 nike

这是我的布局结构

这是主界面

ListView(
children: <Widget>[
_buildCarousel(),
_buildHomeTabBar(),
],
)

这是 HomeTabBar 屏幕

SingleChildScrollView(
child:
DefaultTabController(
length: myTabs.length,
initialIndex: 0,
child: Column(
children: [
TabBar(
isScrollable: true,
tabs: myTabs,
),
Container(
height: 600,
child:
TabBarView(
children: [
ChildScreen(),
ChildScreen2(),
ChildScreen3(),
],
)
)
],
))
);

我想摆脱 Container 的高度。我们如何做到这一点?

ChildScreen 正在从 REST 获取数据,它实际上是一个 GridView.Builder,因此 Container 的高度应该是动态的。

抱歉,我错过了 ChildScreen 的布局,实际上是这样的

SingleChildScrollView(
// shrinkWrap: true,
child: Column(
children: <Widget>[
StreamBuilder(
stream: categoryBloc.categoryList,
builder: (context, AsyncSnapshot<List<Category>> snapshot){
if (snapshot.hasData && snapshot!=null) {
if(snapshot.data.length > 0){
return buildCategoryList(snapshot);
}
else if(snapshot.data.length==0){
return Text('No Data');
}
}
else if (snapshot.hasError) {
return ErrorScreen(errMessage: snapshot.error.toString());
}
return Center(child: CircularProgressIndicator());

},
),
]
)
);

所以 StreamBuilder 里面是 GridView.Builder。主要是我想删除 Container 高度。它在不同的设备上看起来很丑...

因此,如果我删除高度,它将不会显示在屏幕上并引发错误

I/flutter ( 493): #2 RenderObject.layout (package:flutter/src/rendering/object.dart:1578:12) I/flutter ( 493): #3 RenderSliverList.performLayout.advance (package:flutter/src/rendering/sliver_list.dart:200:17) I/flutter ( 493): #4 RenderSliverList.performLayout (package:flutter/src/rendering/sliver_list.dart:233:19) I/flutter ( 493): #5 RenderObject.layout (package:flutter/src/rendering/object.dart:1634:7) I/flutter ( 493): #6 RenderSliverPadding.performLayout (package:flutter/src/rendering/sliver_padding.dart:182:11) I/flutter ( 493): #7 RenderObject.layout (package:flutter/src/rendering/object.dart:1634:7) I/flutter ( 493): #8 RenderViewportBase.layoutChildSequence (package:flutter/src/rendering/viewport.dart:405:13) I/flutter ( 493): #9 RenderViewport._attemptLayout (package:flutter/src/rendering/viewport.dart:1316:12) I/flutter ( 493): #10 RenderViewport.performLayout (package:flutter/src/rendering/viewport.dart:1234:20) I/flutter ( 493): #11 RenderObject.layout (package:flutter/src/rendering/object.dart:1634:7) I/flutter ( 493): #12 _RenderProxyBox&RenderBox&RenderObjectWithChildMixin&RenderProxyBoxMixin.performLayout (package:flutter/src/rendering/proxy_box.dart:104:13) I/flutter ( 493): #13 RenderObject.layout (package:flutter/src/rendering/object.dart:1634:7)

最佳答案

我在我的项目中有类似的任务。问题的根源是你试图把 TabBarView (试图尽可能大的可滚动小部件),在没有高度的列小部件中。

其中一个解决方案是摆脱包装您的 TabBarView 的可滚动小部件在这个例子中 ListView + Column .并使用 NestedScrollView而不是他们。你需要输入 _buildCarousel()TabBarheaderSliverBuilder部分,和 TabBarViewNestedScrollView 的体内.

我不知道你的设计看起来如何,但是NestedScrollView默认情况下打开屏幕 View 的 100% 高度。因此,如果您想使所有内容都在一个屏幕上,则通过更改 ScrollController 来阻止滚动会更容易。需要时的行为。

在此示例中,我阻止了第三个选项卡上的滚动,但您可以检查 GridView 最后一项的可见性。只需将键添加到最后一项,并检查其在屏幕上的位置。

希望对您有所帮助。

class _MyHomePageState extends State<MyHomePage> with SingleTickerProviderStateMixin {
final bodyGlobalKey = GlobalKey();
final List<Widget> myTabs = [
Tab(text: 'auto short'),
Tab(text: 'auto long'),
Tab(text: 'fixed'),
];
TabController _tabController;
ScrollController _scrollController;
bool fixedScroll;

Widget _buildCarousel() {
return Stack(
children: <Widget>[
Placeholder(fallbackHeight: 100),
Positioned.fill(child: Align(alignment: Alignment.center, child: Text('Slider'))),
],
);
}

@override
void initState() {
_scrollController = ScrollController();
_scrollController.addListener(_scrollListener);
_tabController = TabController(length: 3, vsync: this);
_tabController.addListener(_smoothScrollToTop);

super.initState();
}

@override
void dispose() {
_tabController.dispose();
_scrollController.dispose();
super.dispose();
}

_scrollListener() {
if (fixedScroll) {
_scrollController.jumpTo(0);
}
}

_smoothScrollToTop() {
_scrollController.animateTo(
0,
duration: Duration(microseconds: 300),
curve: Curves.ease,
);

setState(() {
fixedScroll = _tabController.index == 2;
});
}

_buildTabContext(int lineCount) => Container(
child: ListView.builder(
physics: const ClampingScrollPhysics(),
itemCount: lineCount,
itemBuilder: (BuildContext context, int index) {
return Text('some content');
},
),
);

@override
Widget build(BuildContext context) {
return Scaffold(
body: NestedScrollView(
controller: _scrollController,
headerSliverBuilder: (context, value) {
return [
SliverToBoxAdapter(child: _buildCarousel()),
SliverToBoxAdapter(
child: TabBar(
controller: _tabController,
labelColor: Colors.redAccent,
isScrollable: true,
tabs: myTabs,
),
),
];
},
body: Container(
child: TabBarView(
controller: _tabController,
children: [_buildTabContext(2), _buildTabContext(200), _buildTabContext(2)],
),
),
),
);
}
}

enter image description here.

获得所需内容的另一种方法是创建自定义 TabView小部件。

关于flutter - 具有动态容器高度的 TabBarView,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54642710/

63 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com