00. 目录

文章目录

  • 00. 目录
  • 01. 概述
  • 02. 开发环境
  • 03. 常用函数详解
  • 04. Qt设计师使用网格布局
  • 05. 使用代码实现网格布局
  • 06. 附录

01. 概述

QGridLayout:格栅布局,也被称作网格布局(多行多列)。

栅格布局将位于其中的窗口部件放入一个网状的栅格之中。QGridLayout需要将提供给它的空间划分成的行和列,并把每个窗口部件插入并管理到正确的单元格。 栅格布局是这样工作的:

它计算了位于其中的空间,然后将它们合理的划分成若干个行(row)和列(column),并把每个由它管理的窗口部件放置在合适的单元之中,这里所指的单元(cell)即是指由行和列交叉所划分出来的空间。

在栅格布局中,行和列本质上是相同的,只是叫法不同而已。下面将重点讨论列,这些内容当然也适用于行。

在栅格布局中,每个列(以及行)都有一个最小宽度(使用setColumnMinimumWidth()设置)以及一个伸缩因子(使用setColumnStretch()设置)。最小宽度指的是位于该列中的窗口部件的最小的宽度,而伸缩因子决定了该列内的窗口部件能够获得多少空间。

02. 开发环境

Windows系统:Windows10

Qt版本:Qt5.15或者Qt6

03. 常用函数详解

QGridLayout 类将控件放置到网格中布局,它本身会从父窗口或父布局中占据尽可能多的界面空间,然后把自己的空间划分为行和列,再把每个控件塞到设置好的一个或多个单元格中。

QGridLayout 类既有控制行的函数,也有对应控制列的函数。对于列来说,有设置每列的最小宽度的函数:
void setColumnMinimumWidth(int column, int minSize)
如果要设置各个列在窗口变化时拉伸比例不同,可以用如下函数:
void setColumnStretch(int column, int stretch)
每列控件之间可以设置布局的水平间隙:
void setHorizontalSpacing(int spacing)
对于行,也都有类似的函数,只是把英文单词换一下:
void setRowMinimumHeight(int row, int minSize) //设置行最小高度
void setRowStretch(int row, int stretch)       //设置行的伸展因子
void setHorizontalSpacing(int spacing)         //设置行的垂直间隙如果要添加控件或其他布局器、自定义布局条目,使用如下函数:
void addWidget(QWidget * widget, int row, int column, Qt::Alignment alignment = 0)
void addWidget(QWidget * widget, int fromRow, int fromColumn, int rowSpan, int columnSpan, Qt::Alignment alignment = 0)
void addLayout(QLayout * layout, int row, int column, Qt::Alignment alignment = 0)
void addLayout(QLayout * layout, int row, int column, int rowSpan, int columnSpan, Qt::Alignment alignment = 0)
void addItem(QLayoutItem * item, int row, int column, int rowSpan = 1, int columnSpan = 1, Qt::Alignment alignment = 0)
函数第一个参数都是要添加的控件、布局器或自定义布局条目,
row 和 column 是左上角起始的单元格坐标,
如果没有指定 rowSpan 和 columnSpan 那么就是 1*1 的唯一单元格,
指定了 rowSpan 和 columnSpan 就会占据 rowSpan * columnSpan 的小矩形,占据连续多行多列单元格。
最后的 alignment 是控件或布局器、布局条目在单元格中的对齐方式,比如水平的左对齐、居中、右对齐,垂直方向顶部对齐、底部对齐、垂直居中等等,具体 的可以查 Qt 帮助文档。Qt 关于对齐方式的枚举常量都是通用的。
通常情况下 QGridLayout 不需要自己添加空白条 QSpacerItem,因为其他功能控件把各自的单元格占据之后,剩下没控件占据的单元格自然就是空的,空的格子默认里面什么都没有,也没有空白条。
如果要获知网格有多少行、有多少列(包括空的格子计数),使用如下函数:
int rowCount() const      //行计数
int columnCount() const   //列计数
如果要获取某个单元格的布局条目,使用:
QLayoutItem * itemAtPosition(int row, int column) const
注意,如果某个格子是全空的,也没有手动添加空白条,那么 itemAtPosition() 返回 NULL 指针。因此使用这个函数必须判断返回值是否为空。rowCount * columnCount 是总共的单元格计数,但并不是控件或子布局的计数。控件或子布局的计数用重载的虚函数:
virtual int count() const
用 add* 函数添加控件或子布局时,每个控件或子布局都对应一个序号,这个序号与网格坐标是无关的,是由 add* 函数添加顺序决定的。
QGridLayout 提供了根据控件或子布局序号查询单元格位置、分布的函数(但没有反查序号的函数):
void getItemPosition(int index, int * row, int * column, int * rowSpan, int * columnSpan) const
getItemPosition() 函数会填充参数里的四个指针指向的变量,四个指针指向的变量就是 add* 函数里面指定的单元格坐标和分布。
根据控件或子布局的序号获取布局条目的函数为:
virtual QLayoutItem * itemAt(int index) const
根据控件序号可以从 QGridLayout 中移除布局条目:
virtual QLayoutItem * takeAt(int index)
凡是函数返回值为指针的都要判断是否为空指针,因为上面函数的序号如果超出范围,也会返回空指针。涉及到指针的操作一定要细心判断。得到非空的 QLayoutItem 对象指针之后,就可以从 QLayoutItem 对象里提取实际的控件或布局器、空白条:
QWidget * QLayoutItem::​widget()
QLayout * QLayoutItem::​layout()
QSpacerItem * QLayoutItem::​spacerItem()
另外如果是自己定制的 QLayoutItem 派生类对象,可以把获取的基类对象指针 QLayoutItem * ,通过 dynamic_cast 转成派生类对象指针试试。 注意判断函数返回的指针是否为空,非空指针才能进行下一步操作。

