【Flutter】基础部件之Container

1,470 阅读4分钟

「这是我参与11月更文挑战的第3天,活动详情查看:2021最后一次更文挑战」。

前言

前文【Flutter】基础组件之Text简单介绍了Text组件,本文就来介绍下Container组件。

一: Container

Container是将普通绘画、定位和调整widget大小相结合的便利widget

1.1 Container结构

Container通常作为其他widget的容器使用,所以最主要的属性就是child(子widget,类似于iOSsubview)。

Container首先使用padding包围child,然后对填充范围应用附加constraints(如果其中一个非空,则将宽度和高度合并为约束),最后,Containermargin描述的其他空位包围。

在绘制过程中,Container首先应用给定的transform,然后绘制decoration以填充填充范围,然后绘制child,最后绘制foregroundDecoration,也填充填充范围。

没有子widgetContainer会尽量大。除非传入的constraintsunbounded(无界的),在这种情况下,它们会尽量小。

带有子widgetContainer,会根据子widget的大小调整自身大小。但是如果构造函数中包含widthheightconstraints ,则会按照构造函数的参数来进行自身大小的调节。

默认情况下,对于所有hit testContainer都返回false。如果指定了color属性,则hit testColoredBox处理,它始终返回true。如果指定了decorationforegroundDecoration属性,则通过Decoration.hitTest处理hit test

1.2 Container布局

由于Container结合了许多其他widget,每个widget都有自己的布局行为,所以Container的布局行为有些复杂。

概要:

  • Container尝试,顺序是:遵循alignment、根据child调整自身大小、遵循widthheightconstraints、扩展自身以适应父部件、调节自身到尽可能小。

更具体地说:

  • 如果没有子部件、widthheightconstraints,并且父部件提供了unbounded constraints,则Container会尝试将自身调节到尽可能小。

  • 如果没有子部件,也没有alignment(对齐方式),但是提供了widthheightconstraints,那么Container将根据这些约束和父部件的约束,将自身调节到尽可能小。

  • 如果没有子部件、widthheightconstraintsalignment,但父部件提供了bounded constraints,则Container将展开以适应父部件提供的约束。

  • 如果有alignment,并且父部件提供了unbounded constraints,那么Container将尝试围绕子部件调整自身大小。

  • 如果有alignment,并且父部件提供了bounded constraints,则Container将尝试展开以适应父部件,然后根据alignment将子部件定位到自身中。

  • 如果有子部件,但没有widthheightconstraintsalignmentContainer将约束从父部件传递给子部件,并调整自身大小以匹配子部件。

  • marginpadding属性也会影响布局,如这些属性的文档中所述(它们的效果只是增强了上述规则)。decoration可以隐含地增加padding

1.3 Container基础属性

image.png

  • keywidget唯一标识,用于验证、更新。

  • alignment:控制child的对齐方式,如果container或者container的父组件尺寸大于child的尺寸,这个属性设置会起作用。

  • paddingdecoration内部的空白区域。如果有child,位于padding内部。

  • colorContainer背景色。如果设置foregroundDecoration,可能会遮盖color效果。

  • decoration:绘制在child后面的装饰,使用color属性指定简单的纯色。

  • foregroundDecoration:在child面前绘制的装饰。

  • constraints:应用于child的额外约束,

  • margin:环绕decorationchild的空白区域。

  • transform:绘制容器之前要应用的变换矩阵。

  • transformAlignment:如果指定了transform,则为原点相对于Container大小的对齐方式。

  • childContainer的子部件。

  • clipBehavior:剪切行为,Container.decoration不为null时有效。

paddingmargin的区别: padding包含在content内,而margin则是外部边界,padding区域可以响应交互,而margin区域不可以。

1.4 Container使用举例

void main() {
  // 执行runApp,传入widget,就会显示到屏幕上了
  runApp(
      MyApp()
  );
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    // TODO: implement build
    return Container(
      margin: EdgeInsets.all(10),
      color: Colors.white,
      alignment: Alignment.center,
      child: Container(
        constraints: BoxConstraints.expand(
          height: Theme.of(context).textTheme.headline4!.fontSize! * 1.1 + 200,
        ),
        padding: const EdgeInsets.all(10.0),
        color: Colors.blue[600],
        alignment: Alignment.center,
        child: Text('Hello Flutter',
          style: Theme.of(context)
                .textTheme
                .headline4!
                .copyWith(color: Colors.white),
            textDirection: TextDirection.ltr,
        ),
        transform: Matrix4.rotationZ(0.1),
      ),
    );
  }
}

运行效果:

image.png

关于Container的更多内容,请移步官方文档Container

期待关注,持续输出。