Qt学习之路13--布局管理器(QBoxLayout)

版权声明:未经说明,禁止转载 https://blog.csdn.net/tqs_1220/article/details/81841571

布局管理器

  • 在之前的GUI开发中我们通常使用绝对定位的方式,通过move函数和resize函数进行位置确定,这种方式是直接在像素级别上进行定位,这样的方式就会存在一个比较严重的问题,那就是坐标信息无法根据窗口大小进行位置自适应。
  • 在Qt中有另外一种方案能够实现对窗口组件进行布局–布局管理器。
  • 通过使用布局管理器后能够使得窗口中的组件进行自动排列;当窗口大小发生变化后其内部的组件大小也会随之变化以达到适应窗口变化。
  • Qt的布局管理器统一使用QLayout作为抽象基类,所有的布局管理器通过继承QLayout实现了功能各异且互补的布局管理,面向对象的好处就是能够以统一的方式来思考一个陌生的事物。
  • 可以根据需要自定义布局管理器。
  • 需要注意的是,布局管理器不是界面元素,这说明他们是不可见的,它只是界面中的一种定位策略,帮助窗口管理界面组件。

Qt预定义的布局管理器总共有四种:QBoxLayout、QGridLayout、QFormLayout、QStackedLayout,它们都是QLayout的子类。
这里写图片描述

QBoxLayout

在QBoxLayout布局管理器中又分为两类:垂直布局管理器QVBoxLayout和水平布局管理器QHBoxLayout,它们继承自QBoxLayout。
这里写图片描述
两者最大的特点就是单行或单列的依次排布。
这里写图片描述

QVBoxLayout

通过几个按钮简单的看看一个QVBoxLayout的使用应该注意哪些细节。
假设按钮组件已经在别的地方定义。

QVBoxLayout* layout = new QVBoxLayout();

TestBtn1.setText("TestBtn1");
TestBtn1.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置大小策略,宽度和高度都设置成可扩展
TestBtn1.setMinimumSize(160,30);//设置按钮的最小尺寸

TestBtn2.setText("TestBtn2");
TestBtn2.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
TestBtn2.setMinimumSize(160,30);

TestBtn3.setText("TestBtn3");
TestBtn3.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
TestBtn3.setMinimumSize(160,30);

TestBtn4.setText("TestBtn4");
TestBtn4.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
TestBtn4.setMinimumSize(160,30);//设置最小size

layout->setSpacing(30);//设置按钮之间的距离
layout->addWidget(&TestBtn1);//将组件添加到布局管理器
layout->addWidget(&TestBtn2);
layout->addWidget(&TestBtn3);
layout->addWidget(&TestBtn4);

layout->setStretch(0,1);//设置索引为0的按钮大小的比例系数为1
layout->setStretch(1,2);//设置索引为1的按钮大小的比例系数为2
layout->setStretch(2,3);//设置索引为2的按钮大小的比例系数为3
layout->setStretch(3,4);//设置索引为3的按钮大小的比例系数为4

setLayout(layout);//为顶级Widget设置一个布局管理器
  • 首先是需要一个QVBoxLayout垂直布局管理器对象,再就是设置按钮的属性,然后将按钮组件添加到布局管理器中,同时为了布局明确可以按照一定的拉伸系数对组件的大小比例进行设置,默认情况下以等比例的方式更新组件的大小关系,最后一步就是将当前的布局管理器对象设置到顶层Widget中,大体四步就能对一个布局管理器进行简单的使用。
  • 组件的初始大小是独立于布局管理器设置的,因此不能保证组件的大小始终符合比例系数的设置,通过设置按钮长宽一个最小值,这样在初始时布局管理器就没法直接更改组件之间的比例关系,而是随着不断的拉伸来达到设定的比例。

未经过拉伸的按钮之间的布局。
这里写图片描述

经过水平和垂直拉伸后的按钮之间的布局。
这里写图片描述
这样通过布局管理器管理窗口组件后就不会因为窗口变化导致整体界面布局出现巨大变化。

QHBoxLayout