04. Qt设计师使用网格布局

第一种方式:选中所有需要使用网格布局的控件,然后鼠标右击选择布局,然后再选择网格布局。

第二种方式:选中所有需要使用网格布局的控件,然后在工具栏中选择使用网格布局。

05. 使用代码实现网格布局

程序示例一:

#include <QApplication>#include <QGridLayout>
#include <QPushButton>
#include <QWidget>
#include <QObject>
#include <QDebug>int main(int argc, char **argv)
{QApplication a(argc, argv);QWidget w;//创建布局对象QGridLayout *layout = new QGridLayout();QPushButton *btn1 = new QPushButton;btn1->setText("Test Button 1");//设置组件大小可以扩展btn1->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn1->setMinimumSize(160, 30);QPushButton *btn2 = new QPushButton;btn2->setText("Test Button 2");//设置组件大小可以扩展btn2->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn2->setMinimumSize(160, 30);QPushButton *btn3 = new QPushButton;btn3->setText("Test Button 3");//设置组件大小可以扩展btn3->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn3->setMinimumSize(160, 30);QPushButton *btn4 = new QPushButton;btn4->setText("Test Button 4");//设置组件大小可以扩展btn4->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn4->setMinimumSize(160, 30);//设置间距layout->setSpacing(10);//网格不同坐标添加不同的组件layout->addWidget(btn1, 0, 0);layout->addWidget(btn2, 0, 1);layout->addWidget(btn3, 1, 0);layout->addWidget(btn4, 1, 1);//设置行列比例系数layout->setRowStretch(0, 1);layout->setRowStretch(1, 3);layout->setColumnStretch(0, 1);layout->setColumnStretch(1, 3);w.setLayout(layout);w.show();return a.exec();
}

执行结果

程序示例二:

