how to create horizontal and vertical scrollable widgets in flutter

送分小仙女□ 提交于 2019-12-18 17:29:52

问题


sample Layout image

I am trying to crate attached layout. It has two containers. - First a fixed size box that scrolls horizontally - second card is a that takes up remaining space with list view inside it.

How can I achieve this layout ?

As you can see, the scroll direction is different for both containers. The code is working till the Tags view (first box) but as soon as I am adding a second box i.e card, it is not showing anything and getting errors at console as below..

I/flutter ( 9412):   AnimatedDefaultTextStyle ← _InkFeatures-[GlobalKey#85877 ink renderer] ←
I/flutter ( 9412):   NotificationListener<LayoutChangedNotification> ← ⋯
I/flutter ( 9412):   parentData: offset=Offset(0.0, 0.0); flex=null; fit=null (can use size)
I/flutter ( 9412):   constraints: BoxConstraints(0.0<=w<=340.0, 0.0<=h<=Infinity)
I/flutter ( 9412):   size: MISSING
I/flutter ( 9412):   additionalConstraints: BoxConstraints(biggest)
I/flutter ( 9412): This RenderObject had the following descendants (showing up to depth 5):
I/flutter ( 9412):   RenderFlex#93e12 NEEDS-LAYOUT NEEDS-PAINT
I/flutter ( 9412):     RenderRepaintBoundary#977a7 NEEDS-LAYOUT NEEDS-PAINT
I/flutter ( 9412):       RenderCustomPaint#b6be8 NEEDS-LAYOUT NEEDS-PAINT
I/flutter ( 9412):         RenderRepaintBoundary#e449b NEEDS-LAYOUT NEEDS-PAINT
I/flutter ( 9412):           _RenderExcludableScrollSemantics#293fd NEEDS-LAYOUT NEEDS-PAINT



class _KanbanState extends State<Kanban> {
  @override
  Widget build(BuildContext context) {

    Widget tagList = 
    new SizedBox(
      height: 100.0,
      child: 
    new Column(
      children: <Widget>[
        new Row(
          mainAxisAlignment: MainAxisAlignment.spaceEvenly,
          children: <Widget>[
            new ActionChip(
                backgroundColor: Colors.yellow,
                label: new Text('Tag1'),
                onPressed: () {
                  // update board with selection
                }),
            new ActionChip(
                //backgroundColor: Colors.transparent,
                label: new Text('Tag2'),
                onPressed: () {
                  // update board with selection
                }),
            new ActionChip(
                label: new Text('Tag3'),
                onPressed: () {
                  // update board with selection
                }),
            new ActionChip(
                label: new Text('Tag4'),
                onPressed: () {
                  // update board with selection
                }),
          ],
        )
      ],
    ),);

    Widget boardView = new Flexible(
      // margin: new EdgeInsets.symmetric(vertical: 15.0),
      child: new Column(
        children: <Widget>[
          new ListView.builder(
            scrollDirection: Axis.vertical,
            itemCount: 5,
            itemBuilder: (BuildContext context, int index) {
              return new ListTile(
                onTap: () {
                },
                title: new Row(
                  children: <Widget>[
                    new Expanded(child: new Text("This is item name")),
                    new Text("12 Dec 18"),
                  ],
                ),
              );
            },
          ),
        ],
      ),
    );

    //  int _value=0;
    return new Container(
        child: new Scaffold(
          appBar: new AppBar(
            elevation: 1.0,
            title: new Text("Test title"),
          ),
          body: new Container(
              margin: new EdgeInsets.all(10.0),
              child: Column(
                children: <Widget>[
                  tagList,
                  boardView,
                ],
              )),
        ));
  }
}

回答1:


tl;dr: the following code does what you want =D

import 'package:flutter/material.dart';

void main() async {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'stack overflow',
      theme: ThemeData(
        primarySwatch: Colors.pink,
      ),
      routes: {},
      home: KanbanState(),
    );
  }
}

class KanbanState extends StatefulWidget {
  @override
  KanbanStateState createState() {
    return KanbanStateState();
  }
}

class KanbanStateState extends State<KanbanState> {
  @override
  Widget build(BuildContext context) {
    Widget tagList = Container(
      color: Colors.green,
      height: 100.0,
      child: ListView(
        scrollDirection: Axis.horizontal,
        children: <Widget>[
          Row(
            children: <Widget>[
              ActionChip(
                  backgroundColor: Colors.yellow,
                  label: Text('Tag1'),
                  onPressed: () {
                    // update board with selection
                  }),
              ActionChip(
                  //backgroundColor: Colors.transparent,
                  label: Text('Tag2'),
                  onPressed: () {
                    // update board with selection
                  }),
              ActionChip(
                  label: Text('Tag3'),
                  onPressed: () {
                    // update board with selection
                  }),
              ActionChip(
                  label: Text('Tag4'),
                  onPressed: () {
                    // update board with selection
                  }),
              ActionChip(
                  backgroundColor: Colors.yellow,
                  label: Text('Tag1'),
                  onPressed: () {
                    // update board with selection
                  }),
              ActionChip(
                  //backgroundColor: Colors.transparent,
                  label: Text('Tag2'),
                  onPressed: () {
                    // update board with selection
                  }),
              ActionChip(
                  label: Text('Tag3'),
                  onPressed: () {
                    // update board with selection
                  }),
              ActionChip(
                  label: Text('Tag4'),
                  onPressed: () {
                    // update board with selection
                  }),
            ],
          )
        ],
      ),
    );

    Widget boardView = Container(
      color: Colors.blue,
      child: ListView.builder(
        scrollDirection: Axis.vertical,
        itemCount: 15,
        itemBuilder: (BuildContext context, int index) {
          return ListTile(
            onTap: () {},
            title: Row(
              children: <Widget>[
                Expanded(child: Text("This is item name")),
                Text("12 Dec 18"),
              ],
            ),
          );
        },
      ),
    );

    //  int _value=0;
    return Scaffold(
        appBar: AppBar(
          elevation: 1.0,
          title: Text("Test title"),
        ),
        body: Container(
          color: Colors.amber,
          child: new Column(
            children: <Widget>[
              tagList,
              Expanded(
                child: boardView,
              )
            ],
          ),
          margin: EdgeInsets.all(10.0),
        ));
  }
}

Heres the thought process: I started cleaning up each widget and making sure they would be properly displayed. In the taglist widget, notice you have a row as the only widget in a column. In the boardView, LisView is also the only element in a column;

Then I added more items to make sure both scrolls would work. Adding scrollDirection: Axis.horizontal int the tagList made sure of that.

At last, time to put it all together and display both elements. Remove the top Container as Scaffold is enough. Then is was inly a matter of placing the boardView in the Expanded widget.

This was a fun exercise. =D




回答2:


Use CustomScrollView with SliverListview then you can achieve any kind of views with vertical scrolling horizontal scrolling.

CustomScrollView(
    slivers: <Widget>[
     SliverList(
  delegate: new SliverChildBuilderDelegate(
    (context, index) {
      return Container(
        child: Row(
          children: <Widget>[
            buildTitle(),
            Expanded(
              child: _buildList(),
            ),
          ],
        ),
      );
    },
    childCount: array.length,
  ),
);,
    ],
  );


来源:https://stackoverflow.com/questions/50766553/how-to-create-horizontal-and-vertical-scrollable-widgets-in-flutter

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!