Column multiple SliverList In CustomScrollView - flutter

CustomScrollView(
scrollDirection: Axis.horizontal,
slivers: [
SliverToBoxAdapter(
child: Container(height: 600, width: 400, color: Colors.red),
),
// HERE I NEED MULTIPLE SliverLists VERTICALLY - BEGIN
Column(
children:[
SliverList(
delegate: SliverChildBuilderDelegate(
(_, index) => SomeExpensiveWidget(index),
childCount: 10000,
),
),
SliverList(
delegate: SliverChildBuilderDelegate(
(_, index) => SomeCustomRowWidget(index),
childCount: 10000,
),
),
]
),
// THIS DOESNT WORK - END
SliverToBoxAdapter(
child: Container(height: 600, width: 400, color: Colors.red),
),
],
),
I have a CustomScrollView and it is scrolling horizontally. Due to some reason I need to have multiple SliverList in a Column widget. I am trying to create a 2D grid and I can't use SliverGrid because my widgets inside SomeCustomRowWidget only works when they are in a Row (elements in row shrink and get bigger according to some condition). I am trying to have multiple SliverList in a Column to give the illusion of a grid but so far its not working because Column widget works with normal widgets. There is no SliverColumn or something like that. How may I position SliverLists as if they are in a Column?

there is a widget let you put any widget as slivers
wrap the widgets you want to show with SliverToBoxAdapter like this
SliverToBoxAdapter(
child: YourWidget(),
),
it will just let adapt your other widgets to the slivers family.

Related

Create a bidirectional infinite ListView.builder in Flutter

I mean in both axis, horizontal and vertical.
I tried nesting two ListView.builder but they don't scroll together as I would like.
class MyWidget extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
drawer: Drawer(),
appBar: AppBar(),
body: Container(
child: ListView.builder(
scrollDirection: Axis.horizontal,
itemBuilder: (context, x) {
return Container(
height: 50,
width: 50,
child: ListView.builder(
itemBuilder: (context, y) {
return Container(
height: 100, child: Text("${y.toString()}"));
},
),
);
}),
));
}
}
Possible solutions I have in mind:
Make the ListView.builders scroll together. But I think that solution may not be efficient performance wise, since flutter still treating each column as an individual scroller
Create a finite ListView.builder and rebuild it as necessary to make the illusion it is infinite. But that may add unnecessary complexity to the project.
Add NeverScrollableScrollPhysics on vertical axis and perform the scroll with another Widget. I failed attempting that. That method just worked for me if the list is finite.
Is there any widget appropriated to that application that I could be maybe missing?
Is there any other better approach to create something like that?
Two dimensional scrolling is supported by DataTable (try the Flutter Gallery "Data tables" demo) and Table. Maybe try building a schedule widget based on on of those.
You can use wrap DataTable inside two SingleChildScrollView widgets to achieve bidirectional scrolling..
By using something like this
SingleChildScrollView(
scrollDirection: Axis.vertical,
child: SingleChildScrollView(
scrollDirection: Axis.horizontal,
child: DataTable(
dataRowHeight: 50,
dividerThickness: 5,
horizontalMargin: 15,
columnSpacing: 13,
showBottomBorder: true,
headingRowColor: MaterialStateProperty.all<Color>(
Colors.blueGrey[100]),
columns: [
DataColumn(
label: Text(
"Module Name",
style: TextStyle(
// fontStyle: FontStyle.italic,
fontWeight: FontWeight.w600,
fontSize: 14,
color: Theme.of(context).highlightColor,
),
),
numeric: false,
),
],
rows: data
.map((details) => DataRow(
cells: [
DataCell(
Text(
details.name,
),
),
//list of cells: remenber the number of DataColumn and DataCell should be same
],
))
.toList()),
),
);
To fetch data from internet you can wrap the first SingleChildScrollView with FutureBuilder
PS: here data is list of modules data fetch from internet,
just for example I have added only one DataColumn you can add as needed

Make Column begin in a fixed position on the screen

I'm trying to make a column with two children begin at a certain position on the screen. The 2nd child is a dynamic ListView where I do not want the number of children changing the position of the column.
How is this possible?
Just wrap your ListView with Expanded widget .
Example:
Column(
children: [
Expanded( //here
child: ListView.builder(
itemBuilder: (context, index) => Text('test $index'),
itemCount: 50, ),
),
Column(
children: [
Container(height: 100, color: Colors.yellow),
OutlinedButton(onPressed: (){}, child: Text('Test'),),
Text('Another Test')
]
)
],
),
I used a Listview.builder because I don't want to do it one by one. Just for the example
You can learn more about Expanded widget by watching this Official video or by visiting flutter.dev

How to make a SingleChildScrollView with nested ListView?