#include <QApplication>#include <QGridLayout>
#include <QPushButton>
#include <QWidget>
#include <QObject>
#include <QDebug>int main(int argc, char **argv)
{QApplication a(argc, argv);QWidget w;//创建布局对象QGridLayout *layout = new QGridLayout();QPushButton *btn1 = new QPushButton("one");QPushButton *btn2 = new QPushButton("two");QPushButton *btn3 = new QPushButton("three");QPushButton *btn4 = new QPushButton("four");QPushButton *btn5 = new QPushButton("five");layout->addWidget(btn1, 0, 0);layout->addWidget(btn2, 0, 1);layout->addWidget(btn3, 1, 0, 1, 2);layout->addWidget(btn4, 2, 0);layout->addWidget(btn5, 2, 1);w.setLayout(layout);w.show();return a.exec();
}

执行结果

程序示例三:

#include <QApplication>#include <QGridLayout>
#include <QPushButton>
#include <QWidget>
#include <QObject>
#include <QDebug>int main(int argc, char **argv)
{QApplication a(argc, argv);QWidget w;//创建布局对象QGridLayout *layout = new QGridLayout();QPushButton *btn1 = new QPushButton;btn1->setText("Test Button 1");//设置组件大小可以扩展btn1->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn1->setMinimumSize(160, 30);QPushButton *btn2 = new QPushButton;btn2->setText("Test Button 2");//设置组件大小可以扩展btn2->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn2->setMinimumSize(160, 30);QPushButton *btn3 = new QPushButton;btn3->setText("Test Button 3");//设置组件大小可以扩展btn3->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn3->setMinimumSize(160, 30);QPushButton *btn4 = new QPushButton;btn4->setText("Test Button 4");//设置组件大小可以扩展btn4->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn4->setMinimumSize(160, 30);//设置间距layout->setSpacing(10);//网格不同坐标添加不同的组件//坐标(0, 0)的组件占用两行一列layout->addWidget(btn1, 0, 0, 2, 1);//坐标(0, 1)的组件占用两行一列layout->addWidget(btn2, 0, 1, 2, 1);//坐标(2, 0)的组件占用一行两列layout->addWidget(btn3, 2, 0, 1, 2);//坐标(3, 0)的组件占用一行两列layout->addWidget(btn4, 3, 0, 1, 2);w.setLayout(layout);w.show();return a.exec();
}

执行结果

程序示例四:

#include <QApplication>#include <QGridLayout>
#include <QVBoxLayout>
#include <QPushButton>
#include <QWidget>
#include <QObject>
#include <QDebug>int main(int argc, char **argv)
{QApplication a(argc, argv);QWidget w;//创建布局对象QGridLayout *gLayout = new QGridLayout();QVBoxLayout *vLayout = new QVBoxLayout();QPushButton *btn1 = new QPushButton;btn1->setText("Test Button 1");//设置组件大小可以扩展btn1->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn1->setMinimumSize(160, 30);QPushButton *btn2 = new QPushButton;btn2->setText("Test Button 2");//设置组件大小可以扩展btn2->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn2->setMinimumSize(160, 30);QPushButton *btn3 = new QPushButton;btn3->setText("Test Button 3");//设置组件大小可以扩展btn3->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn3->setMinimumSize(160, 30);QPushButton *btn4 = new QPushButton;btn4->setText("Test Button 4");//设置组件大小可以扩展btn4->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn4->setMinimumSize(160, 30);QPushButton *btn5 = new QPushButton;btn5->setText("Test Button 5");//设置组件大小可以扩展btn5->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);//设置最小尺寸btn5->setMinimumSize(160, 30);gLayout->setSpacing(10);//编号为1 2 3的进行网格布局gLayout->addWidget(btn1, 0, 0);gLayout->addWidget(btn2, 0, 1);gLayout->addWidget(btn3, 1, 0);//将编号为4 5的按钮添加到垂直布局器中vLayout->addWidget(btn4);vLayout->addWidget(btn5);//布局管理器嵌套gLayout->addLayout(vLayout, 1, 1);w.setLayout(gLayout);w.show();return a.exec();
}

执行结果:

程序示例五:

