簡體   English   中英

如何在顫振中創建完全可水平滾動的垂直列表

[英]How to create a vertical list fully horizontally scrollable in flutter

我需要垂直列表誰的元素超過顯示的寬度(類似於寬的 Flutter 數據表)。 所以我想讓垂直滾動列表也可以水平滾動。 似乎這樣做的方法是將列表放在 SingleChildScrollView 中

   SingleChildScrollView(child: listview, scrollDirection: Axis.horizontal);

...這是有效的,但如果列表視圖包含一行作為元素,則顯然無效:

 Row(
    mainAxisAlignment: MainAxisAlignment.start,
    crossAxisAlignment: CrossAxisAlignment.start,
    mainAxisSize: MainAxisSize.min,
    children: children.toList());

我不明白為什么這是一個問題,因為這種行應該有一個有限的寬度(由於 MainAxisSize.min)。

可以將每個列表元素包裝在 SingleChildScrollView 中,但這只會導致單個元素可滾動。

為此,我不能在 SingleChildScrollView 中使用 Datatable,因為它不支持可變大小的單元格高度。 如何在 Flutter 中創建可水平滾動的垂直列表視圖?


Widget test() {
  Widget child = ListView.builder(
      itemCount: 2,
      shrinkWrap: true,
      itemBuilder: (context, i) {
        Widget child = rowSSMin_([
          Text(
              "AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA"),
          Text(
              "BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB"),
          Text(
              "XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX"),
        ]);
        return child;
      });

  child = scrollH(child);  // < breaks

  return child;
}

//////////////////////////////////////////////////////////////////////////////
//

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
        home: Scaffold(
            body: Center(
                child: Padding(padding: EdgeInsets.all(20), child: test()))));
  }
}


Widget scrollH(Widget child, {ScrollController controller}) =>
    SingleChildScrollView(child: child, scrollDirection: Axis.horizontal, controller: controller);

Widget columnSSMin_(List<Widget> children) => Column(
    mainAxisAlignment: MainAxisAlignment.start,
    crossAxisAlignment: CrossAxisAlignment.start,
    mainAxisSize: MainAxisSize.min,
    children: children);

Widget rowSSMin_(Iterable<Widget> children) => Row(
    mainAxisAlignment: MainAxisAlignment.start,
    crossAxisAlignment: CrossAxisAlignment.start,
    mainAxisSize: MainAxisSize.min,
    children: children.toList());

得到...

════════ Exception caught by rendering library ═════════════════════════════════════════════════════
The following assertion was thrown during performLayout():
RenderBox was not laid out: RenderSemanticsAnnotations#fe879 relayoutBoundary=up10 NEEDS-PAINT NEEDS-COMPOSITING-BITS-UPDATE
'package:flutter/src/rendering/box.dart':
Failed assertion: line 1785 pos 12: 'hasSize'


Either the assertion indicates an error in the framework itself, or we should provide substantially more information in this error message to help you determine and fix the underlying cause.
In either case, please report this assertion by filing a bug on GitHub:
  https://github.com/flutter/flutter/issues/new?template=BUG.md

The relevant error-causing widget was: 
  SingleChildScrollView file:///home/sir/ailive/livebetter/flutterui/lib/scratch2.dart:41:31
When the exception was thrown, this was the stack: 
#2      RenderBox.size (package:flutter/src/rendering/box.dart:1785:12)
#3      RenderProxyBoxMixin.performLayout (package:flutter/src/rendering/proxy_box.dart:114:21)
#4      RenderObject.layout (package:flutter/src/rendering/object.dart:1777:7)
#5      RenderProxyBoxMixin.performLayout (package:flutter/src/rendering/proxy_box.dart:113:14)
#6      RenderObject.layout (package:flutter/src/rendering/object.dart:1777:7)
...
The following RenderObject was being processed when the exception was fired: RenderPointerListener#ea643 relayoutBoundary=up9 NEEDS-LAYOUT NEEDS-PAINT NEEDS-COMPOSITING-BITS-UPDATE
...  parentData: <none> (can use size)
...  constraints: BoxConstraints(0.0<=w<=921.5, 0.0<=h<=512.9)
...  size: MISSING
...  behavior: opaque
...  listeners: down
RenderObject: RenderPointerListener#ea643 relayoutBoundary=up9 NEEDS-LAYOUT NEEDS-PAINT NEEDS-COMPOSITING-BITS-UPDATE
  parentData: <none> (can use size)
  constraints: BoxConstraints(0.0<=w<=921.5, 0.0<=h<=512.9)
  size: MISSING
  behavior: opaque
  listeners: down
