我正在我的 flutter 应用程序中实现一个 DraggableScrollableSheet 并希望有一个粘性标题,即只有列表视图滚动并且工作表的顶部始终保持原位。 我的小部件如下所示:
SizedBox.expand(
child: DraggableScrollableSheet(
maxChildSize: 0.9,
minChildSize: 0.2,
initialChildSize: 0.3,
expand: false,
builder:
(BuildContext context, ScrollController scrollController) {
return Container(
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.only(
topLeft: Radius.circular(20),
topRight: Radius.circular(20),
)),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Align(
alignment: Alignment.topCenter,
child: Container(
margin: EdgeInsets.symmetric(vertical: 8),
height: 8.0,
width: 70.0,
decoration: BoxDecoration(
color: Colors.grey[400],
borderRadius: BorderRadius.circular(10.0)),
),
),
SizedBox(height: 16),
Padding(
padding: const EdgeInsets.symmetric(horizontal: 24),
child: Text(
'Neuigkeiten',
style: TextStyle(
fontSize: 20, fontWeight: FontWeight.bold),
),
),
Padding(
padding: const EdgeInsets.symmetric(horizontal: 24),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
SizedBox(height: 20.0),
Text('Erfahre mehr ... '),
],
),
),
SizedBox(height: 16),
Expanded(child: NewsList(controller: scrollController))
],
),
);
},
),
);
基本功能有效,但只有在列表视图项上拖动/滚动时,工作表才可拖动和滚动。我需要进行哪些更改才能使列中的其他小部件也可滚动。我在没有解决方案的情况下尝试了 Scrollable 和 Draggable 小部件。
感谢任何帮助。
答案 0 :(得分:1)
问题在于 ListView 本身。为此,您需要使用 SliverList,检查 this answer
Widget _buildDiscoverDrawer() {
return DraggableScrollableSheet(
maxChildSize: 0.95,
minChildSize: 0.25,
initialChildSize: 0.4,
builder: (context, scrollController) {
List<Widget> _sliverList(int size, int sliverChildCount) {
List<Widget> widgetList = [];
for (int index = 0; index < size; index++)
widgetList
..add(SliverAppBar(
title: Text("Title $index"),
pinned: true,
))
..add(SliverFixedExtentList(
itemExtent: 50.0,
delegate: SliverChildBuilderDelegate(
(BuildContext context, int index) {
return Container(
alignment: Alignment.center,
color: Colors.lightBlue[100 * (index % 9)],
child: Text('list item $index'),
);
}, childCount: sliverChildCount),
));
return widgetList;
}
return CustomScrollView(
controller: scrollController,
slivers: _sliverList(50, 10),
);
});
}
答案 1 :(得分:0)
video tutorial 表示 builder
应该返回一个可滚动的小部件,例如 SingleChildScrollView
或 ListView
。您是否尝试过使用其中之一而不是 Container
?
答案 2 :(得分:0)
您可以通过使用 Stack
作为工作表的内容来实现此目的。这样,您可以使 ListView
跨越工作表的整个尺寸(因此即使您触摸标题也可以拖动它),并将标题作为叠加层放在顶部。不过,请确保在列表顶部添加一些填充,以免隐藏标题下的第一项。
您必须确保标题不会消耗滑动事件。例如,我想在顶部使用 AppBar
,但该小部件消耗了滑动事件。如果您想使用消耗这些事件的小部件,则应将其包装在 IgnorePointer()
中。
这是 flutter 文档中的示例,但现在带有粘性 AppBar
标头。
class HomePage extends StatelessWidget {
const HomePage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('DraggableScrollableSheet'),
),
body: SizedBox.expand(
child: DraggableScrollableSheet(
builder: (BuildContext context, ScrollController scrollController) {
return Stack(
children: [
//this section is your list
Container(
color: Colors.blue[100],
child: ListView.builder(
controller: scrollController,
itemCount: 26,
itemBuilder: (BuildContext context, int index) {
if(index == 0)return Container(height: 50);//this is the padding on the top of the list
return ListTile(title: Text('Item ${index-1}'));
},
),
),
//this section is your header
IgnorePointer(
child: Container(
height: 50,
child: AppBar(
title: Text("Sheet title"),
automaticallyImplyLeading: false,//this prevents the appBar from having a close button (that button wouldn't work because of IgnorePointer)
),
)),
],
);
},
),
),
);
}
}