#include <QApplication>#include <QGridLayout>
#include <QVBoxLayout>
#include <QPushButton>
#include <QWidget>
#include <QObject>
#include <QLabel>
#include <QLineEdit>
#include <QCheckBox>
#include <QDebug>int main(int argc, char **argv)
{QApplication a(argc, argv);QWidget w;// 构建控件 头像、用户名、密码输入框等QLabel *pImageLabel = new QLabel;QLineEdit *pUserLineEdit = new QLineEdit;QLineEdit *pPasswordLineEdit = new QLineEdit;QCheckBox *pRememberCheckBox = new QCheckBox;QCheckBox *pAutoLoginCheckBox = new QCheckBox;QPushButton *pLoginButton = new QPushButton;QPushButton *pRegisterButton = new QPushButton;QPushButton *pForgotButton = new QPushButton;pLoginButton->setFixedHeight(30);pUserLineEdit->setFixedWidth(200);// 设置头像QPixmap pixmap("../image/b.png");pImageLabel->setFixedSize(90, 90);pImageLabel->setPixmap(pixmap);pImageLabel->setScaledContents(true);// 设置文本pUserLineEdit->setPlaceholderText(QStringLiteral("QQ号码/手机/邮箱"));pPasswordLineEdit->setPlaceholderText(QStringLiteral("密码"));pPasswordLineEdit->setEchoMode(QLineEdit::Password);pRememberCheckBox->setText(QStringLiteral("记住密码"));pAutoLoginCheckBox->setText(QStringLiteral("自动登录"));pLoginButton->setText(QStringLiteral("登录"));pRegisterButton->setText(QStringLiteral("注册账号"));pForgotButton->setText(QStringLiteral("找回密码"));QGridLayout *pLayout = new QGridLayout();// 头像 第0行,第0列开始,占3行1列pLayout->addWidget(pImageLabel, 0, 0, 3, 1);// 用户名输入框 第0行,第1列开始,占1行2列pLayout->addWidget(pUserLineEdit, 0, 1, 1, 2);pLayout->addWidget(pRegisterButton, 0, 4);// 密码输入框 第1行,第1列开始,占1行2列pLayout->addWidget(pPasswordLineEdit, 1, 1, 1, 2);pLayout->addWidget(pForgotButton, 1, 4);// 记住密码 第2行,第1列开始,占1行1列 水平居左 垂直居中pLayout->addWidget(pRememberCheckBox, 2, 1, 1, 1, Qt::AlignLeft | Qt::AlignVCenter);// 自动登录 第2行,第2列开始,占1行1列 水平居右 垂直居中pLayout->addWidget(pAutoLoginCheckBox, 2, 2, 1, 1, Qt::AlignRight | Qt::AlignVCenter);// 登录按钮 第3行,第1列开始,占1行2列pLayout->addWidget(pLoginButton, 3, 1, 1, 2);// 设置水平间距pLayout->setHorizontalSpacing(10);// 设置垂直间距pLayout->setVerticalSpacing(10);// 设置外间距pLayout->setContentsMargins(10, 10, 10, 10);w.setLayout(pLayout);w.show();return a.exec();
}

执行结果:

06. 附录

6.1 Qt教程汇总
网址:https://dengjin.blog.csdn.net/article/details/115174639