I have a list of days, and a list of opening hours for each day.
I need to make the list of days scrollable, and the list of opening hours expands as necessary (= I don't want the list of opening hours to be scrollable into a defined height container).
How to make the list scrollable ?
Here is what I have so far, a list of days that is not scrollable (and I can't see sunday) :
SingleChildScrollView(
child: ListView.builder(
itemCount: _days.length,
itemBuilder: (context, i) {
return Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: EdgeInsets.all(18.0),
child: Text(_days[i],
style: TextStyle(
fontWeight: FontWeight.bold,
color: Colors.grey[700]))),
Container(
decoration: BoxDecoration(color: Colors.white),
child: ListView.builder(
shrinkWrap: true,
itemCount: _daysDispos[i].length,
itemBuilder: (context, j) {
final dispo = _daysDispos[i][j];
return ListTile(
title: Text(dispo.address.line));
}),
)
],
);
})),
EDIT
In the first listView builder, add :
physics: NeverScrollableScrollPhysics()
Solved my issue.
A good solution would be using Expandable package, and add multiple Expandables inside a single ListView.
Another Solution would be replacing the outer ScrollView with one single ListView, whose Childs will be 7 Columns, each column contains a group of opening hours.
You can try CustomScrollView with multiple SliverLists for your purposes instead of using SingleChildScrollView:
Widget build(BuildContext context) {
return CustomScrollView(
slivers: <Widget>[
SliverList(
delegate: SliverChildListDelegate([
Column(
children: <Widget>[
//Widgets you want to use
],
),
]),
),
SliverList(
delegate: SliverChildListDelegate([
Column(
children: <Widget>[
//Widgets you want to use
],
),
]),
),
],
);
}

How to fix text overflow problem and make a card larger in Flutter?

I'm building out an app in flutter and I want to display a few cards in a list-view. The problems I'm facing are the following:
I get a text-overflow when I have Text widgets in a column.I semi-fixed this by wrapping the Text widget in an Expanded widget, but it looks a bit cutoff (ex. "Question: How do you do problem 2?" (refer to picture below)).
I want to build a larger card with a greater height and more room/white space. I've tried wrapping my column widget in a container and set the height manually, but that doesn't seem to do anything.
Here is what the card looks like right now:
Relevant code shown below:
itemBuilder: (context, index) => snapshot
.data.metadata.isFromCache
? _buildListItem(context,
snapshot.data.documents[index])
Widget _buildListItem(BuildContext context, DocumentSnapshot document) {
return document.data['didProblems']
? Card(
child: Center(
child: Container(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text('${document.data['fullName'].toString()}'),
SizedBox(
height: 5.0,
),
Text('HW Assignment: ${document.data['title'].toString()}'),
SizedBox(
height: 5.0,
),
Text('Problems attempted: ${document.data['problems']}'),
Expanded(child: Text('Question: ${document.data['question'].toString()}'), flex: 1,),
],
),
),
),
)
Any help is appreciated. Thanks in advance!
if u r using listview then set itemExtent property to ur convenience e.g.
ListView.builder(
itemCount: 10,
itemBuilder: (_, int index) => YourWidget(),
itemExtent: 150,
),
Even after wrapping your text in an Expanded you have to set overflow to TextOverflow.clip
Try this
Expanded(child: Text('Question: ${document.data['question'].toString()}', overflow: TextOverflow.clip), flex:1,),

Flutter: fully include a ListView inside a Column (no Expanded)

Inside a scroll view I want to display a widget, then a list, then a widget. Something among the lines of:
#override
Widget build(BuildContext context) {
return SingleChildScrollView(
child: Column(
children: <Widget>[
Text("Top of ListView"),
ListView.builder(
itemCount: 100,
itemBuilder: (context, index) => Text('Line $index')),
Text("Below of ListView")
],
),
);
}
Where the content of the SingleChildScrollView would be:
Text("Top of ListView"),
Text('Line 0'),
Text('Line 1'),
...
Text('Line 98'),
Text('Line 99'),
Text("Bottom of ListView")
Of course this code doesn't work, since ListView height is undefined. Wrapping the ListView with Expanded isn't the solution since I want Text("Top of ListView") to disappear when I begin to scroll and Text("Bottom of ListView") to appear only when reaching bottom (as if they are the first item and the last item of the list, respectively).
My ideas:
Putting Text("Top of ListView") and Text("Bottom of ListView")
inside the ListView : easy to do for this example, but in real world there won't be only one widget in front of or behind the list. Messy and hard to maintain.
Adding the list items to the Column directly : aka re-implementing ListView.
Wrapping ListView into a Container with a fixed height corresponding to the calculated ListView height: I don't know how to measure childrens.
Any ideas ?
You must use CustomScrollView to achieve this:
CustomScrollView(
slivers: [
SliverList(
delegate: SliverChildListDelegate([Text("Top of ListView")]),
),
SliverList(
delegate: SliverChildBuilderDelegate(
(context, index) => Text('Line $index')
childCount: 100,
),
),
SliverList(
delegate: SliverChildListDelegate([Text("Below of ListView")]),
),
],
),