【Flutter】十四、Flutter中常用的布局容器——流式布局Wrap、Flow

一、Wrap

熟悉flex布局的同学肯定知道flex布局会有wrap属性,就是换行,而Flex、Column、Row都是不可以换行的。那么如果我们需要换行怎么办呢?Flutte提供了Wrap来解决这一需求,Wrap与Flex具有相似的属性。

构造函数

Wrap({
    Key key,
    this.direction = Axis.horizontal, // 主轴方向
    this.alignment = WrapAlignment.start, //主轴方向上的对齐方式
    this.spacing = 0.0, // 主轴方向上children的间隔
    this.runAlignment = WrapAlignment.start, // children如何放置在交叉轴上
    this.runSpacing = 0.0, // 交叉轴上children的间隔
    this.crossAxisAlignment = WrapCrossAlignment.start, // children之间在交叉轴方向上的对齐方式
    this.textDirection, // 水平开始的方向
    this.verticalDirection = VerticalDirection.down, // 竖直的方向
    List<Widget> children = const <Widget>[],
  }) : super(key: key, children: children);

示例

import 'package:flutter/material.dart';

class WrapDemo extends StatelessWidget{
  @override
  Widget build(BuildContext context) {
    Widget c1 = Container(
      height: 130.0,
      width: 130.0,
      color: Colors.redAccent,
    );
    Widget c2 = Container(
      height: 50.0,
      width: 50.0,
      color: Colors.lightBlueAccent,
    );
    Widget c3 = Container(
      height: 80.0,
      width: 80.0,
      color: Colors.yellow,
    );
    Widget c4 =  Container(
      height: 100.0,
      width: 100.0,
      color: Colors.greenAccent,
    );
    Widget c5 = Container(
      height: 170.0,
      width: 170.0,
      color: Colors.grey,
    );
    // TODO: implement build
    return Container(
      width: double.infinity,
      height: double.infinity,
      child: Wrap(
        direction: Axis.horizontal,
        spacing: 10.0,
        runSpacing: 20.0,
        alignment: WrapAlignment.center,
        runAlignment: WrapAlignment.start,
        crossAxisAlignment: WrapCrossAlignment.start,
        verticalDirection: VerticalDirection.down,
        textDirection: TextDirection.ltr,
        children: <Widget>[c1, c2, c3, c4, c5],
      ),
    );
  }
}

    Wrap的相关属性大部分与Flex类似,如alignment与Flex的mainAxisAlignment类似,都决定了在主轴方向上的对齐方式;crossAlignment与Flex的crossAxisAlignment相似,都决定了children在交叉轴上的对齐方式。这里主要对runAlignment与crossAlignment属性进行说明,runAlignment属性决定了children整体如何放置在交叉轴上,而crossAlignment属性决定了children之间在交叉轴方向上的对齐方式。详细效果参考如下:

runAlignment值效果
WrapAlignment.start在这里插入图片描述
WrapAlignment.center在这里插入图片描述
WrapAlignment.end在这里插入图片描述
WrapAlignment.spaceBetween在这里插入图片描述
WrapAlignment.spaceAround在这里插入图片描述
WrapAlignment.spaceEvenly在这里插入图片描述

二、Flow

Flow可自定义children的排列布局,相对Wrap使用比较复杂。Flow中的delegate属性是自定义布局的关键,具体使用参考下面粒子。

import 'package:flutter/material.dart';

class FlowDemo extends StatelessWidget{
  @override
  Widget build(BuildContext context) {
    // TODO: implement build
    return Flow(
      delegate: TestFlowDelegate(margin:EdgeInsets.only(top: 10.0, left: 10.0)),
      children: <Widget>[
        Container(width: 80.0, height:80.0, color: Colors.red,),
        Container(width: 80.0, height:80.0, color: Colors.green,),
        Container(width: 80.0, height:80.0, color: Colors.blue,),
        Container(width: 80.0, height:80.0,  color: Colors.yellow,),
        Container(width: 80.0, height:80.0, color: Colors.brown,),
        Container(width: 80.0, height:80.0,  color: Colors.purple,),
      ],
    )
    ;
  }
}

class TestFlowDelegate extends FlowDelegate{
  EdgeInsets margin = EdgeInsets.zero;
  TestFlowDelegate({this.margin});
  @override
  void paintChildren(FlowPaintingContext context) {
    double x = margin.left;
    double y = margin.top;
    for (int i = 0; i < context.childCount; i++) {
      double w = context.getChildSize(i).width + x + margin.right;
      if (w < context.size.width) {
        context.paintChild(i, transform: new Matrix4.translationValues(x, y, 0.0));
        x = w + margin.left;
      } else {
        x = margin.left;
        y += context.getChildSize(i).height + margin.top + margin.bottom;
        context.paintChild(i, transform: new Matrix4.translationValues(x, y, 0.0));
        x += context.getChildSize(i).width + margin.left + margin.right;
      }
    }
  }

  @override
  bool shouldRepaint(FlowDelegate oldDelegate) {
    // TODO: implement shouldRepaint
    return oldDelegate != this;
  }

}

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

MAXLZ

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值