【Qt】Qt之网格布局相关推荐

  1. Qt Quick - GridLayout 网格布局

    GridLayout 理论总结 一.概述 二.依赖属性 三.例子 1. 不含跨行的 2. 带跨行列的 3. 从右到左 一.概述 GridLayout 是最常用的布局器,也叫网格布局器,如果网格布局被调 ...

  2. Python界面编程第十三课:Pyside2 (Qt For Python)GridLayout网格布局

    GridLayout 是什么? QGridLayout 是控制网格布局的类. QGridLayout 会占据它的可用空间(通过父布局或parentWidget(),将其划分为行和列,并将其管理的每个控 ...

  3. Qt窗口部件与布局之二:布局管理

    第3章讲述了一些窗口部件,当时往界面上拖放部件时都是随意放置的,这对于学习部件的使用没有太大的影响,但是,对于一个完善的软件,布局管理却是必不可少的. 无论是想要界面中部件有一个很整齐的排列,还是想要 ...

  4. 用qt做python界面设计_Python GUI教程(六):使用Qt设计师进行窗口布局

    本篇介绍使用qt设计师进行GUI窗口的布局管理,主要包含以下内容:使用Qt设计师布局我们的窗口部件: 垂直布局: 水平布局: 网格布局: 使用间隔: 使用"伙伴"将label标签与 ...

  5. qt 设置按钮大小_Python GUI教程(六):使用Qt设计师进行窗口布局

    本篇介绍使用qt设计师进行GUI窗口的布局管理,主要包含以下内容: 使用Qt设计师布局我们的窗口部件: 垂直布局: 水平布局: 网格布局: 使用间隔: 使用"伙伴"将label标签 ...

  6. 4.UI界面PyQt-三大布局(盒子布局、网格布局、表单布局)

    1.1盒子布局-BoxLayout垂直 代码如下(示例): import sysfrom PyQt5.QtWidgets import (QApplication, QWidget, QVBoxLay ...

  7. css 网格布局_我从CSS网格布局中学到的东西

    css 网格布局 by Jennifer Wjertzoch 珍妮弗·维佐奇 我从CSS网格布局中学到的东西 (Things I've learned about CSS grid layout) W ...

  8. CSS Grid 网格布局全解析

    一.介绍 CSS Grid(网格) 布局使我们能够比以往任何时候都可以更灵活构建和控制自定义网格. Grid(网格) 布局使我们能够将网页分成具有简单属性的行和列.它还能使我们在不改变任何HTML的情 ...

  9. jQuery Masonry 一个 jQuery动态网格布局的插件

    jQuery Masonry 是一个 jQuery动态网格布局的插件. 每个元素都是漂浮在固定的网格布局上面,就像一枚图钉定在墙上一样. 我们发现以下的15网站使用jQuery Masonry的范例. ...

最新文章

  1. 【TX2】TX2开发板系统默认串口有ttyS0(调试口)、ttyTHS1、ttyTHS2、ttyTHS3,通过修改设备树文件,可以新增三个串口
  2. 让资源管理器不显示最近常用文件夹
  3. Windows 10 技术预览
  4. java 素数 五行_【数论】素数的判定与筛法
  5. oracle冷备份/恢复
  6. TCP三次握手及四次挥手详细图解(转)
  7. 华为笔记本会不会用鸿蒙,华为MateBook Pro笔记本为什么不用鸿蒙操作系统HarmonyO?...
  8. 【JVM】第二章 JVM类加载、JVM对象
  9. MacBook Pro、iPad所需OLED屏幕有望由三星供应
  10. python性能测试台_性能测试平台效率优化的一次经验(python版)
  11. JAVA在线购物B2C商城源码
  12. ios 基础知识点总结
  13. 使用html制作一个网页
  14. 【防火墙篇】03. Web 登录 ❀ Juniper 防火墙
  15. 每日一问。2015.1.8
  16. 网站开发之ie下在线浏览pdf文件无需本地支持
  17. 如何取消QQ看点的消息通知?
  18. Karto Slam 参数配置
  19. 【Unity小游戏】打字消除字母
  20. EasyClick 易点云测 IOS版自动化测试工具

热门文章

  1. Android开发之Android Material Design Toolbar自定义随笔
  2. Java反射机制Reflection
  3. 【C/C++】实型变量
  4. ASP.NET MVC下使用SWFUpload完成剪切头像功能
  5. Mvc中使用MvcSiteMapProvider实现站点地图之基础篇
  6. windbg学习.formats--转换成各种进制
  7. SQLServer当数据导入平面文件
  8. 再发:VS怎么会这个样子的?
  9. oracle带输出参数存储,oracle带输入输出参数存储过程(包括sql分页功能)
  10. Java黑皮书课后题第2章:2.5(金融应用:计算小费)编写一个程序,读入一笔费用与小费利率,计算小费和总钱数