...  child: RenderSemanticsAnnotations#fe879 relayoutBoundary=up10 NEEDS-PAINT NEEDS-COMPOSITING-BITS-UPDATE
...    parentData: <none> (can use size)
...    constraints: BoxConstraints(0.0<=w<=921.5, 0.0<=h<=512.9)
...    size: MISSING
...    child: RenderIgnorePointer#74492 relayoutBoundary=up11 NEEDS-PAINT NEEDS-COMPOSITING-BITS-UPDATE
...      parentData: <none> (can use size)
...      constraints: BoxConstraints(0.0<=w<=921.5, 0.0<=h<=512.9)
...      size: MISSING
...      ignoring: false
...      ignoringSemantics: false
...      child: _RenderSingleChildViewport#3aec9 relayoutBoundary=up12 NEEDS-PAINT NEEDS-COMPOSITING-BITS-UPDATE
...        needs compositing
...        parentData: <none> (can use size)
...        constraints: BoxConstraints(0.0<=w<=921.5, 0.0<=h<=512.9)
...        size: MISSING
...        child: RenderRepaintBoundary#4986d relayoutBoundary=up13 NEEDS-PAINT NEEDS-COMPOSITING-BITS-UPDATE
...          needs compositing
...          parentData: <none> (can use size)
...          constraints: BoxConstraints(0.0<=w<=Infinity, 0.0<=h<=512.9)
...          size: MISSING
...          usefulness ratio: no metrics collected yet (never painted)

將每一行綁定到 ScrollController 似乎也不會讓整個列表一致地水平滾動:

Widget test() {
  ScrollController controller = ScrollController();

  Widget child = ListView.builder(
      itemCount: 2,
      shrinkWrap: true,
      itemBuilder: (context, i) {
        Widget child = rowSSMin_([
          Text(
              "AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA"),
          Text(
              "BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB"),
          Text(
              "XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX"),
        ]);
        child = scrollH(child, controller:controller);  // Added
        return child;
      });

  // child = scrollH(child, controller:controller);  // Removed

  return child;
}

您可以嘗試使用 Container 包裝可滾動小部件並將其高度和寬度設置為設備的大小:

Container(
  height: MediaQuery.of(context).size.height,
  width: MediaQuery.of(context).size.width,
  child: yourVerticallyOrHorizontallyScrollableWidget
)

是的,您可以,但是使用 2 SingleChildScrollView 並確保其中沒有 ListView。

     SingleChildScrollView(
        scrollDirection: Axis.vertical,
        child: SingleChildScrollView(
          scrollDirection: Axis.horizontal,
          child: Column(
            children: [ 
            \\ Your widgets
            ],
          ),
        ),
      ),

更新

如果你想像評論中所說的那樣使用 ListView.builder ,你應該做兩件事:

1- 為 listView 添加此屬性:

physics: NeverScrollableScrollPhysics()

2- 在任何應該具有寬度和高度的小部件中添加列表視圖。 並且這個寬度應該大於屏幕的寬度。

這是代碼

@override
  Widget build(BuildContext context) {
    return SafeArea(
      child: new Scaffold(
        body: SingleChildScrollView(
          scrollDirection: Axis.horizontal,
          child: SingleChildScrollView(
            scrollDirection: Axis.vertical,
            child: Container(
              width: MediaQuery.of(context).size.width * 1.8,
              height: MediaQuery.of(context).size.height,
              child: ListView.builder(
                  physics: NeverScrollableScrollPhysics(),
                  scrollDirection: Axis.vertical,
                  itemCount: 24,
                  shrinkWrap: false,
                  itemBuilder: (context, i) {
                    return Padding(
                      padding: const EdgeInsets.all(8.0),
                      child: Column(
                          crossAxisAlignment: CrossAxisAlignment.start,
                          children: [
                            Text(
                                "AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA AAAA"),
                            Text(
                                "BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB BBB"),
                            Text(
                                "XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX XXX"),
                          ]),
                    );
                  }),
            ),
          ),
        ),
      ),
    );
  }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM