Reputation: 1999
I'm new to Qt and QML and while I'm trying to learn them I've encountered the following problem which I'm not sure why they appeared.
I'm having a button, at the moment when I'm pressing it will display a new purple Rectangle over the screen. I am trying to position it at the center of the screen, or in other words to fill the whole screen, but for some reason, I can't do that, and It's always going to start from the beginning of Item 2 instead of the beginning of the screen. Also, it's going to be placed under Item 1 and Item 3 instead to overlay them.
MY CODE:
import QtQuick 2.14
import QtQuick.Window 2.14
import QtQuick.Layouts 1.14
import QtQuick.Controls 2.12
Window {
id: mainD
visible: true
width: 640
height: 480
title: qsTr("Hello World")
GridLayout {
id : grid
anchors.fill: parent
rows : 12
columns : 20
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 {
id: id1
color : 'red'
Layout.column: 0
Layout.rowSpan: 10
Layout.columnSpan: 2
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
Rectangle {
id: id2
color : 'green'
Layout.column: 2
Layout.rowSpan: 10
Layout.columnSpan: 18
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
Button{
width: 100
height: 100
anchors.horizontalCenter: parent.horizontalCenter
anchors.verticalCenter: parent.verticalCenter
onClicked: {
id2.state = "STATE_1"
}
}
StackView{
id: st
width: parent.width
height: parent.height + 100
anchors.horizontalCenter: grid.parent.horizontalCenter
anchors.verticalCenter: grid.parent.verticalCenter
visible: false
Rectangle{
anchors.fill: parent
color: "purple"
opacity: 0.7
Button{
width: 100
height: 100
onClicked: {
id2.state = "STATE_2"
}
}
}
}
states: [
State{
name: "STATE_1"
PropertyChanges {
target: st;
visible: true
}
},
State{
name: "STATE_2"
PropertyChanges {
target: st;
visible: false
}
}
]
}
Rectangle {
id: id3
color : 'blue'
Layout.column: 18
Layout.rowSpan: 10
Layout.columnSpan: 2
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
}
}
Can anyone explain to me what I am doing wrong?
Upvotes: 2
Views: 737
Reputation: 2671
I'm having a button, at the moment when I'm pressing it will display a new purple Rectangle over the screen. I am trying to position it at the center of the screen, or in other words to fill the whole screen
As @talamaki mentioned if you want the purple to fill the whole background it is better to have it as child of the main Item instead of having it be part of the grid, and then have it extend the allocated space inside the grid.
but for some reason, I can't do that, and It's always going to start from the beginning of Item 2 instead of the beginning of the screen.
That is because of how grids work. Think of it as like a chess board, item 1 already occupies the first two columns so item 2 will start from 3rd column, and any child of item 2 stars from the coordinate system of item 2. You could make it extend beyond it's starting point but I think it would be cleaner to have the background on the root item.
Also, it's going to be placed under Item 1 and Item 3 instead to overlay them.
To have the purple be underneath 1 and 3 it has to be drawn first (should come first in the QML). If you don't want the button to be affected you should put it below the GridLayout in the QML file so that it is drawn last over it. Putting all this together would be something like this:
import QtQuick 2.14
import QtQuick.Window 2.14
import QtQuick.Layouts 1.14
import QtQuick.Controls 2.12
Window {
id: mainD
visible: true
width: 640
height: 480
title: qsTr("Hello World")
Rectangle{
id: background
anchors.fill: parent
color: "purple"
opacity: 0.7
visible: false
}
GridLayout {
id : grid
anchors.fill: parent
rows : 12
columns : 20
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 {
id: id1
color : 'red'
Layout.column: 0
Layout.rowSpan: 10
Layout.columnSpan: 2
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
Rectangle {
id: id2
color : 'green'
Layout.column: 2
Layout.rowSpan: 10
Layout.columnSpan: 16
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
Rectangle {
id: id3
color : 'blue'
Layout.column: 18
Layout.rowSpan: 10
Layout.columnSpan: 2
Layout.preferredWidth : grid.prefWidth(this)
Layout.preferredHeight : grid.prefHeight(this)
}
}
Button{
width: 100
height: 100
anchors.horizontalCenter: parent.horizontalCenter
anchors.verticalCenter: parent.verticalCenter
onClicked: {
background.visible = !background.visible
}
}
}
From your question it is not clear to me if you want Item 2 to disappear, have its colour blended with background, or have it remain on top when you click the button.
Upvotes: 1
Reputation: 5472
Purple rectangle is an initial item of StackView object with an id "st". It is hidden initially. "id2" is a visual parent of "st". Coordinates of "st" are relative to its visual parent. You are setting its width to be its parent's width and height to be parent's height + 100 so its (0,0) coordinate goes to parent's (0,0). You should read more from the documentation: Visual Parent in Qt Quick.
If you want to fill the whole screen with purple rectangle and position it on top of other visual items you can do it by moving "st" out from the "grid" and place it on the same level with it. Now both "grid" and "st" are children of "mainD", and because StackView is below "grid" you don't need to play with z values but when "st" becomes visible it is rendered on top of "grid".
Window {
id: mainD
...
GridLayout {
id : grid
...
}
StackView{
id: st
width: parent.width
height: parent.height// + 100
//anchors.horizontalCenter: grid.parent.horizontalCenter
//anchors.verticalCenter: grid.parent.verticalCenter
visible: false
Rectangle{
anchors.fill: parent
color: "purple"
opacity: 0.7
Button{
width: 100
height: 100
onClicked: {
id2.state = "STATE_2"
}
}
}
}
}
I recommend Positioning elements
chapter from free Qt5 Cadaques book for further reading.
Upvotes: 2