在水平布局管理器的使用中和垂直布局管理器一模一样,唯一的区别就是两者对组件的管理方式不同,同样是上面的代码,在使用水平布局管理器后的结果是这样的。
这里写图片描述

布局管理器嵌套

布局管理器不仅能够单独使用而且还能够嵌套使用,就是一个布局管理器去管理其他的布局管理器,进而形成更加复杂的界面布局管理。通过使用布局嵌套几乎可以完成所有的常用界面布局。

在之前的四个按钮如果使用布局嵌套达到两行两列的效果的话其结果就是这样:
这里写图片描述
通过一个垂直布局管理器来嵌套管理两个水平布局管理器。

QHBoxLayout* Hlayout1 = new QHBoxLayout();//两个子布局管理器
QHBoxLayout* Hlayout2 = new QHBoxLayout();
QVBoxLayout* Vlayout = new QVBoxLayout();//顶级布局管理器

//设置水平布局管理器
TestBtn1.setText("TestBtn1");
TestBtn1.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置大小策略,宽度和高度都设置成可扩展
TestBtn1.setMinimumSize(160,30);

TestBtn2.setText("TestBtn2");
TestBtn2.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
TestBtn2.setMinimumSize(160,30);

Hlayout1->setSpacing(30);//设置按钮之间的距离
Hlayout1->addWidget(&TestBtn1);//添加按钮到水平布局管理器
Hlayout1->addWidget(&TestBtn2);

//设置水平布局管理器
TestBtn3.setText("TestBtn3");
TestBtn3.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
TestBtn3.setMinimumSize(160,30);

TestBtn4.setText("TestBtn4");
TestBtn4.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
TestBtn4.setMinimumSize(160,30);//设置最小size

Hlayout2->setSpacing(30);//设置按钮之间的距离
Hlayout2->addWidget(&TestBtn3);//添加组件
Hlayout2->addWidget(&TestBtn4);


//布局管理器嵌套
Vlayout->addLayout(Hlayout1);
Vlayout->addLayout(Hlayout2);

Vlayout->setStretchFactor(Hlayout1, 1);//设置布局管理器比例系数
Vlayout->setStretchFactor(Hlayout2, 3);

setLayout(Vlayout);//将Vlayout设置成顶级布局管理器,它能管理其他的布局管理器

代码其实很简单,我们需要知道的不过就是使用布局管理器嵌套的套路,就是分别对子布局管理器进行布局设置,再使用顶级布局管理器对子布局管理器进行管理。
这里写图片描述

QBoxLayout的比例系数设置

void setStretch(int index, int stretch);

在一系列组件中,设置某个索引的组件的比例系数为stretch。

layout->setStretch(0,1);//设置索引为0的格子的比例系数为1
layout->setStretch(1,2);//设置索引为1的格子的比例系数为2
layout->setStretch(2,3);//设置索引为2的格子的比例系数为3
layout->setStretch(3,4);//设置索引为3的格子的比例系数为4

bool setStretchFactor(QWidget* widget, int stretch);

在一系列组件中,通过组件地址(QWidget或继承自QWidegt类对象指针即可)来设置比例系数

layout->setStretchFactor(&TestBtn1, 1);//比例为1:2:3:4
layout->setStretchFactor(&TestBtn2, 2);
layout->setStretchFactor(&TestBtn3, 3);
layout->setStretchFactor(&TestBtn4, 4);

bool setStretchFactor(QLayout* layout, int stretch);

在一系列组件中,通过布局管理器地址(QLayout或继承自QLayout类对象指针即可)来设置比例系数

Vlayout->setStretchFactor(Hlayout1, 1);//比例为1:3
Vlayout->setStretchFactor(Hlayout2, 3);

由于
TestBtn4.setMinimumSize(160,30);//设置最小size
有这么行代码,

小结

  • 绝对定位的方式无法适应窗口变化带来的影响
  • Qt提供相关类实现布局管理
  • 布局管理器能够相互嵌套构成更加复杂的界面

猜你喜欢

转载自blog.csdn.net/tqs_1220/article/details/81841571