可能相关:https://stackoverflow.com/a/30860285/3363018
我一直在尝试创建一个 QML 布局,其中的项目跨越可变数量的行和列。例如,一个跨越两行和四列的矩形,其右侧的一个跨越一行和两列,下面的一个跨越三行和五列。创建此的一般尝试如下:
import QtQuick 2.5
import QtQuick.Layouts 1.2
import QtQuick.Controls 1.4
ApplicationWindow {
visible: true
width: 640
height: 480
title: qsTr("Hello, World")
GridLayout {
anchors.fill: parent
columns: 5
rows: 2
Rectangle {
Layout.column: 0
Layout.columnSpan: 4
Layout.row: 0
Layout.rowSpan: 2
Layout.fillHeight: true
Layout.fillWidth: true
color: "red"
}
Rectangle {
Layout.column: 4
Layout.columnSpan: 1
Layout.row: 0
Layout.rowSpan: 2
Layout.fillHeight: true
Layout.fillWidth: true
color: "green"
}
Rectangle {
Layout.column: 0
Layout.columnSpan: 5
Layout.row: 2
Layout.rowSpan: 3
Layout.fillHeight: true
Layout.fillWidth: true
color: "blue"
}
}
}
结果如下:
如您所见,
Layout.rowSpan
和Layout.columnSpan
似乎不起作用。相反,顶部两行似乎占据了 1:1 而不是 4:1,顶部与底部的比例是 1:1 而不是 2:3。我怀疑这与Layout.fillHeight
和Layout.fillWidth
有关。 文档指出:
如果此属性为 true,则该项目将尽可能宽,同时 尊重给定的限制。
但是,我不确定在这种情况下“给定的约束”是什么。我原本希望它包含行和列跨度,但似乎没有。
我可能可以直接计算项目的宽度和高度(或者可能是
Layout.preferredWidth
和Layout.preferredHeight
),但这似乎使得Layout.rowSpan
和Layout.columnSpan
完全多余。有没有办法根据网格行和列自动计算高度?
我遇到了和你一样的问题,但我认为很容易误解 GridLayout 正在做什么。如果你有 5 列 2 行的网格,你会得到类似这样的东西,其中每个 O 代表一个单元格:
grid
OOOOO
OOOOO
rowSpan 确定对象的TALL 的高度。
columnSpan 确定对象的WIDE 程度。
您想要将这些放入此网格中:
r1 r2 r3
OOOO OO OOOOO
OOOO OOOOO
OOOOO
不难看出,但它们不适合。
这是我对 12x12 网格的解决方案,应该很容易遵循。 GridLayout 似乎不会自动知道分配给其子级的宽度和高度。但这没关系,您可以轻松定义它。本质上,我将矩形传递给我的两个短两个函数。您可以传递 rowSpan 或 columnSpan 但我更喜欢这种方式,因为我不必记住哪个函数需要什么:
GridLayout {
id : grid
anchors.fill: parent
rows : 12
columns : 12
property double colMulti : grid.width / grid.columns
property double rowMulti : grid.height / grid.rows
function prefWidth(item){
return colMulti * item.Layout.columnSpan
}
function prefHeight(item){
return rowMulti * item.Layout.rowSpan
}
Rectangle {
color : 'red'
Layout.rowSpan : 10
Layout.columnSpan: 2
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
Rectangle {
color : 'yellow'
Layout.rowSpan : 10
Layout.columnSpan: 10
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
Rectangle {
id : greenRect
color : 'green'
Layout.rowSpan : 2
Layout.columnSpan : 12
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
}
结果在这里:
右上角矩形的描述已转置行和列。应该是:
右侧的一个跨越一列和两行
行数不正确。应该是:
columns: 5
rows: 5
将首选宽度和高度指定为百分比或单位。我使用下面的单位是因为它更容易与您的 4:1 和 2:3 比例相关:
GridLayout {
anchors.fill: parent
columns: 5
rows: 5 // was 2
Rectangle {
Layout.column: 0
Layout.columnSpan: 4
Layout.row: 0
Layout.rowSpan: 2
Layout.preferredWidth: 4 // 4 of 5 cols
Layout.preferredHeight: 2 // 2 of 5 rows
Layout.fillHeight: true
Layout.fillWidth: true
color: "red"
}
Rectangle {
Layout.column: 4
Layout.columnSpan: 1
Layout.row: 0
Layout.rowSpan: 2
Layout.preferredWidth: 1 // 1 of 5 cols
Layout.preferredHeight: 2 // 2 of 5 rows
Layout.fillHeight: true
Layout.fillWidth: true
color: "green"
}
Rectangle {
Layout.column: 0
Layout.columnSpan: 5
Layout.row: 2
Layout.rowSpan: 3
Layout.preferredHeight: 3 // 3 of 5 rows
Layout.fillHeight: true
Layout.fillWidth: true
color: "blue"
}
}
GridLayout {
anchors.fill: parent
columns: 2
Rectangle {
Layout.fillWidth: true
Layout.fillHeight: true
Layout.preferredWidth: 80
Layout.preferredHeight: 40
color: "red"
}
Rectangle {
Layout.fillWidth: true
Layout.fillHeight: true
Layout.preferredWidth: 20
Layout.preferredHeight: 40
color: "green"
}
Rectangle {
Layout.fillWidth: true
Layout.fillHeight: true
Layout.columnSpan: 2
Layout.preferredWidth: 100
Layout.preferredHeight: 60
color: "blue"
}
}
如果一行上的所有元素都设置了
Layout.fillWidth
true
,则它们的首选宽度将用于确定它们的比例宽度。将元素的 preferredWidth
绑定到其 columnspan
会建立 GridLayout 用于计算元素宽度的比率:在具有 5 列的网格中,跨度为 4 会导致元素占据网格总宽度的 80%。对于列中的元素也是如此。此解决方案使用 Qt 5.15 内联组件:
GridLayout {
anchors.fill: parent
columns: 5
rows: 5
component ProportionalRect: Rectangle {
Layout.fillHeight: true
Layout.fillWidth: true
Layout.preferredWidth: Layout.columnSpan
Layout.preferredHeight: Layout.rowSpan
}
ProportionalRect {
Layout.columnSpan: 4
Layout.rowSpan: 2
color: "red"
}
ProportionalRect {
Layout.columnSpan: 1
Layout.rowSpan: 2
color: "green"
}
ProportionalRect {
Layout.columnSpan: 5
Layout.rowSpan: 3
color: "blue"
}
}
Layout.fillWidth: true
Layout.fillHeight: true
Layout.preferredWidth: Layout.columnSpan
Layout.preferredHeight: Layout.rowSpan